<commit_before>// Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/dom_ui/options/font_settings_utils.h"

#include <windows.h>

#include "base/values.h"

static int CALLBACK EnumFontFamExProc(ENUMLOGFONTEXW *logical_font,
                                      NEWTEXTMETRICEXW *physical_font,
                                      DWORD font_type,
                                      LPARAM lparam) {
  ListValue* font_list = reinterpret_cast<ListValue*>(lparam);
  if (font_list) {
    const LOGFONTW& lf = logical_font->elfLogFont;
    if (lf.lfFaceName[0] && lf.lfFaceName[0] != '@') {
      ListValue* font_item = new ListValue();
      std::wstring face_name(lf.lfFaceName);
      font_item->Append(Value::CreateStringValue(face_name));
      font_item->Append(Value::CreateStringValue(face_name));
      font_list->Append(font_item);
    }
  }
  return 1;
}

ListValue* FontSettingsUtilities::GetFontsList() {
  ListValue* font_list = new ListValue;

  LOGFONTW logfont;
  memset(&logfont, 0, sizeof(logfont));
  logfont.lfCharSet = DEFAULT_CHARSET;

  HDC hdc = ::GetDC(NULL);
  ::EnumFontFamiliesExW(hdc, &logfont, (FONTENUMPROCW)&EnumFontFamExProc,
                        (LPARAM)font_list, 0);
  ::ReleaseDC(NULL, hdc);

  return font_list;
}

void FontSettingsUtilities::ValidateSavedFonts(PrefService* prefs) {
  // nothing to do for Windows.
}

<commit_msg>dom-ui settings: Eliminate duplicate font names in WinChrome.<commit_after>// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/dom_ui/options/font_settings_utils.h"

#include <set>
#include <string>
#include <windows.h>

#include "base/values.h"

static int CALLBACK EnumFontFamExProc(ENUMLOGFONTEXW *logical_font,
                                      NEWTEXTMETRICEXW *physical_font,
                                      DWORD font_type,
                                      LPARAM lparam) {
  std::set<std::wstring>* font_names =
      reinterpret_cast<std::set<std::wstring>*>(lparam);
  if (font_names) {
    const LOGFONTW& lf = logical_font->elfLogFont;
    if (lf.lfFaceName[0] && lf.lfFaceName[0] != '@') {
      std::wstring face_name(lf.lfFaceName);
      font_names->insert(face_name);
    }
  }
  return 1;
}

ListValue* FontSettingsUtilities::GetFontsList() {
  std::set<std::wstring> font_names;

  LOGFONTW logfont;
  memset(&logfont, 0, sizeof(logfont));
  logfont.lfCharSet = DEFAULT_CHARSET;

  HDC hdc = ::GetDC(NULL);
  ::EnumFontFamiliesExW(hdc, &logfont, (FONTENUMPROCW)&EnumFontFamExProc,
                        (LPARAM)&font_names, 0);
  ::ReleaseDC(NULL, hdc);

  ListValue* font_list = new ListValue;
  std::set<std::wstring>::iterator iter;
  for (iter = font_names.begin(); iter != font_names.end(); iter++) {
    ListValue* font_item = new ListValue();
    font_item->Append(Value::CreateStringValue(*iter));
    font_item->Append(Value::CreateStringValue(*iter));
    font_list->Append(font_item);
  }
  return font_list;
}

void FontSettingsUtilities::ValidateSavedFonts(PrefService* prefs) {
  // nothing to do for Windows.
}

<|endoftext|>


<commit_before>// TCP sender
// Author: Max Schwarz <max.schwarz@uni-bonn.de>

#include "tcp_sender.h"
#include "../topic_info.h"

namespace sb_topic_transport
{

TCPSender::TCPSender()
 : m_nh("~")
 , m_fd(-1)
{
	std::string addr;
	if(!m_nh.getParam("address", addr))
	{
		ROS_FATAL("tcp_sender needs an 'address' parameter!");
		throw std::runtime_error("tcp_sender needs an 'address' parameter!");
	}

	int port;
	if(!m_nh.getParam("port", port))
	{
		ROS_FATAL("tcp_sender needs a 'port' parameter!");
		throw std::runtime_error("tcp_sender needs a 'port' parameter!");
	}

	memset(&m_addr, 0, sizeof(m_addr));
	m_addr.sin_family = AF_INET;
	m_addr.sin_addr.s_addr = inet_addr(addr.c_str());
	m_addr.sin_port = htons(port);

	XmlRpc::XmlRpcValue list;
	m_nh.getParam("topics", list);

	ROS_ASSERT(list.getType() == XmlRpc::XmlRpcValue::TypeArray);

	for(int32_t i = 0; i < list.size(); ++i)
	{
		ROS_ASSERT(list[i].getType() == XmlRpc::XmlRpcValue::TypeString);

		boost::function<void(const topic_tools::ShapeShifter&)> func;
		func = boost::bind(&TCPSender::send, this, (std::string)list[i], _1);

		m_subs.push_back(
			m_nh.subscribe<const topic_tools::ShapeShifter>((std::string)list[i], 20, func)
		);
	}
}

TCPSender::~TCPSender()
{
}

bool TCPSender::connect()
{
	m_fd = socket(AF_INET, SOCK_STREAM, 0);
	if(m_fd < 0)
	{
		ROS_ERROR("Could not create socket: %s", strerror(errno));
		return false;
	}

	if(::connect(m_fd, (sockaddr*)&m_addr, sizeof(m_addr)) != 0)
	{
		ROS_ERROR("Could not connect: %s", strerror(errno));
		return false;
	}

	return true;
}

class PtrStream
{
public:
	PtrStream(uint8_t* ptr)
	 : m_ptr(ptr)
	{}

	inline uint8_t* advance(int)
	{ return m_ptr; }
private:
	uint8_t* m_ptr;
};

static void push(const void* data, size_t size, std::vector<uint8_t>* dest)
{
	int pos = dest->size();
	dest->resize(pos + size);
	memcpy(dest->data() + pos, data, size);
}

void TCPSender::send(const std::string& topic, const topic_tools::ShapeShifter& shifter)
{
	std::string type = shifter.getDataType();
	std::string md5 = shifter.getMD5Sum();
	uint32_t size = shifter.size();

	std::vector<uint8_t> packet;
	packet.reserve(
		sizeof(TCPHeader) + topic.length() + type.length() + size
	);

	// Header
	TCPHeader header;
	header.topic_len = topic.length();
	header.type_len = type.length();
	header.data_len = size;

	topic_info::packMD5(md5, header.topic_md5sum);

	push(&header, sizeof(header), &packet);

	// Topic name
	push(topic.c_str(), topic.length(), &packet);

	// Type name
	push(type.c_str(), type.length(), &packet);

	// Data
	uint32_t pos = packet.size();
	packet.resize(pos + size);
	PtrStream stream(packet.data());
	shifter.write(stream);

	// Try to send the packet
	while(1)
	{
		if(m_fd == -1)
		{
			if(!connect())
			{
				ROS_WARN("Connection failed, trying again");
				continue;
			}
		}

		if(write(m_fd, packet.data(), packet.size()) != (int)packet.size())
		{
			ROS_WARN("Could not send data, trying again");
			close(m_fd);
			m_fd = -1;
			continue;
		}

		// Read ACK
		uint8_t ack;
		if(read(m_fd, &ack, 1) != 1)
		{
			ROS_WARN("Could not read ACK, sending again (!)");
			close(m_fd);
			m_fd = -1;
			continue;
		}
	}
}

}

int main(int argc, char** argv)
{
	ros::init(argc, argv, "tcp_sender");

	sb_topic_transport::TCPSender sender;

	ros::spin();

	return 0;
}

<commit_msg>sb_topic_transport: TCP sender: drop message after 10 attempts<commit_after>// TCP sender
// Author: Max Schwarz <max.schwarz@uni-bonn.de>

#include "tcp_sender.h"
#include "../topic_info.h"

namespace sb_topic_transport
{

TCPSender::TCPSender()
 : m_nh("~")
 , m_fd(-1)
{
	std::string addr;
	if(!m_nh.getParam("address", addr))
	{
		ROS_FATAL("tcp_sender needs an 'address' parameter!");
		throw std::runtime_error("tcp_sender needs an 'address' parameter!");
	}

	int port;
	if(!m_nh.getParam("port", port))
	{
		ROS_FATAL("tcp_sender needs a 'port' parameter!");
		throw std::runtime_error("tcp_sender needs a 'port' parameter!");
	}

	memset(&m_addr, 0, sizeof(m_addr));
	m_addr.sin_family = AF_INET;
	m_addr.sin_addr.s_addr = inet_addr(addr.c_str());
	m_addr.sin_port = htons(port);

	XmlRpc::XmlRpcValue list;
	m_nh.getParam("topics", list);

	ROS_ASSERT(list.getType() == XmlRpc::XmlRpcValue::TypeArray);

	for(int32_t i = 0; i < list.size(); ++i)
	{
		ROS_ASSERT(list[i].getType() == XmlRpc::XmlRpcValue::TypeString);

		boost::function<void(const topic_tools::ShapeShifter&)> func;
		func = boost::bind(&TCPSender::send, this, (std::string)list[i], _1);

		m_subs.push_back(
			m_nh.subscribe<const topic_tools::ShapeShifter>((std::string)list[i], 20, func)
		);
	}
}

TCPSender::~TCPSender()
{
}

bool TCPSender::connect()
{
	m_fd = socket(AF_INET, SOCK_STREAM, 0);
	if(m_fd < 0)
	{
		ROS_ERROR("Could not create socket: %s", strerror(errno));
		return false;
	}

	if(::connect(m_fd, (sockaddr*)&m_addr, sizeof(m_addr)) != 0)
	{
		ROS_ERROR("Could not connect: %s", strerror(errno));
		return false;
	}

	return true;
}

class PtrStream
{
public:
	PtrStream(uint8_t* ptr)
	 : m_ptr(ptr)
	{}

	inline uint8_t* advance(int)
	{ return m_ptr; }
private:
	uint8_t* m_ptr;
};

static void push(const void* data, size_t size, std::vector<uint8_t>* dest)
{
	int pos = dest->size();
	dest->resize(pos + size);
	memcpy(dest->data() + pos, data, size);
}

void TCPSender::send(const std::string& topic, const topic_tools::ShapeShifter& shifter)
{
	std::string type = shifter.getDataType();
	std::string md5 = shifter.getMD5Sum();
	uint32_t size = shifter.size();

	std::vector<uint8_t> packet;
	packet.reserve(
		sizeof(TCPHeader) + topic.length() + type.length() + size
	);

	// Header
	TCPHeader header;
	header.topic_len = topic.length();
	header.type_len = type.length();
	header.data_len = size;

	topic_info::packMD5(md5, header.topic_md5sum);

	push(&header, sizeof(header), &packet);

	// Topic name
	push(topic.c_str(), topic.length(), &packet);

	// Type name
	push(type.c_str(), type.length(), &packet);

	// Data
	uint32_t pos = packet.size();
	packet.resize(pos + size);
	PtrStream stream(packet.data());
	shifter.write(stream);

	// Try to send the packet
	for(int tries = 0; tries < 10; ++tries)
	{
		if(m_fd == -1)
		{
			if(!connect())
			{
				ROS_WARN("Connection failed, trying again");
				continue;
			}
		}

		if(write(m_fd, packet.data(), packet.size()) != (int)packet.size())
		{
			ROS_WARN("Could not send data, trying again");
			close(m_fd);
			m_fd = -1;
			continue;
		}

		// Read ACK
		uint8_t ack;
		if(read(m_fd, &ack, 1) != 1)
		{
			ROS_WARN("Could not read ACK, sending again (!)");
			close(m_fd);
			m_fd = -1;
			continue;
		}

		return;
	}

	ROS_ERROR("Could not send TCP packet. Dropping message from topic %s!", topic.c_str());
}

}

int main(int argc, char** argv)
{
	ros::init(argc, argv, "tcp_sender");

	sb_topic_transport::TCPSender sender;

	ros::spin();

	return 0;
}

<|endoftext|>


<commit_before>/*
Copyright (c) 2015 - present Advanced Micro Devices, Inc. All rights reserved.

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.
*/

#include <cstdio>
#include <fstream>
#include <set>
#include <cmath>
#include <chrono>
#include <iomanip>
#include <sstream>
#include "CUDA2HIP.h"
#include "LLVMCompat.h"
#include "HipifyAction.h"
#include "ArgParse.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/Path.h"

#define DEBUG_TYPE "cuda2hip"

std::string sHipify = "[HIPIFY] ", sConflict = "conflict: ", sError = "error: ";
namespace ct = clang::tooling;

std::string getAbsoluteDirectory(const std::string& sDir, std::error_code& EC,
                                 const std::string& sDirType = "temporary",
                                 bool bCreateDir = true) {
  if (sDir.empty()) {
    return sDir;
  }
  SmallString<256> dirAbsPath;
  EC = llcompat::real_path(sDir, dirAbsPath, true);
  if (!EC && sys::fs::is_regular_file(dirAbsPath)) {
    llvm::errs() << "\n" << sHipify << sError << sDir << " is not a directory\n";
    EC = std::error_code(static_cast<int>(std::errc::not_a_directory), std::generic_category());
    return "";
  }
  if (EC && bCreateDir) {
    EC = sys::fs::create_directory(sDir);
    if (EC) {
      llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << sDirType << " directory: " << sDir << "\n";
      return "";
    }
    EC = llcompat::real_path(sDir, dirAbsPath, true);
    if (EC) {
      llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << sDirType << " directory: " << sDir << "\n";
      return "";
    }
  }
  return dirAbsPath.c_str();
}

int main(int argc, const char **argv) {
  std::vector<const char*> new_argv(argv, argv + argc);
  if (std::find(new_argv.begin(), new_argv.end(), std::string("--")) == new_argv.end()) {
    new_argv.push_back("--");
    new_argv.push_back(nullptr);
    argv = new_argv.data();
    argc++;
  }
  llcompat::PrintStackTraceOnErrorSignal();
  ct::CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::OneOrMore);
  std::vector<std::string> fileSources = OptionsParser.getSourcePathList();
  std::string dst = OutputFilename, dstDir = OutputDir;
  std::error_code EC;
  std::string sOutputDirAbsPath = getAbsoluteDirectory(OutputDir, EC, "output");
  if (EC) {
    return 1;
  }
  if (!dst.empty()) {
    if (fileSources.size() > 1) {
      llvm::errs() << sHipify << sConflict << "-o and multiple source files are specified.\n";
      return 1;
    }
    if (Inplace) {
      llvm::errs() << sHipify << sConflict << "both -o and -inplace options are specified.\n";
      return 1;
    }
    if (NoOutput) {
      llvm::errs() << sHipify << sConflict << "both -no-output and -o options are specified.\n";
      return 1;
    }
    if (!dstDir.empty()) {
      dst = sOutputDirAbsPath + "/" + dst;
    }
  }
  if (NoOutput && Inplace) {
    llvm::errs() << sHipify << sConflict << "both -no-output and -inplace options are specified.\n";
    return 1;
  }
  if (!dstDir.empty() && Inplace) {
    llvm::errs() << sHipify << sConflict << "both -o-dir and -inplace options are specified.\n";
    return 1;
  }
  if (Examine) {
    NoOutput = PrintStats = true;
  }
  int Result = 0;
  SmallString<128> tmpFile;
  SmallString<256> sourceAbsPath;
  StringRef sourceFileName, ext = "hip";
  std::string sTmpFileName;
  std::string sTmpDirAbsParh = getAbsoluteDirectory(TemporaryDir, EC);
  if (EC) {
    return 1;
  }
  // Arguments for the Statistics print routines.
  std::unique_ptr<std::ostream> csv = nullptr;
  llvm::raw_ostream* statPrint = nullptr;
  if (!OutputStatsFilename.empty()) {
    csv = std::unique_ptr<std::ostream>(new std::ofstream(OutputStatsFilename, std::ios_base::trunc));
  }
  if (PrintStats) {
    statPrint = &llvm::errs();
  }
  for (const auto & src : fileSources) {
    if (dst.empty()) {
      if (Inplace) {
        dst = src;
      } else {
        dst = src + "." + ext.str();
        if (!dstDir.empty()) {
          dst = sOutputDirAbsPath + "/" + dst;
        }
      }
    }
    // Create a copy of the file to work on. When we're done, we'll move this onto the
    // output (which may mean overwriting the input, if we're in-place).
    // Should we fail for some reason, we'll just leak this file and not corrupt the input.
    EC = llcompat::real_path(src, sourceAbsPath, true);
    sourceFileName = sys::path::filename(sourceAbsPath);
    if (EC) {
      llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << src << "\n";
      Result = 1;
      continue;
    }
    if (TemporaryDir.empty()) {
      EC = sys::fs::createTemporaryFile(sourceFileName, ext, tmpFile);
      if (EC) {
        llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << tmpFile << "\n";
        Result = 1;
        continue;
      }
    } else {
      sTmpFileName = sTmpDirAbsParh + "/" + sourceFileName.str() + "." + ext.str();
      tmpFile = sTmpFileName;
    }
    EC = sys::fs::copy_file(src, tmpFile);
    if (EC) {
      llvm::errs() << "\n" << sHipify << sError << EC.message() << ": while copying " << src << " to " << tmpFile << "\n";
      Result = 1;
      continue;
    }
    // Initialise the statistics counters for this file.
    Statistics::setActive(src);
    // RefactoringTool operates on the file in-place. Giving it the output path is no good,
    // because that'll break relative includes, and we don't want to overwrite the input file.
    // So what we do is operate on a copy, which we then move to the output.
    ct::RefactoringTool Tool(OptionsParser.getCompilations(), std::string(tmpFile.c_str()));
    ct::Replacements& replacementsToUse = llcompat::getReplacements(Tool, tmpFile.c_str());
    ReplacementsFrontendActionFactory<HipifyAction> actionFactory(&replacementsToUse);
    std::string sInclude = "-I" + sys::path::parent_path(sourceAbsPath).str();
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(sInclude.c_str(), ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("cuda", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-x", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("--cuda-host-only", ct::ArgumentInsertPosition::BEGIN));
    if (!CudaPath.empty()) {
      std::string sCudaPath = "--cuda-path=" + CudaPath;
      Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(sCudaPath.c_str(), ct::ArgumentInsertPosition::BEGIN));
    }
    // Includes for clang's CUDA wrappers for using by packaged hipify-clang
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("./include", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-isystem", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("./include/cuda_wrappers", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-isystem", ct::ArgumentInsertPosition::BEGIN));
    // Ensure at least c++11 is used.
    std::string stdCpp = "-std=c++11";
#if defined(_MSC_VER)
    stdCpp = "-std=c++14";
#endif
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(stdCpp.c_str(), ct::ArgumentInsertPosition::BEGIN));
#if defined(HIPIFY_CLANG_RES)
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-resource-dir=" HIPIFY_CLANG_RES));
#endif
    if (!MacroNames.empty()) {
      for (std::string s : MacroNames) {
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-D", ct::ArgumentInsertPosition::END));
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(s.c_str(), ct::ArgumentInsertPosition::END));
      }
    }
    if (!IncludeDirs.empty()) {
      for (std::string s : IncludeDirs) {
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-I", ct::ArgumentInsertPosition::END));
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(s.c_str(), ct::ArgumentInsertPosition::END));
      }
    }
    Tool.appendArgumentsAdjuster(ct::getClangSyntaxOnlyAdjuster());
    Statistics& currentStat = Statistics::current();
    // Hipify _all_ the things!
    if (Tool.runAndSave(&actionFactory)) {
      currentStat.hasErrors = true;
      LLVM_DEBUG(llvm::dbgs() << "Skipped some replacements.\n");
    }
    // Copy the tmpfile to the output
    if (!NoOutput && !currentStat.hasErrors) {
      EC = sys::fs::copy_file(tmpFile, dst);
      if (EC) {
        llvm::errs() << "\n" << sHipify << sError << EC.message() << ": while copying " << tmpFile << " to " << dst << "\n";
        Result = 1;
        continue;
      }
    }
    // Remove the tmp file without error check
    if (!SaveTemps) {
      sys::fs::remove(tmpFile);
    }
    Statistics::current().markCompletion();
    Statistics::current().print(csv.get(), statPrint);
    dst.clear();
  }
  if (fileSources.size() > 1) {
    Statistics::printAggregate(csv.get(), statPrint);
  }
  return Result;
}
<commit_msg>[HIPIFY][fix][#867] Relative paths routines fixes and improvements<commit_after>/*
Copyright (c) 2015 - present Advanced Micro Devices, Inc. All rights reserved.

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.
*/

#include <cstdio>
#include <fstream>
#include <set>
#include <cmath>
#include <chrono>
#include <iomanip>
#include <sstream>
#include "CUDA2HIP.h"
#include "LLVMCompat.h"
#include "HipifyAction.h"
#include "ArgParse.h"
#include "llvm/Support/Debug.h"
#include "llvm/Support/Path.h"

#define DEBUG_TYPE "cuda2hip"

std::string sHipify = "[HIPIFY] ", sConflict = "conflict: ", sError = "error: ";
namespace ct = clang::tooling;

std::string getAbsoluteFilePath(const std::string& sFile, std::error_code& EC) {
  if (sFile.empty()) {
    return sFile;
  }
  if (!sys::fs::exists(sFile)) {
    llvm::errs() << "\n" << sHipify << sError << "source file: " << sFile << " doesn't exist\n";
    EC = std::error_code(static_cast<int>(std::errc::no_such_file_or_directory), std::generic_category());
    return "";
  }
  SmallString<256> fileAbsPath;
  EC = llcompat::real_path(sFile, fileAbsPath, true);
  if (EC) {
    llvm::errs() << "\n" << sHipify << sError << EC.message() << ": source file: " << sFile << "\n";
    return "";
  }
  EC = std::error_code();
  return fileAbsPath.c_str();
}

std::string getAbsoluteDirectoryPath(const std::string& sDir, std::error_code& EC,
                                 const std::string& sDirType = "temporary",
                                 bool bCreateDir = true) {
  if (sDir.empty()) {
    return sDir;
  }
  EC = std::error_code();
  SmallString<256> dirAbsPath;
  if (sys::fs::exists(sDir)) {
    if (sys::fs::is_regular_file(sDir)) {
      llvm::errs() << "\n" << sHipify << sError << sDir << " is not a directory\n";
      EC = std::error_code(static_cast<int>(std::errc::not_a_directory), std::generic_category());
      return "";
    }
  } else {
    if (bCreateDir) {
      EC = sys::fs::create_directory(sDir);
      if (EC) {
        llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << sDirType << " directory: " << sDir << "\n";
        return "";
      }
    } else {
      llvm::errs() << "\n" << sHipify << sError << sDirType << " directory: " << sDir << " doesn't exist\n";
      EC = std::error_code(static_cast<int>(std::errc::no_such_file_or_directory), std::generic_category());
      return "";
    }
  }
  EC = llcompat::real_path(sDir, dirAbsPath, true);
  if (EC) {
    llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << sDirType << " directory: " << sDir << "\n";
    return "";
  }
  return dirAbsPath.c_str();
}

int main(int argc, const char **argv) {
  std::vector<const char*> new_argv(argv, argv + argc);
  if (std::find(new_argv.begin(), new_argv.end(), std::string("--")) == new_argv.end()) {
    new_argv.push_back("--");
    new_argv.push_back(nullptr);
    argv = new_argv.data();
    argc++;
  }
  llcompat::PrintStackTraceOnErrorSignal();
  ct::CommonOptionsParser OptionsParser(argc, argv, ToolTemplateCategory, llvm::cl::OneOrMore);
  std::vector<std::string> fileSources = OptionsParser.getSourcePathList();
  std::string dst = OutputFilename, dstDir = OutputDir;
  std::error_code EC;
  std::string sOutputDirAbsPath = getAbsoluteDirectoryPath(OutputDir, EC, "output");
  if (EC) {
    return 1;
  }
  if (!dst.empty()) {
    if (fileSources.size() > 1) {
      llvm::errs() << sHipify << sConflict << "-o and multiple source files are specified.\n";
      return 1;
    }
    if (Inplace) {
      llvm::errs() << sHipify << sConflict << "both -o and -inplace options are specified.\n";
      return 1;
    }
    if (NoOutput) {
      llvm::errs() << sHipify << sConflict << "both -no-output and -o options are specified.\n";
      return 1;
    }
    if (!dstDir.empty()) {
      dst = sOutputDirAbsPath + "/" + dst;
    }
  }
  if (NoOutput && Inplace) {
    llvm::errs() << sHipify << sConflict << "both -no-output and -inplace options are specified.\n";
    return 1;
  }
  if (!dstDir.empty() && Inplace) {
    llvm::errs() << sHipify << sConflict << "both -o-dir and -inplace options are specified.\n";
    return 1;
  }
  if (Examine) {
    NoOutput = PrintStats = true;
  }
  int Result = 0;
  SmallString<128> tmpFile;
  StringRef sourceFileName, ext = "hip";
  std::string sTmpFileName, sSourceAbsPath;
  std::string sTmpDirAbsParh = getAbsoluteDirectoryPath(TemporaryDir, EC);
  if (EC) {
    return 1;
  }
  // Arguments for the Statistics print routines.
  std::unique_ptr<std::ostream> csv = nullptr;
  llvm::raw_ostream* statPrint = nullptr;
  if (!OutputStatsFilename.empty()) {
    csv = std::unique_ptr<std::ostream>(new std::ofstream(OutputStatsFilename, std::ios_base::trunc));
  }
  if (PrintStats) {
    statPrint = &llvm::errs();
  }
  for (const auto & src : fileSources) {
    // Create a copy of the file to work on. When we're done, we'll move this onto the
    // output (which may mean overwriting the input, if we're in-place).
    // Should we fail for some reason, we'll just leak this file and not corrupt the input.
    sSourceAbsPath = getAbsoluteFilePath(src, EC);
    if (EC) {
      continue;
    }
    sourceFileName = sys::path::filename(sSourceAbsPath);
    if (dst.empty()) {
      if (Inplace) {
        dst = src;
      } else {
        dst = src + "." + ext.str();
        if (!dstDir.empty()) {
          dst = sOutputDirAbsPath + "/" + sourceFileName.str() + "." + ext.str();
        }
      }
    }
    if (TemporaryDir.empty()) {
      EC = sys::fs::createTemporaryFile(sourceFileName, ext, tmpFile);
      if (EC) {
        llvm::errs() << "\n" << sHipify << sError << EC.message() << ": " << tmpFile << "\n";
        Result = 1;
        continue;
      }
    } else {
      sTmpFileName = sTmpDirAbsParh + "/" + sourceFileName.str() + "." + ext.str();
      tmpFile = sTmpFileName;
    }
    EC = sys::fs::copy_file(src, tmpFile);
    if (EC) {
      llvm::errs() << "\n" << sHipify << sError << EC.message() << ": while copying " << src << " to " << tmpFile << "\n";
      Result = 1;
      continue;
    }
    // Initialise the statistics counters for this file.
    Statistics::setActive(src);
    // RefactoringTool operates on the file in-place. Giving it the output path is no good,
    // because that'll break relative includes, and we don't want to overwrite the input file.
    // So what we do is operate on a copy, which we then move to the output.
    ct::RefactoringTool Tool(OptionsParser.getCompilations(), std::string(tmpFile.c_str()));
    ct::Replacements& replacementsToUse = llcompat::getReplacements(Tool, tmpFile.c_str());
    ReplacementsFrontendActionFactory<HipifyAction> actionFactory(&replacementsToUse);
    std::string sInclude = "-I" + sys::path::parent_path(sSourceAbsPath).str();
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(sInclude.c_str(), ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("cuda", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-x", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("--cuda-host-only", ct::ArgumentInsertPosition::BEGIN));
    if (!CudaPath.empty()) {
      std::string sCudaPath = "--cuda-path=" + CudaPath;
      Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(sCudaPath.c_str(), ct::ArgumentInsertPosition::BEGIN));
    }
    // Includes for clang's CUDA wrappers for using by packaged hipify-clang
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("./include", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-isystem", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("./include/cuda_wrappers", ct::ArgumentInsertPosition::BEGIN));
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-isystem", ct::ArgumentInsertPosition::BEGIN));
    // Ensure at least c++11 is used.
    std::string stdCpp = "-std=c++11";
#if defined(_MSC_VER)
    stdCpp = "-std=c++14";
#endif
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(stdCpp.c_str(), ct::ArgumentInsertPosition::BEGIN));
#if defined(HIPIFY_CLANG_RES)
    Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-resource-dir=" HIPIFY_CLANG_RES));
#endif
    if (!MacroNames.empty()) {
      for (std::string s : MacroNames) {
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-D", ct::ArgumentInsertPosition::END));
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(s.c_str(), ct::ArgumentInsertPosition::END));
      }
    }
    if (!IncludeDirs.empty()) {
      for (std::string s : IncludeDirs) {
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster("-I", ct::ArgumentInsertPosition::END));
        Tool.appendArgumentsAdjuster(ct::getInsertArgumentAdjuster(s.c_str(), ct::ArgumentInsertPosition::END));
      }
    }
    Tool.appendArgumentsAdjuster(ct::getClangSyntaxOnlyAdjuster());
    Statistics& currentStat = Statistics::current();
    // Hipify _all_ the things!
    if (Tool.runAndSave(&actionFactory)) {
      currentStat.hasErrors = true;
      LLVM_DEBUG(llvm::dbgs() << "Skipped some replacements.\n");
    }
    // Copy the tmpfile to the output
    if (!NoOutput && !currentStat.hasErrors) {
      EC = sys::fs::copy_file(tmpFile, dst);
      if (EC) {
        llvm::errs() << "\n" << sHipify << sError << EC.message() << ": while copying " << tmpFile << " to " << dst << "\n";
        Result = 1;
        continue;
      }
    }
    // Remove the tmp file without error check
    if (!SaveTemps) {
      sys::fs::remove(tmpFile);
    }
    Statistics::current().markCompletion();
    Statistics::current().print(csv.get(), statPrint);
    dst.clear();
  }
  if (fileSources.size() > 1) {
    Statistics::printAggregate(csv.get(), statPrint);
  }
  return Result;
}
<|endoftext|>


<commit_before>/*
 * Copyright (C) 2012
 * Alessio Sclocco <a.sclocco@vu.nl>
 *
 * This program 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 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

#include <string>
#include <limits>
using std::string;
using std::numeric_limits;

#ifndef OBSERVATION_HPP
#define OBSERVATION_HPP

namespace AstroData {

template< typename T > class Observation {
public:
	Observation(string name, string dataType);
	~Observation();

	// General observation parameters
	inline void setNrSeconds(unsigned int seconds);
	inline void setNrStations(unsigned int nrStations);
	inline void setNrBeams(unsigned int beams);
	inline void setNrSamplesPerSecond(unsigned int samples);
	inline void setNrSamplesPerPaddedSecond(unsigned int samples);
	void setNrChannels(unsigned int channels);
	inline void setNrPaddedChannels(unsigned int channels);

	// Frequency parameters
	inline void setMinFreq(float freq);
	inline void setMaxFreq(float freq);
	inline void setChannelBandwidth(float bandwidth);

	// Statistical properties
	inline void setMinValue(T value);
	inline void setMaxValue(T value);
	inline void setAverage(unsigned int channel, double avg);
	inline void setVariance(unsigned int channel, double var);
	inline void setStdDev(unsigned int channel, double dev);

	// Dispersion measures
	inline void setNrDMs(unsigned int dms);
	inline void setNrPaddedDMs(unsigned int dms);
	inline void setFirstDM(float dm);
	inline void setDMStep(float step);

	// Periods
	inline void setNrPeriods(unsigned int periods);
	inline void setNrPaddedPeriods(unsigned int periods);
	inline void setNrBins(unsigned int bins);
	inline void setNrPaddedBins(unsigned int bins);

	inline string getName();
	inline string getDataType();

	// General observation parameters
	inline unsigned int getNrSeconds();
	inline unsigned int getNrStations();
	inline unsigned int getNrBeams();
	inline unsigned int getNrSamplesPerSecond();
	inline float getSamplingRate();
	inline unsigned int getNrSamplesPerPaddedSecond();
	inline unsigned int getNrChannels();
	inline unsigned int getNrPaddedChannels();

	// Frequency parameters
	inline float getMinFreq();
	inline float getMaxFreq();
	inline float getChannelBandwidth();

	// Statistical properties
	inline T getMinValue();
	inline T getMaxValue();
	inline double getAverage(unsigned int channel);
	inline double getVariance(unsigned int channel);
	inline double getStdDev(unsigned int channel);

	// Dispersion measures
	inline unsigned int getNrDMs();
	inline unsigned int getNrPaddedDMs();
	inline float getFirstDM();
	inline float getDMStep();

	// Periods
	inline unsigned int getNrPeriods();
	inline unsigned int getNrPaddedPeriods();
	inline unsigned int getNrBins();
	inline unsigned int getNrPaddedBins();

private:
	string name;
	string dataType;

	unsigned int nrSeconds;
	unsigned int nrStations;
	unsigned int nrBeams;
	unsigned int nrSamplesPerSecond;
	float samplingRate;
	unsigned int nrSamplesPerPaddedSecond;
	unsigned int nrChannels;
	unsigned int nrPaddedChannels;

	float minFreq;
	float maxFreq;
	float channelBandwidth;

	T minValue;
	T maxValue;
	double *average;
	double *variance;
	double *stdDev;

	unsigned int nrDMs;
	unsigned int nrPaddedDMs;
	float firstDM;
	float DMStep;

	unsigned int nrPeriods;
	unsigned int nrPaddedPeriods;
	unsigned int nrBins;
	unsigned int nrPaddedBins;
};

// Implementation

template< typename T > Observation< T >::Observation(string name, string dataType) : name(name), dataType(dataType), nrSeconds(0), nrStations(0), nrBeams(0), nrSamplesPerSecond(0), samplingRate(0.0f), nrSamplesPerPaddedSecond(0), nrChannels(0), nrPaddedChannels(0), minFreq(0.0f), maxFreq(0.0f), channelBandwidth(0.0f), minValue(numeric_limits< T >::max()), maxValue(numeric_limits< T >::min()), average(0.0), variance(0.0), stdDev(0.0), nrDMs(0), nrPaddedDMs(0), firstDM(0.0f), DMStep(0.0f), nrPeriods(0), nrPaddedPeriods(0), nrBins(0), nrPaddedBins(0) {}

template< typename T > Observation< T >::~Observation() {
	delete [] average;
	delete [] variance;
	delete [] stdDev;
}

template< typename T > inline void Observation< T >::setNrSeconds(unsigned int seconds) {
	nrSeconds = seconds;
}

template< typename T > inline void Observation< T >::setNrStations(unsigned int stations) {
	nrStations = stations;
}

template< typename T > inline void Observation< T >::setNrBeams(unsigned int beams) {
	nrBeams = beams;
}

template< typename T > inline void Observation< T >::setNrSamplesPerSecond(unsigned int samples) {
	nrSamplesPerSecond = samples;
	samplingRate = 1.0f / samples;
}

template< typename T > inline void Observation< T >::setNrSamplesPerPaddedSecond(unsigned int samples) {
	nrSamplesPerPaddedSecond = samples;
}

template< typename T > void Observation< T >::setNrChannels(unsigned int channels) {
	nrChannels = channels;

	average = new double [channels];
	variance = new double [channels];
	stdDev = new double [channels];
}

template< typename T > void Observation< T >::setNrPaddedChannels(unsigned int channels) {
	nrPaddedChannels = channels;
}

template< typename T > inline void Observation< T >::setMinFreq(float freq) {
	minFreq = freq;
}

template< typename T > inline void Observation< T >::setMaxFreq(float freq) {
	maxFreq = freq;
}

template< typename T > inline void Observation< T >::setChannelBandwidth(float bandwidth) {
	channelBandwidth = bandwidth;
}

template< typename T > inline void Observation< T >::setMinValue(T value) {
	minValue = value;
}

template< typename T > inline void Observation< T >::setMaxValue(T value) {
	maxValue = value;
}

template< typename T > inline void Observation< T >::setAverage(unsigned int channel, double avg) {
	average[channel] = avg;
}

template< typename T > inline void Observation< T >::setVariance(unsigned int channel, double var) {
	variance[channel] = var;
}

template< typename T > inline void Observation< T >::setStdDev(unsigned int channel, double dev) {
	stdDev[channel] = dev;
}

template< typename T > inline void Observation< T >::setNrDMs(unsigned int dms) {
	nrDMs = dms;
}

template< typename T > inline void Observation< T >::setNrPaddedDMs(unsigned int dms) {
	nrPaddedDMs = dms;
}

template< typename T > inline void Observation< T >::setFirstDM(float dm) {
	firstDM = dm;
}

template< typename T > inline void Observation< T >::setDMStep(float step) {
	DMStep = step;
}

template< typename T > inline void Observation< T >::setNrPeriods(unsigned int periods) {
	nrPeriods = periods;
}

template< typename T > inline void Observation< T >::setNrPaddedPeriods(unsigned int periods) {
	nrPaddedPeriods = periods;
}

template< typename T > inline void Observation< T >::setNrBins(unsigned int bins) {
	nrBins = bins;
}

template< typename T > inline void Observation< T >::setNrPaddedBins(unsigned int bins) {
	nrPaddedBins = bins;
}

template< typename T > inline string Observation< T >::getName() {
	return name;
}

template< typename T > inline string Observation< T >::getDataType() {
	return dataType;
}

template< typename T > inline unsigned int Observation< T >::getNrSeconds() {
	return nrSeconds;
}

template< typename T > inline unsigned int Observation< T >::getNrStations() {
	return nrStations;
}

template< typename T > inline unsigned int Observation< T >::getNrBeams() {
	return nrBeams;
}

template< typename T > inline unsigned int Observation< T >::getNrSamplesPerSecond() {
	return nrSamplesPerSecond;
}

template< typename T > inline float Observation< T >::getSamplingRate() {
	return samplingRate;
}

template< typename T > inline unsigned int Observation< T >::getNrSamplesPerPaddedSecond() {
	return nrSamplesPerPaddedSecond;
}

template< typename T > inline unsigned int Observation< T >::getNrChannels() {
	return nrChannels;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedChannels() {
	return nrPaddedChannels;
}

template< typename T > inline float Observation< T >::getMinFreq() {
	return minFreq;
}

template< typename T > inline float Observation< T >::getMaxFreq() {
	return maxFreq;
}

template< typename T > inline float Observation< T >::getChannelBandwidth() {
	return channelBandwidth;
}

template< typename T > inline T Observation< T >::getMinValue() {
	return minValue;
}

template< typename T > inline T Observation< T >::getMaxValue() {
	return maxValue;
}

template< typename T > inline double Observation< T >::getAverage(unsigned int channel) {
	return average[channel];
}

template< typename T > inline double Observation< T >::getVariance(unsigned int channel) {
	return variance[channel];
}

template< typename T > inline double Observation< T >::getStdDev(unsigned int channel) {
	return stdDev[channel];
}

template< typename T > inline unsigned int Observation< T >::getNrDMs() {
	return nrDMs;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedDMs() {
	return nrPaddedDMs;
}

template< typename T > inline float Observation< T >::getFirstDM() {
	return firstDM;
}

template< typename T > inline float Observation< T >::getDMStep() {
	return DMStep;
}

template< typename T > inline unsigned int Observation< T >::getNrPeriods() {
	return nrPeriods;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedPeriods() {
	return nrPaddedPeriods;
}

template< typename T > inline unsigned int Observation< T >::getNrBins() {
	return nrBins;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedBins() {
	return nrPaddedBins;
}

} // AstroData

#endif // OBSERVATION_HPP
<commit_msg>Better period parameters.<commit_after>/*
 * Copyright (C) 2012
 * Alessio Sclocco <a.sclocco@vu.nl>
 *
 * This program 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 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

#include <string>
#include <limits>
using std::string;
using std::numeric_limits;

#ifndef OBSERVATION_HPP
#define OBSERVATION_HPP

namespace AstroData {

template< typename T > class Observation {
public:
	Observation(string name, string dataType);
	~Observation();

	// General observation parameters
	inline void setNrSeconds(unsigned int seconds);
	inline void setNrStations(unsigned int nrStations);
	inline void setNrBeams(unsigned int beams);
	inline void setNrSamplesPerSecond(unsigned int samples);
	inline void setNrSamplesPerPaddedSecond(unsigned int samples);
	void setNrChannels(unsigned int channels);
	inline void setNrPaddedChannels(unsigned int channels);

	// Frequency parameters
	inline void setMinFreq(float freq);
	inline void setMaxFreq(float freq);
	inline void setChannelBandwidth(float bandwidth);

	// Statistical properties
	inline void setMinValue(T value);
	inline void setMaxValue(T value);
	inline void setAverage(unsigned int channel, double avg);
	inline void setVariance(unsigned int channel, double var);
	inline void setStdDev(unsigned int channel, double dev);

	// Dispersion measures
	inline void setNrDMs(unsigned int dms);
	inline void setNrPaddedDMs(unsigned int dms);
	inline void setFirstDM(float dm);
	inline void setDMStep(float step);

	// Periods
	inline void setNrPeriods(unsigned int periods);
	inline void setNrPaddedPeriods(unsigned int periods);
	inline void setNrBins(unsigned int bins);
	inline void setNrPaddedBins(unsigned int bins);
	inline void setFirstPeriod(unsigned int period);
	inline void setPeriodStep(unsigned int step);

	inline string getName();
	inline string getDataType();

	// General observation parameters
	inline unsigned int getNrSeconds();
	inline unsigned int getNrStations();
	inline unsigned int getNrBeams();
	inline unsigned int getNrSamplesPerSecond();
	inline float getSamplingRate();
	inline unsigned int getNrSamplesPerPaddedSecond();
	inline unsigned int getNrChannels();
	inline unsigned int getNrPaddedChannels();

	// Frequency parameters
	inline float getMinFreq();
	inline float getMaxFreq();
	inline float getChannelBandwidth();

	// Statistical properties
	inline T getMinValue();
	inline T getMaxValue();
	inline double getAverage(unsigned int channel);
	inline double getVariance(unsigned int channel);
	inline double getStdDev(unsigned int channel);

	// Dispersion measures
	inline unsigned int getNrDMs();
	inline unsigned int getNrPaddedDMs();
	inline float getFirstDM();
	inline float getDMStep();

	// Periods
	inline unsigned int getNrPeriods();
	inline unsigned int getNrPaddedPeriods();
	inline unsigned int getNrBins();
	inline unsigned int getNrPaddedBins();
	inline unsigned int getFirstPeriod();
	inline unsigned int getPeriodStep();

private:
	string name;
	string dataType;

	unsigned int nrSeconds;
	unsigned int nrStations;
	unsigned int nrBeams;
	unsigned int nrSamplesPerSecond;
	float samplingRate;
	unsigned int nrSamplesPerPaddedSecond;
	unsigned int nrChannels;
	unsigned int nrPaddedChannels;

	float minFreq;
	float maxFreq;
	float channelBandwidth;

	T minValue;
	T maxValue;
	double *average;
	double *variance;
	double *stdDev;

	unsigned int nrDMs;
	unsigned int nrPaddedDMs;
	float firstDM;
	float DMStep;

	unsigned int nrPeriods;
	unsigned int nrPaddedPeriods;
	unsigned int nrBins;
	unsigned int nrPaddedBins;
	unsigned int firstPeriod;
	unsigned int periodStep;
};

// Implementation

template< typename T > Observation< T >::Observation(string name, string dataType) : name(name), dataType(dataType), nrSeconds(0), nrStations(0), nrBeams(0), nrSamplesPerSecond(0), samplingRate(0.0f), nrSamplesPerPaddedSecond(0), nrChannels(0), nrPaddedChannels(0), minFreq(0.0f), maxFreq(0.0f), channelBandwidth(0.0f), minValue(numeric_limits< T >::max()), maxValue(numeric_limits< T >::min()), average(0.0), variance(0.0), stdDev(0.0), nrDMs(0), nrPaddedDMs(0), firstDM(0.0f), DMStep(0.0f), nrPeriods(0), nrPaddedPeriods(0), nrBins(0), nrPaddedBins(0), firstPeriod(0), periodStep(0) {}

template< typename T > Observation< T >::~Observation() {
	delete [] average;
	delete [] variance;
	delete [] stdDev;
}

template< typename T > inline void Observation< T >::setNrSeconds(unsigned int seconds) {
	nrSeconds = seconds;
}

template< typename T > inline void Observation< T >::setNrStations(unsigned int stations) {
	nrStations = stations;
}

template< typename T > inline void Observation< T >::setNrBeams(unsigned int beams) {
	nrBeams = beams;
}

template< typename T > inline void Observation< T >::setNrSamplesPerSecond(unsigned int samples) {
	nrSamplesPerSecond = samples;
	samplingRate = 1.0f / samples;
}

template< typename T > inline void Observation< T >::setNrSamplesPerPaddedSecond(unsigned int samples) {
	nrSamplesPerPaddedSecond = samples;
}

template< typename T > void Observation< T >::setNrChannels(unsigned int channels) {
	nrChannels = channels;

	average = new double [channels];
	variance = new double [channels];
	stdDev = new double [channels];
}

template< typename T > void Observation< T >::setNrPaddedChannels(unsigned int channels) {
	nrPaddedChannels = channels;
}

template< typename T > inline void Observation< T >::setMinFreq(float freq) {
	minFreq = freq;
}

template< typename T > inline void Observation< T >::setMaxFreq(float freq) {
	maxFreq = freq;
}

template< typename T > inline void Observation< T >::setChannelBandwidth(float bandwidth) {
	channelBandwidth = bandwidth;
}

template< typename T > inline void Observation< T >::setMinValue(T value) {
	minValue = value;
}

template< typename T > inline void Observation< T >::setMaxValue(T value) {
	maxValue = value;
}

template< typename T > inline void Observation< T >::setAverage(unsigned int channel, double avg) {
	average[channel] = avg;
}

template< typename T > inline void Observation< T >::setVariance(unsigned int channel, double var) {
	variance[channel] = var;
}

template< typename T > inline void Observation< T >::setStdDev(unsigned int channel, double dev) {
	stdDev[channel] = dev;
}

template< typename T > inline void Observation< T >::setNrDMs(unsigned int dms) {
	nrDMs = dms;
}

template< typename T > inline void Observation< T >::setNrPaddedDMs(unsigned int dms) {
	nrPaddedDMs = dms;
}

template< typename T > inline void Observation< T >::setFirstDM(float dm) {
	firstDM = dm;
}

template< typename T > inline void Observation< T >::setDMStep(float step) {
	DMStep = step;
}

template< typename T > inline void Observation< T >::setNrPeriods(unsigned int periods) {
	nrPeriods = periods;
}

template< typename T > inline void Observation< T >::setNrPaddedPeriods(unsigned int periods) {
	nrPaddedPeriods = periods;
}

template< typename T > inline void Observation< T >::setNrBins(unsigned int bins) {
	nrBins = bins;
}

template< typename T > inline void Observation< T >::setNrPaddedBins(unsigned int bins) {
	nrPaddedBins = bins;
}

template< typename T > inline void Observation< T >::setFirstPeriod(unsigned int period) {
	firstPeriod = period;
}

template< typename T > inline void Observation< T >::setPeriodStep(unsigned int step) {
	periodStep = step;
}

template< typename T > inline string Observation< T >::getName() {
	return name;
}

template< typename T > inline string Observation< T >::getDataType() {
	return dataType;
}

template< typename T > inline unsigned int Observation< T >::getNrSeconds() {
	return nrSeconds;
}

template< typename T > inline unsigned int Observation< T >::getNrStations() {
	return nrStations;
}

template< typename T > inline unsigned int Observation< T >::getNrBeams() {
	return nrBeams;
}

template< typename T > inline unsigned int Observation< T >::getNrSamplesPerSecond() {
	return nrSamplesPerSecond;
}

template< typename T > inline float Observation< T >::getSamplingRate() {
	return samplingRate;
}

template< typename T > inline unsigned int Observation< T >::getNrSamplesPerPaddedSecond() {
	return nrSamplesPerPaddedSecond;
}

template< typename T > inline unsigned int Observation< T >::getNrChannels() {
	return nrChannels;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedChannels() {
	return nrPaddedChannels;
}

template< typename T > inline float Observation< T >::getMinFreq() {
	return minFreq;
}

template< typename T > inline float Observation< T >::getMaxFreq() {
	return maxFreq;
}

template< typename T > inline float Observation< T >::getChannelBandwidth() {
	return channelBandwidth;
}

template< typename T > inline T Observation< T >::getMinValue() {
	return minValue;
}

template< typename T > inline T Observation< T >::getMaxValue() {
	return maxValue;
}

template< typename T > inline double Observation< T >::getAverage(unsigned int channel) {
	return average[channel];
}

template< typename T > inline double Observation< T >::getVariance(unsigned int channel) {
	return variance[channel];
}

template< typename T > inline double Observation< T >::getStdDev(unsigned int channel) {
	return stdDev[channel];
}

template< typename T > inline unsigned int Observation< T >::getNrDMs() {
	return nrDMs;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedDMs() {
	return nrPaddedDMs;
}

template< typename T > inline float Observation< T >::getFirstDM() {
	return firstDM;
}

template< typename T > inline float Observation< T >::getDMStep() {
	return DMStep;
}

template< typename T > inline unsigned int Observation< T >::getNrPeriods() {
	return nrPeriods;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedPeriods() {
	return nrPaddedPeriods;
}

template< typename T > inline unsigned int Observation< T >::getNrBins() {
	return nrBins;
}

template< typename T > inline unsigned int Observation< T >::getNrPaddedBins() {
	return nrPaddedBins;
}

template< typename T > inline unsigned int Observation< T >::getFirstPeriod() {
	return firstPeriod;
}

template< typename T > inline unsigned int Observation< T >::getPeriodStep() {
	return periodStep;
}

} // AstroData

#endif // OBSERVATION_HPP
<|endoftext|>


<commit_before>// Copyright (c) 2009 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/extensions/extension_apitest.h"

IN_PROC_BROWSER_TEST_F(ExtensionApiTest, Toolstrip) {
  ASSERT_TRUE(RunExtensionTest("toolstrip")) << message_;
}
<commit_msg>disable toolstrip test for chromeos/linux_view<commit_after>// Copyright (c) 2009 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "chrome/browser/extensions/extension_apitest.h"

#if !defined(OS_CHROMEOS)
IN_PROC_BROWSER_TEST_F(ExtensionApiTest, Toolstrip) {
  ASSERT_TRUE(RunExtensionTest("toolstrip")) << message_;
}
#endif
<|endoftext|>


<commit_before>#ifndef ATLAS_INCLUDE_ATLAS_SCENE_HPP
#define ATLAS_INCLUDE_ATLAS_SCENE_HPP

#pragma once

#include "Atlas.hpp"
#include "Matrix.hpp"

namespace atlas
{
    class Scene
    {
    public:
        Scene();
        ~Scene();

        virtual void mousePressEvent(int button, int action, int modifiers);
        virtual void mouseMoveEvent(double xPos, double yPos);
        virtual void keyPressEvent(int key, int scancode, int action,
            int mods);
        virtual void screenResizeEvent(int width, int height);
        virtual void updateScene(double time);
        virtual void renderScene();
        virtual bool sceneEnded();

    protected:
        Matrix4 mProjection;
        Matrix4 mView;
    };
}

#endif<commit_msg>[brief] Adds the Time struct for animation scenes.<commit_after>#ifndef ATLAS_INCLUDE_ATLAS_SCENE_HPP
#define ATLAS_INCLUDE_ATLAS_SCENE_HPP

#pragma once

#include "Atlas.hpp"
#include "Matrix.hpp"
#include "Time.hpp"

namespace atlas
{
    class Scene
    {
    public:
        Scene();
        ~Scene();

        virtual void mousePressEvent(int button, int action, int modifiers);
        virtual void mouseMoveEvent(double xPos, double yPos);
        virtual void keyPressEvent(int key, int scancode, int action,
            int mods);
        virtual void screenResizeEvent(int width, int height);
        virtual void updateScene(double time);
        virtual void renderScene();
        virtual bool sceneEnded();

    protected:
        Matrix4 mProjection;
        Matrix4 mView;
        Time mTime;
    };
}

#endif<|endoftext|>


<commit_before>#pragma once
/**
	@file
	@brief unit test class

	Copyright (C) 2008 Cybozu Labs, Inc., all rights reserved.
*/

#include <stdio.h>
#include <string.h>
#include <string>
#include <list>
#include <iostream>
#include <utility>
#if defined(_MSC_VER) && (MSC_VER <= 1500)
	#include <cybozu/inttype.hpp>
#else
	#include <stdint.h>
#endif

namespace cybozu { namespace test {

class AutoRun {
	typedef void (*Func)();
	typedef std::list<std::pair<const char*, Func> > UnitTestList;
public:
	AutoRun()
		: init_(0)
		, term_(0)
		, okCount_(0)
		, ngCount_(0)
		, exceptionCount_(0)
	{
	}
	void setup(Func init, Func term)
	{
		init_ = init;
		term_ = term;
	}
	void append(const char *name, Func func)
	{
		list_.push_back(std::make_pair(name, func));
	}
	void set(bool isOK)
	{
		if (isOK) {
			okCount_++;
		} else {
			ngCount_++;
		}
	}
	std::string getBaseName(const std::string& name) const
	{
#ifdef _WIN32
		const char sep = '\\';
#else
		const char sep = '/';
#endif
		size_t pos = name.find_last_of(sep);
		std::string ret = name.substr(pos + 1);
		pos = ret.find('.');
		return ret.substr(0, pos);
	}
	int run(int, char *argv[])
	{
		std::string msg;
		try {
			if (init_) init_();
			for (UnitTestList::const_iterator i = list_.begin(), ie = list_.end(); i != ie; ++i) {
				std::cout << "ctest:module=" << i->first << std::endl;
				try {
					(i->second)();
				} catch (std::exception& e) {
					exceptionCount_++;
					std::cout << "ctest:  " << i->first << " is stopped by exception " << e.what() << std::endl;
				} catch (...) {
					exceptionCount_++;
					std::cout << "ctest:  " << i->first << " is stopped by unknown exception" << std::endl;
				}
			}
			if (term_) term_();
		} catch (std::exception& e) {
			msg = std::string("ctest:err:") + e.what();
		} catch (...) {
			msg = "ctest:err: catch unknown exception";
		}
		fflush(stdout);
		if (msg.empty()) {
			std::cout << "ctest:name=" << getBaseName(*argv)
					  << ", module=" << list_.size()
					  << ", total=" << (okCount_ + ngCount_ + exceptionCount_)
					  << ", ok=" << okCount_
					  << ", ng=" << ngCount_
					  << ", exception=" << exceptionCount_ << std::endl;
			return 0;
		} else {
			std::cout << msg << std::endl;
			return 1;
		}
	}
	static inline AutoRun& getInstance()
	{
		static AutoRun instance;
		return instance;
	}
private:
	Func init_;
	Func term_;
	int okCount_;
	int ngCount_;
	int exceptionCount_;
	UnitTestList list_;
};

static AutoRun& autoRun = AutoRun::getInstance();

inline void test(bool ret, const std::string& msg, const std::string& param, const char *file, int line)
{
	autoRun.set(ret);
	if (!ret) {
		std::cout << file << "(" << line << "):" << "ctest:" << msg << "(" << param << ");" << std::endl;
	}
}

template<typename T, typename U>
bool isEqual(const T& lhs, const U& rhs)
{
	return lhs == rhs;
}

inline bool isEqual(const char *lhs, const char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
inline bool isEqual(char *lhs, const char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
inline bool isEqual(const char *lhs, char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
inline bool isEqual(char *lhs, char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
// avoid to compare float directly
inline bool isEqual(float lhs, float rhs)
{
	union fi {
		float f;
		uint32_t i;
	} lfi, rfi;
	lfi.f = lhs;
	rfi.f = rhs;
	return lfi.i == rfi.i;
}
// avoid to compare double directly
inline bool isEqual(double lhs, double rhs)
{
	union di {
		double d;
		uint64_t i;
	} ldi, rdi;
	ldi.d = lhs;
	rdi.d = rhs;
	return ldi.i == rdi.i;
}

} } // cybozu::test

#ifndef CYBOZU_TEST_DISABLE_AUTO_RUN
int main(int argc, char *argv[])
{
	return cybozu::test::autoRun.run(argc, argv);
}
#endif

/**
	alert if !x
	@param x [in]
*/
#define CYBOZU_TEST_ASSERT(x) cybozu::test::test(!!(x), "CYBOZU_TEST_ASSERT", #x, __FILE__, __LINE__)

/**
	alert if x != y
	@param x [in]
	@param y [in]
*/
#define CYBOZU_TEST_EQUAL(x, y) { \
	bool eq = cybozu::test::isEqual(x, y); \
	cybozu::test::test(eq, "CYBOZU_TEST_EQUAL", #x ", " #y, __FILE__, __LINE__); \
	if (!eq) { \
		std::cout << "ctest:  lhs=" << (x) << std::endl; \
		std::cout << "ctest:  rhs=" << (y) << std::endl; \
	} \
}
/**
	alert if fabs(x, y) >= eps
	@param x [in]
	@param y [in]
*/
#define CYBOZU_TEST_NEAR(x, y, eps) { \
	bool isNear = fabs((x) - (y)) < eps; \
	cybozu::test::test(isNear, "CYBOZU_TEST_NEAR", #x ", " #y, __FILE__, __LINE__); \
	if (!isNear) { \
		std::cout << "ctest:  lhs=" << (x) << std::endl; \
		std::cout << "ctest:  rhs=" << (y) << std::endl; \
	} \
}

#define CYBOZU_TEST_EQUAL_POINTER(x, y) { \
	bool eq = x == y; \
	cybozu::test::test(eq, "CYBOZU_TEST_EQUAL_POINTER", #x ", " #y, __FILE__, __LINE__); \
	if (!eq) { \
		std::cout << "ctest:  lhs=" << static_cast<const void*>(x) << std::endl; \
		std::cout << "ctest:  rhs=" << static_cast<const void*>(y) << std::endl; \
	} \
}

/**
	always alert
	@param msg [in]
*/
#define CYBOZU_TEST_FAIL(msg) cybozu::test::test(false, "CYBOZU_TEST_FAIL", msg, __FILE__, __LINE__)

/**
	verify message in exception
*/
#define CYBOZU_TEST_EXCEPTION_MESSAGE(statement, Exception, msg) \
{ \
	int ret = 0; \
	std::string errMsg; \
	try { \
		statement; \
		ret = 1; \
	} catch (const Exception& e) { \
		errMsg = e.what(); \
		if (errMsg.find(msg) == std::string::npos) { \
			ret = 2; \
		} \
	} catch (...) { \
		ret = 3; \
	} \
	if (ret) { \
		cybozu::test::test(false, "CYBOZU_TEST_EXCEPTION_MESSAGE", #statement ", " #Exception ", " #msg, __FILE__, __LINE__); \
		if (ret == 1) { \
			std::cout << "ctest:  no exception" << std::endl; \
		} else if (ret == 2) { \
			std::cout << "ctest:  bad exception msg:" << errMsg << std::endl; \
		} else { \
			std::cout << "ctest:  unexpected exception" << std::endl; \
		} \
	} else { \
		cybozu::test::autoRun.set(true); \
	} \
}

#define CYBOZU_TEST_EXCEPTION(statement, Exception) \
{ \
	int ret = 0; \
	try { \
		statement; \
		ret = 1; \
	} catch (const Exception&) { \
	} catch (...) { \
		ret = 2; \
	} \
	if (ret) { \
		cybozu::test::test(false, "CYBOZU_TEST_EXCEPTION", #statement ", " #Exception, __FILE__, __LINE__); \
		if (ret == 1) { \
			std::cout << "ctest:  no exception" << std::endl; \
		} else { \
			std::cout << "ctest:  unexpected exception" << std::endl; \
		} \
	} else { \
		cybozu::test::autoRun.set(true); \
	} \
}

/**
	verify statement does not throw
*/
#define CYBOZU_TEST_NO_EXCEPTION(statement) \
try { \
	statement; \
	cybozu::test::autoRun.set(true); \
} catch (...) { \
	cybozu::test::test(false, "CYBOZU_TEST_NO_EXCEPTION", #statement, __FILE__, __LINE__); \
}

/**
	append auto unit test
	@param name [in] module name
*/
#define CYBOZU_TEST_AUTO(name) \
void cybozu_test_ ## name(); \
struct cybozu_test_local_ ## name { \
	cybozu_test_local_ ## name() \
	{ \
		cybozu::test::autoRun.append(#name, cybozu_test_ ## name); \
	} \
} cybozu_test_local_instance_ ## name; \
void cybozu_test_ ## name()

/**
	append auto unit test with fixture
	@param name [in] module name
*/
#define CYBOZU_TEST_AUTO_WITH_FIXTURE(name, Fixture) \
void cybozu_test_ ## name(); \
void cybozu_test_real_ ## name() \
{ \
	Fixture f; \
	cybozu_test_ ## name(); \
} \
struct cybozu_test_local_ ## name { \
	cybozu_test_local_ ## name() \
	{ \
		cybozu::test::autoRun.append(#name, cybozu_test_real_ ## name); \
	} \
} cybozu_test_local_instance_ ## name; \
void cybozu_test_ ## name()

/**
	setup fixture
	@param Fixture [in] class name of fixture
	@note cstr of Fixture is called before test and dstr of Fixture is called after test
*/
#define CYBOZU_TEST_SETUP_FIXTURE(Fixture) \
Fixture *cybozu_test_local_fixture; \
void cybozu_test_local_init() \
{ \
	cybozu_test_local_fixture = new Fixture(); \
} \
void cybozu_test_local_term() \
{ \
	delete cybozu_test_local_fixture; \
} \
struct cybozu_test_local_fixture_setup_ { \
	cybozu_test_local_fixture_setup_() \
	{ \
		cybozu::test::autoRun.setup(cybozu_test_local_init, cybozu_test_local_term); \
	} \
} cybozu_test_local_fixture_setup_instance_;
<commit_msg>avoid influence of std::hex<commit_after>#pragma once
/**
	@file
	@brief unit test class

	Copyright (C) 2008 Cybozu Labs, Inc., all rights reserved.
*/

#include <stdio.h>
#include <string.h>
#include <string>
#include <list>
#include <iostream>
#include <utility>
#if defined(_MSC_VER) && (MSC_VER <= 1500)
	#include <cybozu/inttype.hpp>
#else
	#include <stdint.h>
#endif

namespace cybozu { namespace test {

class AutoRun {
	typedef void (*Func)();
	typedef std::list<std::pair<const char*, Func> > UnitTestList;
public:
	AutoRun()
		: init_(0)
		, term_(0)
		, okCount_(0)
		, ngCount_(0)
		, exceptionCount_(0)
	{
	}
	void setup(Func init, Func term)
	{
		init_ = init;
		term_ = term;
	}
	void append(const char *name, Func func)
	{
		list_.push_back(std::make_pair(name, func));
	}
	void set(bool isOK)
	{
		if (isOK) {
			okCount_++;
		} else {
			ngCount_++;
		}
	}
	std::string getBaseName(const std::string& name) const
	{
#ifdef _WIN32
		const char sep = '\\';
#else
		const char sep = '/';
#endif
		size_t pos = name.find_last_of(sep);
		std::string ret = name.substr(pos + 1);
		pos = ret.find('.');
		return ret.substr(0, pos);
	}
	int run(int, char *argv[])
	{
		std::string msg;
		try {
			if (init_) init_();
			for (UnitTestList::const_iterator i = list_.begin(), ie = list_.end(); i != ie; ++i) {
				std::cout << "ctest:module=" << i->first << std::endl;
				try {
					(i->second)();
				} catch (std::exception& e) {
					exceptionCount_++;
					std::cout << "ctest:  " << i->first << " is stopped by exception " << e.what() << std::endl;
				} catch (...) {
					exceptionCount_++;
					std::cout << "ctest:  " << i->first << " is stopped by unknown exception" << std::endl;
				}
			}
			if (term_) term_();
		} catch (std::exception& e) {
			msg = std::string("ctest:err:") + e.what();
		} catch (...) {
			msg = "ctest:err: catch unknown exception";
		}
		fflush(stdout);
		if (msg.empty()) {
			std::cout << "ctest:name=" << getBaseName(*argv)
					  << ", module=" << list_.size()
					  << ", total=" << (okCount_ + ngCount_ + exceptionCount_)
					  << ", ok=" << okCount_
					  << ", ng=" << ngCount_
					  << ", exception=" << exceptionCount_ << std::endl;
			return 0;
		} else {
			std::cout << msg << std::endl;
			return 1;
		}
	}
	static inline AutoRun& getInstance()
	{
		static AutoRun instance;
		return instance;
	}
private:
	Func init_;
	Func term_;
	int okCount_;
	int ngCount_;
	int exceptionCount_;
	UnitTestList list_;
};

static AutoRun& autoRun = AutoRun::getInstance();

inline void test(bool ret, const std::string& msg, const std::string& param, const char *file, int line)
{
	autoRun.set(ret);
	if (!ret) {
		printf("%s(%d):ctest:%s(%s);\n", file, line, msg.c_str(), param.c_str());
	}
}

template<typename T, typename U>
bool isEqual(const T& lhs, const U& rhs)
{
	return lhs == rhs;
}

inline bool isEqual(const char *lhs, const char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
inline bool isEqual(char *lhs, const char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
inline bool isEqual(const char *lhs, char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
inline bool isEqual(char *lhs, char *rhs)
{
	return strcmp(lhs, rhs) == 0;
}
// avoid to compare float directly
inline bool isEqual(float lhs, float rhs)
{
	union fi {
		float f;
		uint32_t i;
	} lfi, rfi;
	lfi.f = lhs;
	rfi.f = rhs;
	return lfi.i == rfi.i;
}
// avoid to compare double directly
inline bool isEqual(double lhs, double rhs)
{
	union di {
		double d;
		uint64_t i;
	} ldi, rdi;
	ldi.d = lhs;
	rdi.d = rhs;
	return ldi.i == rdi.i;
}

} } // cybozu::test

#ifndef CYBOZU_TEST_DISABLE_AUTO_RUN
int main(int argc, char *argv[])
{
	return cybozu::test::autoRun.run(argc, argv);
}
#endif

/**
	alert if !x
	@param x [in]
*/
#define CYBOZU_TEST_ASSERT(x) cybozu::test::test(!!(x), "CYBOZU_TEST_ASSERT", #x, __FILE__, __LINE__)

/**
	alert if x != y
	@param x [in]
	@param y [in]
*/
#define CYBOZU_TEST_EQUAL(x, y) { \
	bool eq = cybozu::test::isEqual(x, y); \
	cybozu::test::test(eq, "CYBOZU_TEST_EQUAL", #x ", " #y, __FILE__, __LINE__); \
	if (!eq) { \
		std::cout << "ctest:  lhs=" << (x) << std::endl; \
		std::cout << "ctest:  rhs=" << (y) << std::endl; \
	} \
}
/**
	alert if fabs(x, y) >= eps
	@param x [in]
	@param y [in]
*/
#define CYBOZU_TEST_NEAR(x, y, eps) { \
	bool isNear = fabs((x) - (y)) < eps; \
	cybozu::test::test(isNear, "CYBOZU_TEST_NEAR", #x ", " #y, __FILE__, __LINE__); \
	if (!isNear) { \
		std::cout << "ctest:  lhs=" << (x) << std::endl; \
		std::cout << "ctest:  rhs=" << (y) << std::endl; \
	} \
}

#define CYBOZU_TEST_EQUAL_POINTER(x, y) { \
	bool eq = x == y; \
	cybozu::test::test(eq, "CYBOZU_TEST_EQUAL_POINTER", #x ", " #y, __FILE__, __LINE__); \
	if (!eq) { \
		std::cout << "ctest:  lhs=" << static_cast<const void*>(x) << std::endl; \
		std::cout << "ctest:  rhs=" << static_cast<const void*>(y) << std::endl; \
	} \
}

/**
	always alert
	@param msg [in]
*/
#define CYBOZU_TEST_FAIL(msg) cybozu::test::test(false, "CYBOZU_TEST_FAIL", msg, __FILE__, __LINE__)

/**
	verify message in exception
*/
#define CYBOZU_TEST_EXCEPTION_MESSAGE(statement, Exception, msg) \
{ \
	int ret = 0; \
	std::string errMsg; \
	try { \
		statement; \
		ret = 1; \
	} catch (const Exception& e) { \
		errMsg = e.what(); \
		if (errMsg.find(msg) == std::string::npos) { \
			ret = 2; \
		} \
	} catch (...) { \
		ret = 3; \
	} \
	if (ret) { \
		cybozu::test::test(false, "CYBOZU_TEST_EXCEPTION_MESSAGE", #statement ", " #Exception ", " #msg, __FILE__, __LINE__); \
		if (ret == 1) { \
			std::cout << "ctest:  no exception" << std::endl; \
		} else if (ret == 2) { \
			std::cout << "ctest:  bad exception msg:" << errMsg << std::endl; \
		} else { \
			std::cout << "ctest:  unexpected exception" << std::endl; \
		} \
	} else { \
		cybozu::test::autoRun.set(true); \
	} \
}

#define CYBOZU_TEST_EXCEPTION(statement, Exception) \
{ \
	int ret = 0; \
	try { \
		statement; \
		ret = 1; \
	} catch (const Exception&) { \
	} catch (...) { \
		ret = 2; \
	} \
	if (ret) { \
		cybozu::test::test(false, "CYBOZU_TEST_EXCEPTION", #statement ", " #Exception, __FILE__, __LINE__); \
		if (ret == 1) { \
			std::cout << "ctest:  no exception" << std::endl; \
		} else { \
			std::cout << "ctest:  unexpected exception" << std::endl; \
		} \
	} else { \
		cybozu::test::autoRun.set(true); \
	} \
}

/**
	verify statement does not throw
*/
#define CYBOZU_TEST_NO_EXCEPTION(statement) \
try { \
	statement; \
	cybozu::test::autoRun.set(true); \
} catch (...) { \
	cybozu::test::test(false, "CYBOZU_TEST_NO_EXCEPTION", #statement, __FILE__, __LINE__); \
}

/**
	append auto unit test
	@param name [in] module name
*/
#define CYBOZU_TEST_AUTO(name) \
void cybozu_test_ ## name(); \
struct cybozu_test_local_ ## name { \
	cybozu_test_local_ ## name() \
	{ \
		cybozu::test::autoRun.append(#name, cybozu_test_ ## name); \
	} \
} cybozu_test_local_instance_ ## name; \
void cybozu_test_ ## name()

/**
	append auto unit test with fixture
	@param name [in] module name
*/
#define CYBOZU_TEST_AUTO_WITH_FIXTURE(name, Fixture) \
void cybozu_test_ ## name(); \
void cybozu_test_real_ ## name() \
{ \
	Fixture f; \
	cybozu_test_ ## name(); \
} \
struct cybozu_test_local_ ## name { \
	cybozu_test_local_ ## name() \
	{ \
		cybozu::test::autoRun.append(#name, cybozu_test_real_ ## name); \
	} \
} cybozu_test_local_instance_ ## name; \
void cybozu_test_ ## name()

/**
	setup fixture
	@param Fixture [in] class name of fixture
	@note cstr of Fixture is called before test and dstr of Fixture is called after test
*/
#define CYBOZU_TEST_SETUP_FIXTURE(Fixture) \
Fixture *cybozu_test_local_fixture; \
void cybozu_test_local_init() \
{ \
	cybozu_test_local_fixture = new Fixture(); \
} \
void cybozu_test_local_term() \
{ \
	delete cybozu_test_local_fixture; \
} \
struct cybozu_test_local_fixture_setup_ { \
	cybozu_test_local_fixture_setup_() \
	{ \
		cybozu::test::autoRun.setup(cybozu_test_local_init, cybozu_test_local_term); \
	} \
} cybozu_test_local_fixture_setup_instance_;
<|endoftext|>


<commit_before>#ifndef ECL_COMMAND_HPP
#define ECL_COMMAND_HPP

#include <cstddef>
#include <cstdint>

#include <cstring>

#include "sized_data.h"

#ifndef RECEIVER_CAPACITY
#define RECEIVER_CAPACITY 32
#endif

namespace ecl
{

namespace detail
{

template<typename cmd>
class i_receiver
{
protected:
    virtual ~i_receiver() {}

public:
    virtual void receive(cmd&)                                              = 0;
};

template<typename cmd>
class cmd_core
{
protected:
    void reg(detail::i_receiver<cmd>* const i)
    {
        for(auto &itf: s_array)
        {
            if(nullptr == itf)
            {
                itf = i;
                return;
            }
        }
    }

    void execute(cmd& c)                                                   const
    {
        for(auto itf: s_array)
        {
            if(nullptr != itf)
            {
                itf->receive(c);
            }
        }
    }

private:
    static detail::i_receiver<cmd>* s_array[RECEIVER_CAPACITY];
};

} // namespace detail

class i_command
{
public:
    virtual bool init(const uint8_t               argc,
                      const uint8_t* const* const argv)                     = 0;

    virtual bool dispatch()                                                 = 0;
};

template<typename NAME, typename cmd>
class command : public virtual detail::cmd_core<cmd>,
                public i_command
{
public:
    explicit command(const sized_data* const buf) :
        m_buf(buf),
        m_size(0)
    {}

    virtual bool dispatch()                                             override
    {
        this->execute(*static_cast<cmd*>(this));

        return true;
    }

    virtual bool init(const uint8_t               argc,
                      const uint8_t* const* const argv)                 override
    {
        (void)(argc);
        (void)(argv);
        return true;
    }

    size_t append(const sized_data& d)
    {
        if(nullptr == m_buf)
        {
            return 0;
        }

        if( (nullptr == m_buf->ptr) || (nullptr == d.ptr) || (0 == d.size) )
        {
            return 0;
        }

        size_t remain = m_buf->size - m_size;
        size_t size_safe = (d.size < remain) ? d.size : remain;
        for(size_t i = 0; i < size_safe; ++i)
        {
            m_buf->ptr[m_size + i] = d.ptr[i];
            ++m_size;
        }

        return size_safe;
    }

    size_t append(const char* const str)
    {
        sized_data d = {
            (uint8_t* const)str,
            strlen(str)
        };

        return append(d);
    }

    constexpr static const char* const name()
    {
        return NAME::name();
    }

protected:
    uint8_t                 m_argc;
    const uint8_t**         m_argv;

    const sized_data* const m_buf;
    size_t                  m_size;
};

template<typename cmd>
class receiver : public virtual detail::cmd_core<cmd>,
                 public detail::i_receiver<cmd>
{
protected:
    receiver()
    {
        this->detail::cmd_core<cmd>::reg(this);
    }

    virtual ~receiver() {}
};

} // namespace ecl

#endif // ECL_COMMAND_HPP
<commit_msg>Command changed. Now std::array with singleton used instead of plain C-array. Now no need to store array in separate cpp-file.<commit_after>#ifndef ECL_COMMAND_HPP
#define ECL_COMMAND_HPP

#include <cstddef>
#include <cstdint>
#include <cstring>

#include <array>

#include "sized_data.h"
#include "singleton.hpp"

#ifndef RECEIVER_CAPACITY
#define RECEIVER_CAPACITY 32
#endif

namespace ecl
{

namespace detail
{

template<typename cmd>
class i_receiver
{
protected:
    virtual ~i_receiver() {}

public:
    virtual void receive(cmd&)                                              = 0;
};

template<typename cmd>
class cmd_core
{
protected:
    void reg(detail::i_receiver<cmd>* const i)
    {
        for(auto &itf: array_singleton::instance())
        {
            if(nullptr == itf)
            {
                itf = i;
                return;
            }
        }
    }

    void execute(cmd& c)                                                   const
    {
        for(auto itf: array_singleton::instance())
        {
            if(nullptr != itf)
            {
                itf->receive(c);
            }
        }
    }

private:
    typedef ecl::singleton<
                std::array<detail::i_receiver<cmd>*, RECEIVER_CAPACITY>
                > array_singleton;
};

} // namespace detail

class i_command
{
public:
    virtual bool init(const uint8_t               argc,
                      const uint8_t* const* const argv)                     = 0;

    virtual bool dispatch()                                                 = 0;
};

template<typename NAME, typename cmd>
class command : public virtual detail::cmd_core<cmd>,
                public i_command
{
public:
    explicit command(const sized_data* const buf) :
        m_buf(buf),
        m_size(0)
    {}

    virtual bool dispatch()                                             override
    {
        this->execute(*static_cast<cmd*>(this));

        return true;
    }

    virtual bool init(const uint8_t               argc,
                      const uint8_t* const* const argv)                 override
    {
        (void)(argc);
        (void)(argv);
        return true;
    }

    size_t append(const sized_data& d)
    {
        if(nullptr == m_buf)
        {
            return 0;
        }

        if( (nullptr == m_buf->ptr) || (nullptr == d.ptr) || (0 == d.size) )
        {
            return 0;
        }

        size_t remain = m_buf->size - m_size;
        size_t size_safe = (d.size < remain) ? d.size : remain;
        for(size_t i = 0; i < size_safe; ++i)
        {
            m_buf->ptr[m_size + i] = d.ptr[i];
            ++m_size;
        }

        return size_safe;
    }

    size_t append(const char* const str)
    {
        sized_data d = {
            (uint8_t* const)str,
            strlen(str)
        };

        return append(d);
    }

    constexpr static const char* const name()
    {
        return NAME::name();
    }

protected:
    uint8_t                 m_argc;
    const uint8_t**         m_argv;

    const sized_data* const m_buf;
    size_t                  m_size;
};

template<typename cmd>
class receiver : public virtual detail::cmd_core<cmd>,
                 public detail::i_receiver<cmd>
{
protected:
    receiver()
    {
        this->detail::cmd_core<cmd>::reg(this);
    }

    virtual ~receiver() {}
};

} // namespace ecl

#endif // ECL_COMMAND_HPP
<|endoftext|>


<commit_before>// Copyright 2018 Global Phasing Ltd.
//
// Read small molecule CIF file into SmallStructure (from small.hpp).

#ifndef GEMMI_SMCIF_HPP_
#define GEMMI_SMCIF_HPP_

#include "small.hpp"     // SmallStructure
#include "cifdoc.hpp"
#include "numb.hpp"      // for as_number
#include "symmetry.hpp"  // SpaceGroup

namespace gemmi {

inline
SmallStructure make_small_structure_from_block(const cif::Block& block_) {
  using cif::as_number;
  using cif::as_string;
  cif::Block& block = const_cast<cif::Block&>(block_);
  SmallStructure st;
  st.name = block.name;

  // unit cell and symmetry
  cif::Table cell = block.find("_cell_",
                               {"length_a", "length_b", "length_c",
                                "angle_alpha", "angle_beta", "angle_gamma"});
  if (cell.ok()) {
    auto c = cell.one();
    if (!cif::is_null(c[0]) && !cif::is_null(c[1]) && !cif::is_null(c[2]))
      st.cell.set(as_number(c[0]), as_number(c[1]), as_number(c[2]),
                  as_number(c[3]), as_number(c[4]), as_number(c[5]));
  }
  for (const char* tag : {"_space_group_name_H-M_alt",
                          "_symmetry_space_group_name_H-M"})
    if (const std::string* val = block.find_value(tag)) {
      st.spacegroup_hm = as_string(*val);
      break;
    }

  enum { kLabel, kSymbol, kX, kY, kZ, kUiso, kOcc, kDisorderGroup };
  cif::Table atom_table = block.find("_atom_site_",
                                     {"label",
                                      "?type_symbol",
                                      "?fract_x",
                                      "?fract_y",
                                      "?fract_z",
                                      "?U_iso_or_equiv",
                                      "?occupancy",
                                      "?disorder_group"});
  for (auto row : atom_table) {
    SmallStructure::Site site;
    site.label = as_string(row[kLabel]);
    if (row.has(kSymbol))
      site.type_symbol = as_string(row[kSymbol]);
    else
      site.type_symbol = site.label;
    if (row.has(kX))
      site.fract.x = as_number(row[kX]);
    if (row.has(kY))
      site.fract.y = as_number(row[kY]);
    if (row.has(kZ))
      site.fract.z = as_number(row[kZ]);
    if (row.has(kUiso))
      site.u_iso = as_number(row[kUiso], 0.0);
    if (row.has(kOcc))
      site.occ = as_number(row[kOcc], 1.0);
    if (row.has2(kDisorderGroup))
      // ignore non-integer _atom_site_disorder_group
      site.disorder_group = string_to_int(row[kDisorderGroup], false);
    split_element_and_charge(site.type_symbol, &site);
    st.sites.push_back(site);
  }

  std::vector<SmallStructure::Site>::iterator aniso_site = st.sites.begin();
  for (auto row : block.find("_atom_site_aniso_",
                             {"label", "U_11", "U_22", "U_33",
                              "U_12", "U_13", "U_23"})) {
    std::string aniso_label = row.str(0);
    if (aniso_site == st.sites.end() || aniso_site->label != aniso_label) {
      aniso_site = std::find_if(st.sites.begin(), st.sites.end(),
              [&](SmallStructure::Site& x) { return x.label == aniso_label; });
      if (aniso_site == st.sites.end())
        continue;
    }
    aniso_site->u11 = as_number(row[1], 0.0);
    aniso_site->u22 = as_number(row[2], 0.0);
    aniso_site->u33 = as_number(row[3], 0.0);
    aniso_site->u12 = as_number(row[4], 0.0);
    aniso_site->u13 = as_number(row[5], 0.0);
    aniso_site->u23 = as_number(row[6], 0.0);
    ++aniso_site;
  }

  for (auto row : block.find("_atom_type_",
                             {"symbol",
                              "scat_dispersion_real",
                              "scat_dispersion_imag"})) {
    SmallStructure::AtomType atom_type;
    atom_type.symbol = row.str(0);
    atom_type.dispersion_real = cif::as_number(row[1]);
    atom_type.dispersion_imag = cif::as_number(row[2]);
    split_element_and_charge(atom_type.symbol, &atom_type);
    st.atom_types.push_back(atom_type);
  }
  if (cif::Column w_col = block.find_values("_diffrn_radiation_wavelength"))
    st.wavelength = cif::as_number(w_col.at(0));

  const SpaceGroup* sg = find_spacegroup_by_name(st.spacegroup_hm,
                                                 st.cell.alpha, st.cell.gamma);
  st.cell.set_cell_images_from_spacegroup(sg);
  return st;
}

} // namespace gemmi
#endif
<commit_msg>smcif.hpp: if U is not given read _atom_site_B_iso_or_equiv<commit_after>// Copyright 2018 Global Phasing Ltd.
//
// Read small molecule CIF file into SmallStructure (from small.hpp).

#ifndef GEMMI_SMCIF_HPP_
#define GEMMI_SMCIF_HPP_

#include "small.hpp"     // SmallStructure
#include "cifdoc.hpp"
#include "numb.hpp"      // for as_number
#include "symmetry.hpp"  // SpaceGroup

namespace gemmi {

inline
SmallStructure make_small_structure_from_block(const cif::Block& block_) {
  using cif::as_number;
  using cif::as_string;
  cif::Block& block = const_cast<cif::Block&>(block_);
  SmallStructure st;
  st.name = block.name;

  // unit cell and symmetry
  cif::Table cell = block.find("_cell_",
                               {"length_a", "length_b", "length_c",
                                "angle_alpha", "angle_beta", "angle_gamma"});
  if (cell.ok()) {
    auto c = cell.one();
    if (!cif::is_null(c[0]) && !cif::is_null(c[1]) && !cif::is_null(c[2]))
      st.cell.set(as_number(c[0]), as_number(c[1]), as_number(c[2]),
                  as_number(c[3]), as_number(c[4]), as_number(c[5]));
  }
  for (const char* tag : {"_space_group_name_H-M_alt",
                          "_symmetry_space_group_name_H-M"})
    if (const std::string* val = block.find_value(tag)) {
      st.spacegroup_hm = as_string(*val);
      break;
    }

  enum { kLabel, kSymbol, kX, kY, kZ, kUiso, kBiso, kOcc, kDisorderGroup };
  cif::Table atom_table = block.find("_atom_site_",
                                     {"label",
                                      "?type_symbol",
                                      "?fract_x",
                                      "?fract_y",
                                      "?fract_z",
                                      "?U_iso_or_equiv",
                                      "?B_iso_or_equiv",
                                      "?occupancy",
                                      "?disorder_group"});
  for (auto row : atom_table) {
    SmallStructure::Site site;
    site.label = as_string(row[kLabel]);
    if (row.has(kSymbol))
      site.type_symbol = as_string(row[kSymbol]);
    else
      site.type_symbol = site.label;
    if (row.has(kX))
      site.fract.x = as_number(row[kX]);
    if (row.has(kY))
      site.fract.y = as_number(row[kY]);
    if (row.has(kZ))
      site.fract.z = as_number(row[kZ]);
    if (row.has(kUiso))
      site.u_iso = as_number(row[kUiso], 0.0);
    else if (row.has(kBiso))
      site.u_iso = as_number(row[kBiso], 0.0) / (8 * pi() * pi());
    if (row.has(kOcc))
      site.occ = as_number(row[kOcc], 1.0);
    if (row.has2(kDisorderGroup))
      // ignore non-integer _atom_site_disorder_group
      site.disorder_group = string_to_int(row[kDisorderGroup], false);
    split_element_and_charge(site.type_symbol, &site);
    st.sites.push_back(site);
  }

  std::vector<SmallStructure::Site>::iterator aniso_site = st.sites.begin();
  for (auto row : block.find("_atom_site_aniso_",
                             {"label", "U_11", "U_22", "U_33",
                              "U_12", "U_13", "U_23"})) {
    std::string aniso_label = row.str(0);
    if (aniso_site == st.sites.end() || aniso_site->label != aniso_label) {
      aniso_site = std::find_if(st.sites.begin(), st.sites.end(),
              [&](SmallStructure::Site& x) { return x.label == aniso_label; });
      if (aniso_site == st.sites.end())
        continue;
    }
    aniso_site->u11 = as_number(row[1], 0.0);
    aniso_site->u22 = as_number(row[2], 0.0);
    aniso_site->u33 = as_number(row[3], 0.0);
    aniso_site->u12 = as_number(row[4], 0.0);
    aniso_site->u13 = as_number(row[5], 0.0);
    aniso_site->u23 = as_number(row[6], 0.0);
    ++aniso_site;
  }

  for (auto row : block.find("_atom_type_",
                             {"symbol",
                              "scat_dispersion_real",
                              "scat_dispersion_imag"})) {
    SmallStructure::AtomType atom_type;
    atom_type.symbol = row.str(0);
    atom_type.dispersion_real = cif::as_number(row[1]);
    atom_type.dispersion_imag = cif::as_number(row[2]);
    split_element_and_charge(atom_type.symbol, &atom_type);
    st.atom_types.push_back(atom_type);
  }
  if (cif::Column w_col = block.find_values("_diffrn_radiation_wavelength"))
    st.wavelength = cif::as_number(w_col.at(0));

  const SpaceGroup* sg = find_spacegroup_by_name(st.spacegroup_hm,
                                                 st.cell.alpha, st.cell.gamma);
  st.cell.set_cell_images_from_spacegroup(sg);
  return st;
}

} // namespace gemmi
#endif
<|endoftext|>


<commit_before>#pragma once

#include <cstdint>
#include <cstddef>
#include <string>

#include <athena/DNA.hpp>
#include <logvisor/logvisor.hpp>

namespace hecl {

/**
 * @brief FourCC representation used within HECL's database
 *
 * FourCCs are efficient, mnemonic four-char-sequences used to represent types
 * while fitting comfortably in a 32-bit word. HECL uses a four-char array
 * to remain endian-independent.
 */
class FourCC {
protected:
  union {
    char fcc[4];
    uint32_t num = 0;
  };

public:
  // Sentinel FourCC
  constexpr FourCC() noexcept = default;
  constexpr FourCC(const FourCC& other) noexcept = default;
  constexpr FourCC(FourCC&& other) noexcept = default;
  constexpr FourCC(const char* name) noexcept : fcc{name[0], name[1], name[2], name[3]} {}
  constexpr FourCC(uint32_t n) noexcept : num(n) {}

  constexpr FourCC& operator=(const FourCC&) noexcept = default;
  constexpr FourCC& operator=(FourCC&&) noexcept = default;

  constexpr bool operator==(const FourCC& other) const noexcept { return num == other.num; }
  constexpr bool operator!=(const FourCC& other) const noexcept { return !operator==(other); }
  constexpr bool operator==(const char* other) const noexcept {
    return other[0] == fcc[0] && other[1] == fcc[1] && other[2] == fcc[2] && other[3] == fcc[3];
  }
  constexpr bool operator!=(const char* other) const noexcept { return !operator==(other); }
  constexpr bool operator==(int32_t other) const noexcept { return num == uint32_t(other); }
  constexpr bool operator!=(int32_t other) const noexcept { return !operator==(other); }
  constexpr bool operator==(uint32_t other) const noexcept { return num == other; }
  constexpr bool operator!=(uint32_t other) const noexcept { return !operator==(other); }

  std::string toString() const { return std::string(std::begin(fcc), std::end(fcc)); }
  constexpr std::string_view toStringView() const { return std::string_view(fcc, std::size(fcc)); }
  constexpr uint32_t toUint32() const noexcept { return num; }
  constexpr const char* getChars() const noexcept { return fcc; }
  constexpr char* getChars() noexcept { return fcc; }
  constexpr bool IsValid() const noexcept { return num != 0; }
};
#define FOURCC(chars) FourCC(SBIG(chars))

using BigDNA = athena::io::DNA<athena::Endian::Big>;

/** FourCC with DNA read/write */
class DNAFourCC final : public BigDNA, public FourCC {
public:
  constexpr DNAFourCC() : FourCC() {}
  constexpr DNAFourCC(const FourCC& other) : FourCC() { num = other.toUint32(); }
  constexpr DNAFourCC(const char* name) : FourCC(name) {}
  constexpr DNAFourCC(uint32_t n) : FourCC(n) {}
  AT_DECL_EXPLICIT_DNA_YAML
};
template <>
inline void DNAFourCC::Enumerate<BigDNA::Read>(Read::StreamT& r) {
  r.readUBytesToBuf(fcc, std::size(fcc));
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::Write>(Write::StreamT& w) {
  w.writeBytes(fcc, std::size(fcc));
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::ReadYaml>(ReadYaml::StreamT& r) {
  const std::string rs = r.readString();
  rs.copy(fcc, std::size(fcc));
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::WriteYaml>(WriteYaml::StreamT& w) {
  w.writeString(std::string_view{fcc, std::size(fcc)});
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::BinarySize>(BinarySize::StreamT& s) {
  s += std::size(fcc);
}

} // namespace hecl

namespace std {
template <>
struct hash<hecl::FourCC> {
  size_t operator()(const hecl::FourCC& val) const noexcept { return val.toUint32(); }
};
} // namespace std

FMT_CUSTOM_FORMATTER(hecl::FourCC, "{:c}{:c}{:c}{:c}", obj.getChars()[0], obj.getChars()[1], obj.getChars()[2],
                     obj.getChars()[3])
FMT_CUSTOM_FORMATTER(hecl::DNAFourCC, "{:c}{:c}{:c}{:c}", obj.getChars()[0], obj.getChars()[1], obj.getChars()[2],
                     obj.getChars()[3])
<commit_msg>Add IStreamReader overloaded constructor to DNAFourCC<commit_after>#pragma once

#include <cstdint>
#include <cstddef>
#include <string>

#include <athena/DNA.hpp>
#include <logvisor/logvisor.hpp>

namespace hecl {

/**
 * @brief FourCC representation used within HECL's database
 *
 * FourCCs are efficient, mnemonic four-char-sequences used to represent types
 * while fitting comfortably in a 32-bit word. HECL uses a four-char array
 * to remain endian-independent.
 */
class FourCC {
protected:
  union {
    char fcc[4];
    uint32_t num = 0;
  };

public:
  // Sentinel FourCC
  constexpr FourCC() noexcept = default;
  constexpr FourCC(const FourCC& other) noexcept = default;
  constexpr FourCC(FourCC&& other) noexcept = default;
  constexpr FourCC(const char* name) noexcept : fcc{name[0], name[1], name[2], name[3]} {}
  constexpr FourCC(uint32_t n) noexcept : num(n) {}

  constexpr FourCC& operator=(const FourCC&) noexcept = default;
  constexpr FourCC& operator=(FourCC&&) noexcept = default;

  constexpr bool operator==(const FourCC& other) const noexcept { return num == other.num; }
  constexpr bool operator!=(const FourCC& other) const noexcept { return !operator==(other); }
  constexpr bool operator==(const char* other) const noexcept {
    return other[0] == fcc[0] && other[1] == fcc[1] && other[2] == fcc[2] && other[3] == fcc[3];
  }
  constexpr bool operator!=(const char* other) const noexcept { return !operator==(other); }
  constexpr bool operator==(int32_t other) const noexcept { return num == uint32_t(other); }
  constexpr bool operator!=(int32_t other) const noexcept { return !operator==(other); }
  constexpr bool operator==(uint32_t other) const noexcept { return num == other; }
  constexpr bool operator!=(uint32_t other) const noexcept { return !operator==(other); }

  std::string toString() const { return std::string(std::begin(fcc), std::end(fcc)); }
  constexpr std::string_view toStringView() const { return std::string_view(fcc, std::size(fcc)); }
  constexpr uint32_t toUint32() const noexcept { return num; }
  constexpr const char* getChars() const noexcept { return fcc; }
  constexpr char* getChars() noexcept { return fcc; }
  constexpr bool IsValid() const noexcept { return num != 0; }
};
#define FOURCC(chars) FourCC(SBIG(chars))

using BigDNA = athena::io::DNA<athena::Endian::Big>;

/** FourCC with DNA read/write */
class DNAFourCC final : public BigDNA, public FourCC {
public:
  constexpr DNAFourCC() noexcept : FourCC() {}
  constexpr DNAFourCC(const FourCC& other) noexcept : FourCC(other) {}
  constexpr DNAFourCC(const char* name) noexcept : FourCC(name) {}
  constexpr DNAFourCC(uint32_t n) noexcept : FourCC(n) {}
  constexpr DNAFourCC(athena::io::IStreamReader& r) { read(r); }
  AT_DECL_EXPLICIT_DNA_YAML
};
template <>
inline void DNAFourCC::Enumerate<BigDNA::Read>(Read::StreamT& r) {
  r.readUBytesToBuf(fcc, std::size(fcc));
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::Write>(Write::StreamT& w) {
  w.writeBytes(fcc, std::size(fcc));
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::ReadYaml>(ReadYaml::StreamT& r) {
  const std::string rs = r.readString();
  rs.copy(fcc, std::size(fcc));
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::WriteYaml>(WriteYaml::StreamT& w) {
  w.writeString(std::string_view{fcc, std::size(fcc)});
}
template <>
inline void DNAFourCC::Enumerate<BigDNA::BinarySize>(BinarySize::StreamT& s) {
  s += std::size(fcc);
}

} // namespace hecl

namespace std {
template <>
struct hash<hecl::FourCC> {
  size_t operator()(const hecl::FourCC& val) const noexcept { return val.toUint32(); }
};
} // namespace std

FMT_CUSTOM_FORMATTER(hecl::FourCC, "{:c}{:c}{:c}{:c}", obj.getChars()[0], obj.getChars()[1], obj.getChars()[2],
                     obj.getChars()[3])
FMT_CUSTOM_FORMATTER(hecl::DNAFourCC, "{:c}{:c}{:c}{:c}", obj.getChars()[0], obj.getChars()[1], obj.getChars()[2],
                     obj.getChars()[3])
<|endoftext|>