<commit_before>#pragma once
//=====================================================================//
/*! @file
    @brief  EFO Test・アプリケーション・クラス
    @author 平松邦仁 (hira@rvf-rc45.net)
	@copyright	Copyright (C) 2017 Kunihito Hiramatsu @n
				Released under the MIT license @n
				https://github.com/hirakuni45/RX/blob/master/LICENSE
*/
//=====================================================================//
#include "main.hpp"
#include "core/glcore.hpp"
#include "utils/i_scene.hpp"
#include "utils/director.hpp"
#include "widgets/widget.hpp"
#include "widgets/widget_frame.hpp"
#include "widgets/widget_null.hpp"
#include "widgets/widget_button.hpp"
#include "widgets/widget_list.hpp"
#include "widgets/widget_filer.hpp"
#include "widgets/widget_terminal.hpp"
#include "widgets/widget_view.hpp"
#include "widgets/widget_utils.hpp"

#include "gl_fw/render_waves.hpp"

namespace app {

	//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
	/*!
		@brief  Ignitor アプリケーション・クラス
	*/
	//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
	class efo_test : public utils::i_scene {

		utils::director<core>&	director_;

		gui::widget_frame*		menu_;
		gui::widget_button*		load_;
		gui::widget_list*		div_;

		gui::widget_filer*		load_ctx_;

		gui::widget_frame*		wave_;

		gui::widget_frame*		terminal_frame_;
		gui::widget_terminal*	terminal_core_;

		gui::widget_frame*		view_frame_;
		gui::widget_view*		view_core_;

		typedef view::render_waves<uint16_t, 65536 * 4> WAVES;
		WAVES					waves_;

		// ターミナル、行入力
		void term_enter_(const utils::lstring& text) {
			auto s = utils::utf32_to_utf8(text);
//			project_.logic_edit_.command(s);
///			std::cout << s << std::endl;
		}

		// 波形描画
		void update_view_()
		{
		}

		void render_view_(const vtx::irect& clip)
		{
			glDisable(GL_TEXTURE_2D);

			gl::glColor(img::rgba8(255, 255));
			waves_.render(clip.size.x);

			glEnable(GL_TEXTURE_2D);
		}

		void service_view_()
		{
		}

	public:
		//-----------------------------------------------------------------//
		/*!
			@brief  コンストラクター
		*/
		//-----------------------------------------------------------------//
		efo_test(utils::director<core>& d) : director_(d),
			menu_(nullptr), load_(nullptr), load_ctx_(nullptr),
			wave_(nullptr),
			terminal_frame_(nullptr), terminal_core_(nullptr),
			view_frame_(nullptr), view_core_(nullptr)
		{ }

		//-----------------------------------------------------------------//
		/*!
			@brief  初期化
		*/
		//-----------------------------------------------------------------//
		void initialize()
		{
			using namespace gui;
			widget_director& wd = director_.at().widget_director_;
			gl::core& core = gl::core::get_instance();

			int menu_width  = 130;
			int menu_height = 300;
			{	// メニューパレット
				widget::param wp(vtx::irect(10, 10, menu_width, menu_height));
				widget_frame::param wp_;
				wp_.plate_param_.set_caption(12);
				menu_ = wd.add_widget<widget_frame>(wp, wp_);
				menu_->set_state(gui::widget::state::SIZE_LOCK);
			}

			{ // ロード起動ボタン
				widget::param wp(vtx::irect(10, 20+40*0, menu_width - 20, 30), menu_);
				widget_button::param wp_("load");
				wp_.select_func_ = [this](int id) {
//					gui::get_open_file_name();
					if(load_ctx_) {
//						script_on_ = false;
						bool f = load_ctx_->get_state(gui::widget::state::ENABLE);
						load_ctx_->enable(!f);
//						save_->set_stall(!f);
//						export_->set_stall(!f);
//						script_->set_stall(!f);
					}
				};
				load_ = wd.add_widget<widget_button>(wp, wp_);
			}

			{ // DIV select
				widget::param wp(vtx::irect(10, 20+40*1, menu_width - 20, 30), menu_);
				widget_list::param wp_("1000 ms");
				wp_.text_list_.push_back("1000 ms");
				wp_.text_list_.push_back("500 ms");
				wp_.text_list_.push_back("250 ms");
				wp_.text_list_.push_back("100 ms");
				wp_.text_list_.push_back("50 ms");
				wp_.text_list_.push_back("10 ms");
				wp_.text_list_.push_back("5 ms");
				wp_.text_list_.push_back("1 ms");
				wp_.text_list_.push_back("500 us");
				wp_.text_list_.push_back("100 us");
				wp_.text_list_.push_back("50 us");
				wp_.text_list_.push_back("25 us");
				wp_.text_list_.push_back("10 us");
				wp_.text_list_.push_back("5 us");
				wp_.text_list_.push_back("1 us");
//				wp_.select_func_ = [this](const std::string& text, uint32_t pos) {
//					utils::format("List Selected: '%s', (%d)\n") % text.c_str() % pos;
//				};
				div_ = wd.add_widget<widget_list>(wp, wp_);
			}

			{ // load ファイラー本体
				widget::param wp(vtx::irect(10, 30, 300, 200));
				widget_filer::param wp_(core.get_current_path());
				wp_.select_file_func_ = [this](const std::string& path) {
#if 0
					bool f = false;
					if(script_on_) {
						f = project_.logic_edit_.injection(path);
					} else {
						f = project_.logic_.load(path);
					}
					load_->set_stall(false);
					save_->set_stall(false);
					export_->set_stall(false);
					script_->set_stall(false);
					if(!f) {  // load error
						if(script_on_) dialog_->set_text("Script error:\n" + path);
						else dialog_->set_text("Load error:\n" + path);
						dialog_->enable();
					}
#endif
				};
				load_ctx_ = wd.add_widget<widget_filer>(wp, wp_);
				load_ctx_->enable(false);
			}

			{	// ターミナル
				{
					widget::param wp(vtx::irect(20, 100, 100, 200));
					widget_frame::param wp_;
					wp_.plate_param_.set_caption(12);
					terminal_frame_ = wd.add_widget<widget_frame>(wp, wp_);
				}
				{
					widget::param wp(vtx::irect(0), terminal_frame_);
					widget_terminal::param wp_;
					wp_.enter_func_ = [this](const utils::lstring& text) {
						term_enter_(text);
					};
					terminal_core_ = wd.add_widget<widget_terminal>(wp, wp_);
					term_chaout::set_output(terminal_core_);
				}

				// ロジック編集クラスの出力先の設定
//				project_.logic_edit_.set_output([this](const std::string& s) {
//					terminal_core_->output(s);
//				}
//				);
			}

			{	// 波形ビュー
				{
					widget::param wp(vtx::irect(40, 150, 200, 200));
					widget_frame::param wp_;
					wp_.plate_param_.set_caption(12);
					view_frame_ = wd.add_widget<widget_frame>(wp, wp_);
				}
				{
					widget::param wp(vtx::irect(0, 50, 0, 0), view_frame_);
					widget_view::param wp_;
					wp_.update_func_ = [this]() {
						update_view_();
					};
					wp_.render_func_ = [this](const vtx::irect& clip) {
						render_view_(clip);
					};
					wp_.service_func_ = [this]() {
						service_view_();
					};
					view_core_ = wd.add_widget<widget_view>(wp, wp_);
				}
			}

			// プリファレンスのロード
			sys::preference& pre = director_.at().preference_;

			if(menu_ != nullptr) {
				menu_->load(pre, false, false);
			}

///			project_.load(pre);

			if(terminal_frame_ != nullptr) {
				terminal_frame_->load(pre);
			}

			if(view_frame_ != nullptr) {
				view_frame_->load(pre);
			}

//			if(argv_frame_ != nullptr) {
//				argv_frame_->load(pre);
//			}

			if(load_ctx_ != nullptr) load_ctx_->load(pre);
///			if(save_ctx_ != nullptr) save_ctx_->load(pre);

			if(div_ != nullptr) div_->load(pre);

			// テスト波形生成
			waves_.create_waves(0.5, 5.0 * 10e-6);
			waves_.create_sin(10000000, 1 * 10e-3);
		}

		//-----------------------------------------------------------------//
		/*!
			@brief  アップデート
		*/
		//-----------------------------------------------------------------//
		void update()
		{
			gui::widget_director& wd = director_.at().widget_director_;
#if 0
			// Drag & Drop されたファイル
			gl::core& core = gl::core::get_instance();
			int id = core.get_recv_files_id();
			if(drop_file_id_ != id) {
				drop_file_id_ = id;
				const utils::strings& ss = core.get_recv_files_path();
				if(!ss.empty()) {
					std::string path = ss[0];
					if(load_ctx_ != nullptr && load_ctx_->get_local_param().select_file_func_ != nullptr) {
						load_ctx_->get_local_param().select_file_func_(path);
					}
				}
			}
#endif
			wd.update();
		}

		//-----------------------------------------------------------------//
		/*!
			@brief  レンダリング
		*/
		//-----------------------------------------------------------------//
		void render()
		{
			director_.at().widget_director_.service();
			director_.at().widget_director_.render();
		}

		//-----------------------------------------------------------------//
		/*!
			@brief  廃棄
		*/
		//-----------------------------------------------------------------//
		void destroy()
		{
			sys::preference& pre = director_.at().preference_;

			if(div_ != nullptr) div_->save(pre);

			if(load_ctx_ != nullptr) load_ctx_->save(pre);
///			if(save_ctx_ != nullptr) save_ctx_->save(pre);

//			if(argv_frame_ != nullptr) {
//				argv_frame_->save(pre);
//			}

			if(view_frame_ != nullptr) {
				view_frame_->save(pre);
			}

			if(terminal_frame_ != nullptr) {
				terminal_frame_->save(pre);
			}

//			project_.save(pre);

			if(menu_ != nullptr) {
				menu_->save(pre);
			}
		}
	};
}
<commit_msg>update widget_list manage<commit_after>#pragma once
//=====================================================================//
/*! @file
    @brief  EFO Test・アプリケーション・クラス
    @author 平松邦仁 (hira@rvf-rc45.net)
	@copyright	Copyright (C) 2017 Kunihito Hiramatsu @n
				Released under the MIT license @n
				https://github.com/hirakuni45/RX/blob/master/LICENSE
*/
//=====================================================================//
#include "main.hpp"
#include "core/glcore.hpp"
#include "utils/i_scene.hpp"
#include "utils/director.hpp"
#include "widgets/widget.hpp"
#include "widgets/widget_frame.hpp"
#include "widgets/widget_null.hpp"
#include "widgets/widget_button.hpp"
#include "widgets/widget_list.hpp"
#include "widgets/widget_filer.hpp"
#include "widgets/widget_terminal.hpp"
#include "widgets/widget_view.hpp"
#include "widgets/widget_utils.hpp"

#include "gl_fw/render_waves.hpp"

namespace app {

	//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
	/*!
		@brief  Ignitor アプリケーション・クラス
	*/
	//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++//
	class efo_test : public utils::i_scene {

		utils::director<core>&	director_;

		gui::widget_frame*		menu_;
		gui::widget_button*		load_;
		gui::widget_list*		div_;

		gui::widget_filer*		load_ctx_;

		gui::widget_frame*		wave_;

		gui::widget_frame*		terminal_frame_;
		gui::widget_terminal*	terminal_core_;

		gui::widget_frame*		view_frame_;
		gui::widget_view*		view_core_;

		typedef view::render_waves<uint16_t, 65536 * 4> WAVES;
		WAVES					waves_;

		// ターミナル、行入力
		void term_enter_(const utils::lstring& text) {
			auto s = utils::utf32_to_utf8(text);
//			project_.logic_edit_.command(s);
///			std::cout << s << std::endl;
		}

		// 波形描画
		void update_view_()
		{
		}

		void render_view_(const vtx::irect& clip)
		{
			glDisable(GL_TEXTURE_2D);

			gl::glColor(img::rgba8(255, 255));
			waves_.render(clip.size.x);

			glEnable(GL_TEXTURE_2D);
		}

		void service_view_()
		{
		}

	public:
		//-----------------------------------------------------------------//
		/*!
			@brief  コンストラクター
		*/
		//-----------------------------------------------------------------//
		efo_test(utils::director<core>& d) : director_(d),
			menu_(nullptr), load_(nullptr), load_ctx_(nullptr),
			wave_(nullptr),
			terminal_frame_(nullptr), terminal_core_(nullptr),
			view_frame_(nullptr), view_core_(nullptr)
		{ }

		//-----------------------------------------------------------------//
		/*!
			@brief  初期化
		*/
		//-----------------------------------------------------------------//
		void initialize()
		{
			using namespace gui;
			widget_director& wd = director_.at().widget_director_;
			gl::core& core = gl::core::get_instance();

			int menu_width  = 130;
			int menu_height = 300;
			{	// メニューパレット
				widget::param wp(vtx::irect(10, 10, menu_width, menu_height));
				widget_frame::param wp_;
				wp_.plate_param_.set_caption(12);
				menu_ = wd.add_widget<widget_frame>(wp, wp_);
				menu_->set_state(gui::widget::state::SIZE_LOCK);
			}

			{ // ロード起動ボタン
				widget::param wp(vtx::irect(10, 20+40*0, menu_width - 20, 30), menu_);
				widget_button::param wp_("load");
				wp_.select_func_ = [this](int id) {
//					gui::get_open_file_name();
					if(load_ctx_) {
//						script_on_ = false;
						bool f = load_ctx_->get_state(gui::widget::state::ENABLE);
						load_ctx_->enable(!f);
//						save_->set_stall(!f);
//						export_->set_stall(!f);
//						script_->set_stall(!f);
					}
				};
				load_ = wd.add_widget<widget_button>(wp, wp_);
			}

			{ // DIV select
				widget::param wp(vtx::irect(10, 20+40*1, menu_width - 20, 30), menu_);
				widget_list::param wp_("1000 ms");
				wp_.init_list_.push_back("1000 ms");
				wp_.init_list_.push_back("500 ms");
				wp_.init_list_.push_back("250 ms");
				wp_.init_list_.push_back("100 ms");
				wp_.init_list_.push_back("50 ms");
				wp_.init_list_.push_back("10 ms");
				wp_.init_list_.push_back("5 ms");
				wp_.init_list_.push_back("1 ms");
				wp_.init_list_.push_back("500 us");
				wp_.init_list_.push_back("100 us");
				wp_.init_list_.push_back("50 us");
				wp_.init_list_.push_back("25 us");
				wp_.init_list_.push_back("10 us");
				wp_.init_list_.push_back("5 us");
				wp_.init_list_.push_back("1 us");
//				wp_.select_func_ = [this](const std::string& text, uint32_t pos) {
//					utils::format("List Selected: '%s', (%d)\n") % text.c_str() % pos;
//				};
				div_ = wd.add_widget<widget_list>(wp, wp_);
			}

			{ // load ファイラー本体
				widget::param wp(vtx::irect(10, 30, 300, 200));
				widget_filer::param wp_(core.get_current_path());
				wp_.select_file_func_ = [this](const std::string& path) {
#if 0
					bool f = false;
					if(script_on_) {
						f = project_.logic_edit_.injection(path);
					} else {
						f = project_.logic_.load(path);
					}
					load_->set_stall(false);
					save_->set_stall(false);
					export_->set_stall(false);
					script_->set_stall(false);
					if(!f) {  // load error
						if(script_on_) dialog_->set_text("Script error:\n" + path);
						else dialog_->set_text("Load error:\n" + path);
						dialog_->enable();
					}
#endif
				};
				load_ctx_ = wd.add_widget<widget_filer>(wp, wp_);
				load_ctx_->enable(false);
			}

			{	// ターミナル
				{
					widget::param wp(vtx::irect(20, 100, 100, 200));
					widget_frame::param wp_;
					wp_.plate_param_.set_caption(12);
					terminal_frame_ = wd.add_widget<widget_frame>(wp, wp_);
				}
				{
					widget::param wp(vtx::irect(0), terminal_frame_);
					widget_terminal::param wp_;
					wp_.enter_func_ = [this](const utils::lstring& text) {
						term_enter_(text);
					};
					terminal_core_ = wd.add_widget<widget_terminal>(wp, wp_);
					term_chaout::set_output(terminal_core_);
				}

				// ロジック編集クラスの出力先の設定
//				project_.logic_edit_.set_output([this](const std::string& s) {
//					terminal_core_->output(s);
//				}
//				);
			}

			{	// 波形ビュー
				{
					widget::param wp(vtx::irect(40, 150, 200, 200));
					widget_frame::param wp_;
					wp_.plate_param_.set_caption(12);
					view_frame_ = wd.add_widget<widget_frame>(wp, wp_);
				}
				{
					widget::param wp(vtx::irect(0, 50, 0, 0), view_frame_);
					widget_view::param wp_;
					wp_.update_func_ = [this]() {
						update_view_();
					};
					wp_.render_func_ = [this](const vtx::irect& clip) {
						render_view_(clip);
					};
					wp_.service_func_ = [this]() {
						service_view_();
					};
					view_core_ = wd.add_widget<widget_view>(wp, wp_);
				}
			}

			// プリファレンスのロード
			sys::preference& pre = director_.at().preference_;

			if(menu_ != nullptr) {
				menu_->load(pre, false, false);
			}

///			project_.load(pre);

			if(terminal_frame_ != nullptr) {
				terminal_frame_->load(pre);
			}

			if(view_frame_ != nullptr) {
				view_frame_->load(pre);
			}

//			if(argv_frame_ != nullptr) {
//				argv_frame_->load(pre);
//			}

			if(load_ctx_ != nullptr) load_ctx_->load(pre);
///			if(save_ctx_ != nullptr) save_ctx_->load(pre);

			if(div_ != nullptr) div_->load(pre);

			// テスト波形生成
			waves_.create_waves(0.5, 5.0 * 10e-6);
			waves_.create_sin(10000000, 1 * 10e-3);
		}

		//-----------------------------------------------------------------//
		/*!
			@brief  アップデート
		*/
		//-----------------------------------------------------------------//
		void update()
		{
			gui::widget_director& wd = director_.at().widget_director_;
#if 0
			// Drag & Drop されたファイル
			gl::core& core = gl::core::get_instance();
			int id = core.get_recv_files_id();
			if(drop_file_id_ != id) {
				drop_file_id_ = id;
				const utils::strings& ss = core.get_recv_files_path();
				if(!ss.empty()) {
					std::string path = ss[0];
					if(load_ctx_ != nullptr && load_ctx_->get_local_param().select_file_func_ != nullptr) {
						load_ctx_->get_local_param().select_file_func_(path);
					}
				}
			}
#endif
			wd.update();
		}

		//-----------------------------------------------------------------//
		/*!
			@brief  レンダリング
		*/
		//-----------------------------------------------------------------//
		void render()
		{
			director_.at().widget_director_.service();
			director_.at().widget_director_.render();
		}

		//-----------------------------------------------------------------//
		/*!
			@brief  廃棄
		*/
		//-----------------------------------------------------------------//
		void destroy()
		{
			sys::preference& pre = director_.at().preference_;

			if(div_ != nullptr) div_->save(pre);

			if(load_ctx_ != nullptr) load_ctx_->save(pre);
///			if(save_ctx_ != nullptr) save_ctx_->save(pre);

//			if(argv_frame_ != nullptr) {
//				argv_frame_->save(pre);
//			}

			if(view_frame_ != nullptr) {
				view_frame_->save(pre);
			}

			if(terminal_frame_ != nullptr) {
				terminal_frame_->save(pre);
			}

//			project_.save(pre);

			if(menu_ != nullptr) {
				menu_->save(pre);
			}
		}
	};
}
<|endoftext|>


<commit_before>/*********************************************************************
** Author: Zach Colbert
** Date: 1 November 2017
** Description:
*********************************************************************/

#include <string>
#include "Player.hpp"

#ifndef TEAM_HPP
#define TEAM_HPP

class Team
{
private:
    // Member variables for each position on the team
    Player pointGuard, shootingGuard, smallForward, powerForward, center;

public:
    // This class doesn't get a default constructor, because there's no "I" in "Team"
    Team::Team(Player point_Guard, Player shooting_Guard, Player small_Forward, Player power_Forward, Player center_In);

    // Mutator for pointGuard
    void setPointGuard(Player p);

    // Accessor for pointGuard
    Player getPointGuard();

    // Mutator for shootingGuard
    void setShootingGuard(Player p);

    // Accessor for shootingGuard
    Player getShootingGuard();

    // Mutator for smallForward
    void setSmallForward(Player p);

    // Accessor for smallForward
    Player getSmallForward();

    // Mutator for powerForward
    void setPowerForward(Player p);

    // Accessor for powerForward
    Player getPowerForward();

    // Mutator for center
    void setCenter(Player p);

    // Accessor for center
    Player getCenter();

    // totalPoints gets the points attribute from each of the member variables, and returns the total
    int totalPoints();

};

#endif<commit_msg>Some variables didn't play nice. Team function did not need a class:: prefix<commit_after>/*********************************************************************
** Author: Zach Colbert
** Date: 1 November 2017
** Description:
*********************************************************************/

#include <string>
#include "Player.hpp"

#ifndef TEAM_HPP
#define TEAM_HPP

class Team
{
private:
    // Member variables for each position on the team
    Player pointGuard, shootingGuard, smallForward, powerForward, center;

public:
    // This class doesn't get a default constructor, because there's no "I" in "Team"
    Team(Player point_Guard, Player shooting_Guard, Player small_Forward, Player power_Forward, Player center_In);

    // Mutator for pointGuard
    void setPointGuard(Player pIn);

    // Accessor for pointGuard
    Player getPointGuard();

    // Mutator for shootingGuard
    void setShootingGuard(Player pIn);

    // Accessor for shootingGuard
    Player getShootingGuard();

    // Mutator for smallForward
    void setSmallForward(Player pIn);

    // Accessor for smallForward
    Player getSmallForward();

    // Mutator for powerForward
    void setPowerForward(Player pIn);

    // Accessor for powerForward
    Player getPowerForward();

    // Mutator for center
    void setCenter(Player pIn);

    // Accessor for center
    Player getCenter();

    // totalPoints gets the points attribute from each of the member variables, and returns the total
    int totalPoints();

};

#endif<|endoftext|>


<commit_before>/*
 * Object to format common types of MIDI events into raw MIDI event dictionaries
 * Copyright © 2011, Timothy Place
 *
 * License: This code is licensed under the terms of the "New BSD License"
 * http://creativecommons.org/licenses/BSD/
 */

#include "TTGraphObjectBase.h"
#include "TTMidiFormat.h"
#ifdef TT_PLATFORM_WIN
#include <algorithm>
#endif

#define thisTTClass			TTMidiFormat
#define thisTTClassName		"midi.format"
#define thisTTClassTags		"midi"

TT_OBJECT_CONSTRUCTOR
{
	addMessageWithArguments(dictionary);
}

TTMidiFormat::~TTMidiFormat()
{
	;
}

TTErr TTMidiFormat::dictionary(const TTValue& input, TTValue& output)
{
	TTDictionaryPtr	d = NULL;
	TTSymbol		schema;

	//input.get(0, (TTPtr*)(&d));
    d = TTDictionaryPtr(TTPtr(input[0]));

	schema = d->getSchema();

	if (schema == TT("MidiNoteEvent")) {
		TTValue v;
		TTUInt8	noteNumber = 0;
		TTUInt8 noteVelocity = 0;
		TTUInt8 noteChannel = 1;

		d->getValue(v);
		v.get(0, noteNumber);
		v.get(1, noteVelocity);
		v.get(2, noteChannel);

		if (noteVelocity > 0)	// Note-on
			d->append(TT("status"), 143 + noteChannel);
		else					// Note-off
			d->append(TT("status"), 127 + noteChannel);

		d->append(TT("data1"), noteNumber);
		d->append(TT("data2"), noteVelocity);
		d->setSchema(TT("RawMidiEvent"));
		output.set(0, TTPtr(d));
	}
	else if (schema == TT("RawMidiEvent"))
		output = input; // Nothing to do...
	else
		return kTTErrInvalidType;

	return kTTErrNone;
}

<commit_msg>replacing deprecated get() and set() calls in Graph MidiLib<commit_after>/*
 * Object to format common types of MIDI events into raw MIDI event dictionaries
 * Copyright © 2011, Timothy Place
 *
 * License: This code is licensed under the terms of the "New BSD License"
 * http://creativecommons.org/licenses/BSD/
 */

#include "TTGraphObjectBase.h"
#include "TTMidiFormat.h"
#ifdef TT_PLATFORM_WIN
#include <algorithm>
#endif

#define thisTTClass			TTMidiFormat
#define thisTTClassName		"midi.format"
#define thisTTClassTags		"midi"

TT_OBJECT_CONSTRUCTOR
{
	addMessageWithArguments(dictionary);
}

TTMidiFormat::~TTMidiFormat()
{
	;
}

TTErr TTMidiFormat::dictionary(const TTValue& input, TTValue& output)
{
	TTDictionaryPtr	d = NULL;
	TTSymbol		schema;

	//input.get(0, (TTPtr*)(&d));
    d = TTDictionaryPtr(TTPtr(input[0]));

	schema = d->getSchema();

	if (schema == TT("MidiNoteEvent")) {
		TTValue v;
		TTUInt8	noteNumber = 0;
		TTUInt8 noteVelocity = 0;
		TTUInt8 noteChannel = 1;

		d->getValue(v);
		noteNumber   = v[0];
		noteVelocity = v[1];
		noteChannel  = v[2];

		if (noteVelocity > 0)	// Note-on
			d->append(TT("status"), 143 + noteChannel);
		else					// Note-off
			d->append(TT("status"), 127 + noteChannel);

		d->append(TT("data1"), noteNumber);
		d->append(TT("data2"), noteVelocity);
		d->setSchema(TT("RawMidiEvent"));
		output[0] = TTPtr(d);
	}
	else if (schema == TT("RawMidiEvent"))
		output = input; // Nothing to do...
	else
		return kTTErrInvalidType;

	return kTTErrNone;
}

<|endoftext|>


<commit_before>// [standard includes]
#include <vector>
#include <set>
#include <queue>
#include <algorithm>
#include <fstream>
#include <sstream>
#include <iostream>
#include <thread>
#include <mutex>
#include <condition_variable>
#include <atomic>
#include <memory>
#include <cstdio>
#include <typeinfo>

// [external includes]
#include <opencl_utils.h>

// [local includes]
#include "options.h"
#include "run.h"

template<typename T>
using Matrix = std::vector<T>;

template<typename T>
struct MVRun : public Run {
  // input matrix size
  std::size_t size;

  // list of additional buffers to allocate
  std::vector<int> extra_buffer_size;
  std::vector<cl::Buffer> extra_args;

  // list of additional local buffers to allocate
  std::vector<int> extra_local_buffer_size;
  std::vector<cl::LocalSpaceArg> extra_local_args;

  /**
   * Deserialize a line from the CSV
   */
  MVRun(const std::vector<std::string>& values) {
    assert(values.size() > 8 && "Bad CSV format");

    // input size
    size = Csv::readInt(values[0]);

    // global NDRange
    glob1 = Csv::readInt(values[1]);
    glob2 = Csv::readInt(values[2]);
    glob3 = Csv::readInt(values[3]);

    // local NDRange
    loc1 = Csv::readInt(values[4]);
    loc2 = Csv::readInt(values[5]);
    loc3 = Csv::readInt(values[6]);

    // source hash
    hash = values[7];
    hash.erase(std::remove_if(std::begin(hash), std::end(hash), isspace), std::end(hash));

    // number of temporary buffers to allocate and their sizes
    auto num_buf = Csv::readInt(values[8]);
    for(unsigned i = 9+3; i < 9+3 + num_buf; ++i) {
      extra_buffer_size.push_back((int)Csv::readInt(values[i]));
    }

    // number of local buffers to allocate and their sizes
    auto num_local = Csv::readInt(values[12+num_buf]);
    for (unsigned i = 13 + (unsigned) num_buf; i < 13 + num_buf + num_local; ++i) {
      extra_local_buffer_size.push_back((int)Csv::readInt(values[i]));
    }
  }

  void setup(cl::Context context) override {
    // Allocate extra buffers
    for(auto &size: extra_buffer_size)
      extra_args.push_back({context, CL_MEM_READ_WRITE, (size_t) size});

    for (auto &size: extra_local_buffer_size)
      extra_local_args.push_back({(size_t) size});

    // Skip the first 3 to compensate for the csv (forgot a drop(3) in scala)
    for(unsigned i = 0; i < extra_args.size(); ++i)
      kernel.setArg(3+i, extra_args[i]);

    for (unsigned i = 0; i < extra_local_args.size(); ++i)
      kernel.setArg((unsigned) extra_args.size() + 3 + i, extra_local_args[i]);

    kernel.setArg((unsigned)extra_local_args.size()+(unsigned)extra_args.size()+3, (int)size);
    kernel.setArg((unsigned)extra_local_args.size()+(unsigned)extra_args.size()+4, (int)size);
  }

  void cleanup() override {
    extra_buffer_size.clear();
    kernel = cl::Kernel();
  }
};

/**
 * FIXME: This is a lazy copy paste of the old main with a template switch for single and double precision
 */
template<typename Float>
void run_harness(
    std::vector<std::shared_ptr<Run>>& all_run,
    const unsigned N,
    const std::string& mat_file,
    const std::string& vec_file,
    const std::string& gold_file,
    const bool force,
    const bool transposeIn,
    const bool threaded,
    const bool binary
)
{
  using namespace std;

  if(binary)
    std::cout << "Using precompiled binaries" << std::endl;
  // Compute input and output
  Matrix<Float> mat(N*N);
  std::vector<Float> vec(N);
  std::vector<Float> gold(N);

  if(File::is_file_exist(gold_file) && File::is_file_exist(mat_file) && File::is_file_exist(vec_file) && !force ) {
    File::load_input(gold, gold_file);
    File::load_input(mat, mat_file);
    File::load_input(vec, vec_file);
  } else {
    for(unsigned y = 0; y < N; ++y) {
      for (unsigned x = 0; x < N; ++x) {
        mat[y * N + x] = (((y * 3 + x * 2) % 10) + 1) * 1.0f;
      }
      vec[y] = (y%10)*0.5f;
    }

    // compute gold
    for (int i=0; i<N; i++) {
      Float Result=0.0;
      for (int j=0; j<N; j++)
        Result+=mat[i*N+j]*vec[j];

      gold[i]=Result;
    }

    if (transposeIn) {
      std::vector<Float> Tmat(N*N);
      for(unsigned y = 0; y < N; ++y)
        for(unsigned x = 0; x < N; ++x)
          Tmat[y*N+x] = mat[x*N+y];
      std::swap(Tmat, mat);
    }

    File::save_input(gold, gold_file);
    File::save_input(mat, mat_file);
    File::save_input(vec, vec_file);
  }

  // validation function
  auto validate = [&](const std::vector<Float> &output) {
    if(gold.size() != output.size()) return false;
    for(unsigned i = 0; i < gold.size(); ++i) {
      auto x = gold[i];
      auto y = output[i];

      if(abs(x - y) > 0.001f * max(abs(x), abs(y))) {
        cout << "at " << i << ": " << x << "=/=" << y <<std::endl;
        return false;
      }
    }
    return true;
  };

  // Allocating buffers
  const size_t buf_size = mat.size() * sizeof(Float);
  cl::Buffer mat_dev = OpenCL::alloc( CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
                                      buf_size, static_cast<void*>(mat.data()) );
  cl::Buffer vec_dev = OpenCL::alloc( CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
                                      N*sizeof(Float), static_cast<void*>(vec.data()) );
  cl::Buffer output_dev = OpenCL::alloc( CL_MEM_READ_WRITE, N*sizeof(Float) );

  // multi-threaded exec
  if(threaded) {
    std::mutex m;
    std::condition_variable cv;

    bool done = false;
    bool ready = false;
    std::queue<Run*> ready_queue;

    // compilation thread
    auto compilation_thread = std::thread([&] {
      for (auto &r: all_run) {
        if (r->compile(binary)) {
          std::unique_lock<std::mutex> locker(m);
          ready_queue.push(&*r);
          ready = true;
          cv.notify_one();
        }
      }
    });

    auto execute_thread = std::thread([&] {
      Run *r = nullptr;
      while (!done) {
        {
          std::unique_lock<std::mutex> locker(m);
          while (!ready) cv.wait(locker);
        }

        while (!ready_queue.empty()) {
          {
            std::unique_lock<std::mutex> locker(m);
            r = ready_queue.front();
            ready_queue.pop();
          }
          r->getKernel().setArg(0, mat_dev);
          r->getKernel().setArg(1, vec_dev);
          r->getKernel().setArg(2, output_dev);
          OpenCL::executeRun<Float>(*r, output_dev, N, validate);
        }
      }
    });

    compilation_thread.join();
    done = true;
    cv.notify_one();
    execute_thread.join();
  }
    // single threaded exec
  else {
    for (auto &r: all_run) {
      if (r->compile(binary)) {
        r->getKernel().setArg(0, mat_dev);
        r->getKernel().setArg(1, vec_dev);
        r->getKernel().setArg(2, output_dev);
        OpenCL::executeRun<Float>(*r, output_dev, N, validate);
      }
    }
  }
};

int main(int argc, char *argv[]) {
  OptParser op("Harness for simple matrix-matrix multiply.");

  auto opt_platform = op.addOption<unsigned>({'p', "platform", "OpenCL platform index (default 0).", 0});
  auto opt_device = op.addOption<unsigned>({'d', "device", "OpenCL device index (default 0).", 0});

  auto opt_size = op.addOption<std::size_t>({'s', "size", "Matrix size (default 1024).", 1024});
  auto opt_transpose = op.addOption<bool>({0, "transpose-in", "Transpose the input matrix before computation.", false});
  auto opt_binary = op.addOption<bool>({'b', "binary", "Load programs as binaries instead of compiling OpenCL-C source.", false});
  auto opt_timeout = op.addOption<float>({'t', "timeout", "Timeout to avoid multiple executions (default 100ms).", 100.0f});
  auto opt_double = op.addOption<bool>({0, "double", "Use double precision.", false});
  auto opt_threaded = op.addOption<bool>({'t', "threaded", "Use a separate thread for compilation and execution (default true).", true});
  auto opt_force = op.addOption<bool>({'f', "force", "Override cached cross validation files.", false});
  auto opt_clean = op.addOption<bool>({'c', "clean", "Clean temporary files and exit.", false});
  op.parse(argc, argv);

  using namespace std;

  // Option handling
  const size_t N = opt_size->get();
  File::setSize(opt_size->get());
  OpenCL::timeout = opt_timeout->get();

  // temporary files
  std::string gold_file = "/tmp/apart_mv_gold_" + std::to_string(N);
  std::string mat_file = "/tmp/apart_mv_mat_" + std::to_string(N);
  std::string vec_file = "/tmp/apart_mv_vec_" + std::to_string(N);

  if(opt_clean->get()) {
    std::cout << "Cleaning..." << std::endl;
    for(const auto& file: {gold_file, mat_file, vec_file})
      std::remove(file.data());
    return 0;
  }

  // === Loading CSV file ===
  auto all_run = Csv::init(
      [&](const std::vector<std::string>& values) -> std::shared_ptr<Run> {
        return (opt_double->get() ?
               std::shared_ptr<Run>(new MVRun<double>(values)) :
               std::shared_ptr<Run>(new MVRun<float>(values)));
      });
  if (all_run.size() == 0) return 0;

  // === OpenCL init ===
  OpenCL::init(opt_platform->get(), opt_device->get());

  // run the harness
  if (opt_double->get())
    run_harness<double>(
        all_run, N,
        mat_file, vec_file, gold_file,
        opt_force->get(),
        opt_transpose->get(),
        opt_threaded->get(), opt_binary->get()
    );
  else
    run_harness<float>(
        all_run, N,
        mat_file, vec_file, gold_file,
        opt_force->get(),
        opt_transpose->get(),
        opt_threaded->get(), opt_binary->get()
    );
}

<commit_msg>Removing deadlock in executor<commit_after>// [standard includes]
#include <vector>
#include <set>
#include <queue>
#include <algorithm>
#include <fstream>
#include <sstream>
#include <iostream>
#include <thread>
#include <mutex>
#include <condition_variable>
#include <atomic>
#include <memory>
#include <cstdio>
#include <typeinfo>

// [external includes]
#include <opencl_utils.h>

// [local includes]
#include "options.h"
#include "run.h"

template<typename T>
using Matrix = std::vector<T>;

template<typename T>
struct MVRun : public Run {
  // input matrix size
  std::size_t size;

  // list of additional buffers to allocate
  std::vector<int> extra_buffer_size;
  std::vector<cl::Buffer> extra_args;

  // list of additional local buffers to allocate
  std::vector<int> extra_local_buffer_size;
  std::vector<cl::LocalSpaceArg> extra_local_args;

  /**
   * Deserialize a line from the CSV
   */
  MVRun(const std::vector<std::string>& values) {
    assert(values.size() > 8 && "Bad CSV format");

    // input size
    size = Csv::readInt(values[0]);

    // global NDRange
    glob1 = Csv::readInt(values[1]);
    glob2 = Csv::readInt(values[2]);
    glob3 = Csv::readInt(values[3]);

    // local NDRange
    loc1 = Csv::readInt(values[4]);
    loc2 = Csv::readInt(values[5]);
    loc3 = Csv::readInt(values[6]);

    // source hash
    hash = values[7];
    hash.erase(std::remove_if(std::begin(hash), std::end(hash), isspace), std::end(hash));

    // number of temporary buffers to allocate and their sizes
    auto num_buf = Csv::readInt(values[8]);
    for(unsigned i = 9+3; i < 9+3 + num_buf; ++i) {
      extra_buffer_size.push_back((int)Csv::readInt(values[i]));
    }

    // number of local buffers to allocate and their sizes
    auto num_local = Csv::readInt(values[12+num_buf]);
    for (unsigned i = 13 + (unsigned) num_buf; i < 13 + num_buf + num_local; ++i) {
      extra_local_buffer_size.push_back((int)Csv::readInt(values[i]));
    }
  }

  void setup(cl::Context context) override {
    // Allocate extra buffers
    for(auto &size: extra_buffer_size)
      extra_args.push_back({context, CL_MEM_READ_WRITE, (size_t) size});

    for (auto &size: extra_local_buffer_size)
      extra_local_args.push_back({(size_t) size});

    // Skip the first 3 to compensate for the csv (forgot a drop(3) in scala)
    for(unsigned i = 0; i < extra_args.size(); ++i)
      kernel.setArg(3+i, extra_args[i]);

    for (unsigned i = 0; i < extra_local_args.size(); ++i)
      kernel.setArg((unsigned) extra_args.size() + 3 + i, extra_local_args[i]);

    kernel.setArg((unsigned)extra_local_args.size()+(unsigned)extra_args.size()+3, (int)size);
    kernel.setArg((unsigned)extra_local_args.size()+(unsigned)extra_args.size()+4, (int)size);
  }

  void cleanup() override {
    extra_buffer_size.clear();
    kernel = cl::Kernel();
  }
};

/**
 * FIXME: This is a lazy copy paste of the old main with a template switch for single and double precision
 */
template<typename Float>
void run_harness(
    std::vector<std::shared_ptr<Run>>& all_run,
    const unsigned N,
    const std::string& mat_file,
    const std::string& vec_file,
    const std::string& gold_file,
    const bool force,
    const bool transposeIn,
    const bool threaded,
    const bool binary
)
{
  using namespace std;

  if(binary)
    std::cout << "Using precompiled binaries" << std::endl;
  // Compute input and output
  Matrix<Float> mat(N*N);
  std::vector<Float> vec(N);
  std::vector<Float> gold(N);

  if(File::is_file_exist(gold_file) && File::is_file_exist(mat_file) && File::is_file_exist(vec_file) && !force ) {
    File::load_input(gold, gold_file);
    File::load_input(mat, mat_file);
    File::load_input(vec, vec_file);
  } else {
    for(unsigned y = 0; y < N; ++y) {
      for (unsigned x = 0; x < N; ++x) {
        mat[y * N + x] = (((y * 3 + x * 2) % 10) + 1) * 1.0f;
      }
      vec[y] = (y%10)*0.5f;
    }

    // compute gold
    for (int i=0; i<N; i++) {
      Float Result=0.0;
      for (int j=0; j<N; j++)
        Result+=mat[i*N+j]*vec[j];

      gold[i]=Result;
    }

    if (transposeIn) {
      std::vector<Float> Tmat(N*N);
      for(unsigned y = 0; y < N; ++y)
        for(unsigned x = 0; x < N; ++x)
          Tmat[y*N+x] = mat[x*N+y];
      std::swap(Tmat, mat);
    }

    File::save_input(gold, gold_file);
    File::save_input(mat, mat_file);
    File::save_input(vec, vec_file);
  }

  // validation function
  auto validate = [&](const std::vector<Float> &output) {
    if(gold.size() != output.size()) return false;
    for(unsigned i = 0; i < gold.size(); ++i) {
      auto x = gold[i];
      auto y = output[i];

      if(abs(x - y) > 0.001f * max(abs(x), abs(y))) {
        cout << "at " << i << ": " << x << "=/=" << y <<std::endl;
        return false;
      }
    }
    return true;
  };

  // Allocating buffers
  const size_t buf_size = mat.size() * sizeof(Float);
  cl::Buffer mat_dev = OpenCL::alloc( CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
                                      buf_size, static_cast<void*>(mat.data()) );
  cl::Buffer vec_dev = OpenCL::alloc( CL_MEM_READ_ONLY | CL_MEM_COPY_HOST_PTR,
                                      N*sizeof(Float), static_cast<void*>(vec.data()) );
  cl::Buffer output_dev = OpenCL::alloc( CL_MEM_READ_WRITE, N*sizeof(Float) );

  // multi-threaded exec
  if(threaded) {
    std::mutex m;
    std::condition_variable cv;

    bool done = false;
    bool ready = false;
    std::queue<Run*> ready_queue;

    // compilation thread
    auto compilation_thread = std::thread([&] {
      for (auto &r: all_run) {
        if (r->compile(binary)) {
          std::unique_lock<std::mutex> locker(m);
          ready_queue.push(&*r);
          ready = true;
          cv.notify_one();
        }
      }
    });

    auto execute_thread = std::thread([&] {
      Run *r = nullptr;
      while (!done) {
        {
          std::unique_lock<std::mutex> locker(m);
          while (!ready && !done) cv.wait(locker);
        }

        while (!ready_queue.empty()) {
          {
            std::unique_lock<std::mutex> locker(m);
            r = ready_queue.front();
            ready_queue.pop();
          }
          r->getKernel().setArg(0, mat_dev);
          r->getKernel().setArg(1, vec_dev);
          r->getKernel().setArg(2, output_dev);
          OpenCL::executeRun<Float>(*r, output_dev, N, validate);
        }
      }
    });

    compilation_thread.join();
    done = true;
    cv.notify_one();
    execute_thread.join();
  }
    // single threaded exec
  else {
    for (auto &r: all_run) {
      if (r->compile(binary)) {
        r->getKernel().setArg(0, mat_dev);
        r->getKernel().setArg(1, vec_dev);
        r->getKernel().setArg(2, output_dev);
        OpenCL::executeRun<Float>(*r, output_dev, N, validate);
      }
    }
  }
};

int main(int argc, char *argv[]) {
  OptParser op("Harness for simple matrix-matrix multiply.");

  auto opt_platform = op.addOption<unsigned>({'p', "platform", "OpenCL platform index (default 0).", 0});
  auto opt_device = op.addOption<unsigned>({'d', "device", "OpenCL device index (default 0).", 0});

  auto opt_size = op.addOption<std::size_t>({'s', "size", "Matrix size (default 1024).", 1024});
  auto opt_transpose = op.addOption<bool>({0, "transpose-in", "Transpose the input matrix before computation.", false});
  auto opt_binary = op.addOption<bool>({'b', "binary", "Load programs as binaries instead of compiling OpenCL-C source.", false});
  auto opt_timeout = op.addOption<float>({'t', "timeout", "Timeout to avoid multiple executions (default 100ms).", 100.0f});
  auto opt_double = op.addOption<bool>({0, "double", "Use double precision.", false});
  auto opt_threaded = op.addOption<bool>({'t', "threaded", "Use a separate thread for compilation and execution (default true).", true});
  auto opt_force = op.addOption<bool>({'f', "force", "Override cached cross validation files.", false});
  auto opt_clean = op.addOption<bool>({'c', "clean", "Clean temporary files and exit.", false});
  op.parse(argc, argv);

  using namespace std;

  // Option handling
  const size_t N = opt_size->get();
  File::setSize(opt_size->get());
  OpenCL::timeout = opt_timeout->get();

  // temporary files
  std::string gold_file = "/tmp/apart_mv_gold_" + std::to_string(N);
  std::string mat_file = "/tmp/apart_mv_mat_" + std::to_string(N);
  std::string vec_file = "/tmp/apart_mv_vec_" + std::to_string(N);

  if(opt_clean->get()) {
    std::cout << "Cleaning..." << std::endl;
    for(const auto& file: {gold_file, mat_file, vec_file})
      std::remove(file.data());
    return 0;
  }

  // === Loading CSV file ===
  auto all_run = Csv::init(
      [&](const std::vector<std::string>& values) -> std::shared_ptr<Run> {
        return (opt_double->get() ?
               std::shared_ptr<Run>(new MVRun<double>(values)) :
               std::shared_ptr<Run>(new MVRun<float>(values)));
      });
  if (all_run.size() == 0) return 0;

  // === OpenCL init ===
  OpenCL::init(opt_platform->get(), opt_device->get());

  // run the harness
  if (opt_double->get())
    run_harness<double>(
        all_run, N,
        mat_file, vec_file, gold_file,
        opt_force->get(),
        opt_transpose->get(),
        opt_threaded->get(), opt_binary->get()
    );
  else
    run_harness<float>(
        all_run, N,
        mat_file, vec_file, gold_file,
        opt_force->get(),
        opt_transpose->get(),
        opt_threaded->get(), opt_binary->get()
    );
}

<|endoftext|>


<commit_before>/* GNE - Game Networking Engine, a portable multithreaded networking library.
 * Copyright (C) 2001 Jason Winnebeck (gillius@mail.rit.edu)
 * Project website: http://www.rit.edu/~jpw9607/
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library 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
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

#include "../include/gnelib/gneintern.h"
#include "../include/gnelib/ServerConnection.h"
#include "../include/gnelib/ConnectionListener.h"
#include "../include/gnelib/Connection.h"
#include "../include/gnelib/SyncConnection.h"
#include "../include/gnelib/ServerConnectionListener.h"
#include "../include/gnelib/Address.h"
#include "../include/gnelib/EventThread.h"
#include "../include/gnelib/RawPacket.h"
#include "../include/gnelib/Error.h"
#include "../include/gnelib/SocketPair.h"
#include "../include/gnelib/GNE.h"

namespace GNE {

/**
 * Simply just a class to temporarily hold connection parameters until the
 * ClientConnection is connected, then it is useless.
 */
//##ModelId=3C5CED05010A
class ServerConnectionParams {
public:
  //##ModelId=3C5CED0502EB
  int outRate;
  //##ModelId=3C5CED0502EC
  int inRate;
  //##ModelId=3C65C6D000F9
  ServerConnectionListener* creator;
  //##ModelId=3C5CED0502F2
  bool unrel;
  //##ModelId=3C7059BF0112
  bool doJoin;
};

//##ModelId=3B075381027A
ServerConnection::ServerConnection(int outRate, int inRate,
                                   ConnectionListener* listener,
                                   NLsocket rsocket2,
                                   ServerConnectionListener* creator)
: Connection(listener), Thread("SrvrConn") {
  gnedbgo(5, "created");
  sockets.r = rsocket2;
  params = new ServerConnectionParams;
  params->outRate = outRate;
  params->inRate = inRate;
  params->creator = creator;
  params->doJoin = true;
}

//##ModelId=3B075381027E
ServerConnection::~ServerConnection() {
  //If this is the current thread, we did a detach(true) because we failed
  //before onNewConn.  Else this is another thread (likely our event thread)
  //and therefore we call join to wait for run to complete if it is still
  //running (as it would be if an error occured after onNewConn but before
  //run finished), and join will also release thread resources.
  //We have to rely on params because Thread::currentThread is not valid in
  //the dtor when we do detach(true).  When an error occurs, params was not
  //deleted, so if it was deleted we know we did not call detach(true) because
  //we did not catch an error.
  if (params == NULL)
    join();
  delete params;
  gnedbgo(5, "destroyed");
}

//##ModelId=3B0753810280
void ServerConnection::run() {
  assert(sockets.r != NL_INVALID);
  assert(eventListener != NULL);
  gnedbgo1(1, "New connection incoming from %s", getRemoteAddress(true).toString().c_str());

  //Do the GNE protocol handshake.
  try {
    doHandshake();
  } catch (Error e) {
    params->creator->onListenFailure(e, getRemoteAddress(true), getListener());
    //We delete ourselves when we terminate since we were never seen by the
    //user and no one has seen us yet.
    detach(true);
    return;
  }
  gnedbgo(4, "GNE Protocol Handshake Successful.");

  //Start up the connecting SyncConnection and start the onNewConn event.
  bool onNewConnFinished = false;
  SyncConnection sConn(this);
  try {
    sConn.startConnect();
    ps->start();
    connecting = true;
    eventListener->start();
    reg(true, (sockets.u != NL_INVALID));

    gnedbgo2(2, "Starting onNewConn r: %i, u: %i", sockets.r, sockets.u);
    getListener()->onNewConn(sConn); //SyncConnection will relay this
    onNewConnFinished = true;
    finishedConnecting();

    //Start bringing connection to normal state.  SyncConnection will make
    //sure onDisconnect gets called starting with endConnect().
    sConn.endConnect(true);
    sConn.release();
  } catch (Error e) {
    if (!onNewConnFinished) {
      sConn.endConnect(false);
      params->creator->onListenFailure(e, getRemoteAddress(true), getListener());
      //We delete ourselves when we terminate since we were never seen by the
      //user and no one has seen us yet.
      detach(true);
      return;
    }
  }

  //If there were no errors, we delete our connection params:
  delete params;
  params = NULL;
}

//##ModelId=3C783ACF02BE
void ServerConnection::doHandshake() throw (Error) {
  //Receive the client's CRP.
  gnedbgo(4, "Waiting for the client's CRP.");
  try {
    getCRP();
  } catch (Error e) {
    if (e.getCode() == Error::GNETheirVersionHigh ||
      e.getCode() == Error::GNETheirVersionLow ||
      e.getCode() == Error::UserVersionMismatch) {
      gnedbgo(4, "Versions don't match, sending refusal.");
      sendRefusal();
    }
    throw;
  }

  //Else, we send the CAP
  gnedbgo(4, "Got CRP, now sending CAP.");
  sendCAP();

  //Then we handle anything related to the unreliable connection if needed.
  if (params->unrel) {
    gnedbgo(4, "Unreliable requested.  Getting unrel info.");
    getUnreliableInfo();
  } else {
    gnedbgo(4, "Unreliable connection not requested.");
  }
}

const int CRPLEN = sizeof(guint8) + sizeof(guint8) + sizeof(guint16) +
                   sizeof(guint32) + sizeof(guint32) + sizeof(gbool);

//##ModelId=3C5CED0502CD
void ServerConnection::getCRP() throw (Error) {
  gbyte* crpBuf = new gbyte[RawPacket::RAW_PACKET_LEN];
  int check = sockets.rawRead(true, crpBuf, RawPacket::RAW_PACKET_LEN);
  if (check != CRPLEN) {
    delete[] crpBuf;
    if (check == NL_INVALID) {
      gnedbgo(1, "nlRead error when trying to get CRP.");
      throw Error::createLowLevelError(Error::Read);
    } else {
      gnedbgo2(1, "Protocol violation trying to get CRP.  Got %d bytes expected %d",
        check, CRPLEN);
      throw Error::createLowLevelError(Error::ProtocolViolation);
    }
  }

  //Now parse the CRP
  RawPacket crp(crpBuf);

  //Get the version numbers
  GNEProtocolVersionNumber them;
  crp >> them.version >> them.subVersion >> them.build;

  guint32 themUser;
  crp >> themUser;

  guint32 maxOutRate;
  crp >> maxOutRate;

  gbool unreliable;
  crp >> unreliable;
  params->unrel = (unreliable != 0);

  //We are done with the CRP packet
  delete[] crpBuf;

  //This will throw an Error of the versions are wrong.
  GNE::checkVersions(them, themUser);

  //Now that we know the versions are OK, make the PacketStream
  ps = new PacketStream(params->outRate, maxOutRate, *this);
}

//##ModelId=3C5CED0502CE
void ServerConnection::sendRefusal() {
  GNEProtocolVersionNumber us = GNE::getGNEProtocolVersion();
  RawPacket ref;
  ref << gFalse;
  ref << us.version << us.subVersion << us.build;
  ref << GNE::getUserVersion();

  sockets.rawWrite(true, ref.getData(), (NLint)ref.getPosition());
  //We don't check for error because if there we don't really care since we
  //are refusing the connection and there is nothing else we can do.
}

//##ModelId=3C5CED0502D7
void ServerConnection::sendCAP() throw (Error) {
  RawPacket cap;
  cap << gTrue;
  cap << params->inRate;
  if (params->unrel) {
    //If the client requested it, open an unreliable port and send the port
    //number to the client.
    sockets.u = nlOpen(0, NL_UNRELIABLE);
    cap << (guint16)(sockets.getLocalAddress(false).getPort());
  }

  int check = sockets.rawWrite(true, cap.getData(), (NLint)cap.getPosition());
  //The write should succeed and have sent all of our data.
  if (check != cap.getPosition())
    throw Error::createLowLevelError(Error::Write);
}

//##ModelId=3C5CED0502D8
void ServerConnection::getUnreliableInfo() throw (Error) {
  gbyte* buf = new gbyte[RawPacket::RAW_PACKET_LEN];
  int check = sockets.rawRead(true, buf, RawPacket::RAW_PACKET_LEN);
  if (check != sizeof(guint16)) {
    delete[] buf;
    if (check == NL_INVALID) {
      gnedbgo(1, "nlRead error when trying to get unreliable info.");
      throw Error::createLowLevelError(Error::Read);
    } else {
      gnedbgo2(1, "Protocol violation trying to get unrel info.  Got %d bytes expected %d",
        check, sizeof(guint16));
      throw Error(Error::ProtocolViolation);
    }
  }

  RawPacket raw(buf);
  guint16 portNum;
  raw >> portNum;

  Address uDest = sockets.getRemoteAddress(true);
  uDest.setPort((int)portNum);
  nlSetRemoteAddr(sockets.u, &uDest.getAddress());

  delete[] buf;
}

}
<commit_msg>Mingw compile fix.<commit_after>/* GNE - Game Networking Engine, a portable multithreaded networking library.
 * Copyright (C) 2001 Jason Winnebeck (gillius@mail.rit.edu)
 * Project website: http://www.rit.edu/~jpw9607/
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library 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
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

#include "../include/gnelib/gneintern.h"
#include "../include/gnelib/ServerConnection.h"
#include "../include/gnelib/ConnectionListener.h"
#include "../include/gnelib/Connection.h"
#include "../include/gnelib/SyncConnection.h"
#include "../include/gnelib/ServerConnectionListener.h"
#include "../include/gnelib/Address.h"
#include "../include/gnelib/EventThread.h"
#include "../include/gnelib/RawPacket.h"
#include "../include/gnelib/Error.h"
#include "../include/gnelib/SocketPair.h"
#include "../include/gnelib/GNE.h"

namespace GNE {

/**
 * Simply just a class to temporarily hold connection parameters until the
 * ClientConnection is connected, then it is useless.
 */
//##ModelId=3C5CED05010A
class ServerConnectionParams {
public:
  //##ModelId=3C5CED0502EB
  int outRate;
  //##ModelId=3C5CED0502EC
  int inRate;
  //##ModelId=3C65C6D000F9
  ServerConnectionListener* creator;
  //##ModelId=3C5CED0502F2
  bool unrel;
  //##ModelId=3C7059BF0112
  bool doJoin;
};

//##ModelId=3B075381027A
ServerConnection::ServerConnection(int outRate, int inRate,
                                   ConnectionListener* listener,
                                   NLsocket rsocket2,
                                   ServerConnectionListener* creator)
: Connection(listener), Thread("SrvrConn") {
  gnedbgo(5, "created");
  sockets.r = rsocket2;
  params = new ServerConnectionParams;
  params->outRate = outRate;
  params->inRate = inRate;
  params->creator = creator;
  params->doJoin = true;
}

//##ModelId=3B075381027E
ServerConnection::~ServerConnection() {
  //If this is the current thread, we did a detach(true) because we failed
  //before onNewConn.  Else this is another thread (likely our event thread)
  //and therefore we call join to wait for run to complete if it is still
  //running (as it would be if an error occured after onNewConn but before
  //run finished), and join will also release thread resources.
  //We have to rely on params because Thread::currentThread is not valid in
  //the dtor when we do detach(true).  When an error occurs, params was not
  //deleted, so if it was deleted we know we did not call detach(true) because
  //we did not catch an error.
  if (params == NULL)
    join();
  delete params;
  gnedbgo(5, "destroyed");
}

//##ModelId=3B0753810280
void ServerConnection::run() {
  assert(sockets.r != NL_INVALID);
  assert(eventListener != NULL);
  gnedbgo1(1, "New connection incoming from %s", getRemoteAddress(true).toString().c_str());

  //Do the GNE protocol handshake.
  try {
    doHandshake();
  } catch (Error e) {
    params->creator->onListenFailure(e, getRemoteAddress(true), getListener());
    //We delete ourselves when we terminate since we were never seen by the
    //user and no one has seen us yet.
    detach(true);
    return;
  }
  gnedbgo(4, "GNE Protocol Handshake Successful.");

  //Start up the connecting SyncConnection and start the onNewConn event.
  bool onNewConnFinished = false;
  SyncConnection sConn(this);
  try {
    sConn.startConnect();
    ps->start();
    connecting = true;
    eventListener->start();
    reg(true, (sockets.u != NL_INVALID));

    gnedbgo2(2, "Starting onNewConn r: %i, u: %i", sockets.r, sockets.u);
    getListener()->onNewConn(sConn); //SyncConnection will relay this
    onNewConnFinished = true;
    finishedConnecting();

    //Start bringing connection to normal state.  SyncConnection will make
    //sure onDisconnect gets called starting with endConnect().
    sConn.endConnect(true);
    sConn.release();
  } catch (Error e) {
    if (!onNewConnFinished) {
      sConn.endConnect(false);
      params->creator->onListenFailure(e, getRemoteAddress(true), getListener());
      //We delete ourselves when we terminate since we were never seen by the
      //user and no one has seen us yet.
      detach(true);
      return;
    }
  }

  //If there were no errors, we delete our connection params:
  delete params;
  params = NULL;
}

//##ModelId=3C783ACF02BE
void ServerConnection::doHandshake() throw (Error) {
  //Receive the client's CRP.
  gnedbgo(4, "Waiting for the client's CRP.");
  try {
    getCRP();
  } catch (Error e) {
    if (e.getCode() == Error::GNETheirVersionHigh ||
      e.getCode() == Error::GNETheirVersionLow ||
      e.getCode() == Error::UserVersionMismatch) {
      gnedbgo(4, "Versions don't match, sending refusal.");
      sendRefusal();
    }
    throw;
  }

  //Else, we send the CAP
  gnedbgo(4, "Got CRP, now sending CAP.");
  sendCAP();

  //Then we handle anything related to the unreliable connection if needed.
  if (params->unrel) {
    gnedbgo(4, "Unreliable requested.  Getting unrel info.");
    getUnreliableInfo();
  } else {
    gnedbgo(4, "Unreliable connection not requested.");
  }
}

const int CRPLEN = sizeof(guint8) + sizeof(guint8) + sizeof(guint16) +
                   sizeof(guint32) + sizeof(guint32) + sizeof(gbool);

//##ModelId=3C5CED0502CD
void ServerConnection::getCRP() throw (Error) {
  gbyte* crpBuf = new gbyte[RawPacket::RAW_PACKET_LEN];
  int check = sockets.rawRead(true, crpBuf, RawPacket::RAW_PACKET_LEN);
  if (check != CRPLEN) {
    delete[] crpBuf;
    if (check == NL_INVALID) {
      gnedbgo(1, "nlRead error when trying to get CRP.");
      throw Error::createLowLevelError(Error::Read);
    } else {
      gnedbgo2(1, "Protocol violation trying to get CRP.  Got %d bytes expected %d",
        check, CRPLEN);
      throw Error::createLowLevelError(Error::ProtocolViolation);
    }
  }

  //Now parse the CRP
  RawPacket crp(crpBuf);

  //Get the version numbers
  GNEProtocolVersionNumber them;
  crp >> them.version >> them.subVersion >> them.build;

  guint32 themUser;
  crp >> themUser;

  guint32 maxOutRate;
  crp >> maxOutRate;

  gbool unreliable;
  crp >> unreliable;
  params->unrel = (unreliable != 0);

  //We are done with the CRP packet
  delete[] crpBuf;

  //This will throw an Error of the versions are wrong.
  GNE::checkVersions(them, themUser);

  //Now that we know the versions are OK, make the PacketStream
  ps = new PacketStream(params->outRate, maxOutRate, *this);
}

//##ModelId=3C5CED0502CE
void ServerConnection::sendRefusal() {
  GNEProtocolVersionNumber us = GNE::getGNEProtocolVersion();
  RawPacket ref;
  ref << gFalse;
  ref << us.version << us.subVersion << us.build;
  ref << GNE::getUserVersion();

  sockets.rawWrite(true, ref.getData(), (NLint)ref.getPosition());
  //We don't check for error because if there we don't really care since we
  //are refusing the connection and there is nothing else we can do.
}

//##ModelId=3C5CED0502D7
void ServerConnection::sendCAP() throw (Error) {
  RawPacket cap;
  cap << gTrue;
  cap << params->inRate;
  if (params->unrel) {
    //If the client requested it, open an unreliable port and send the port
    //number to the client.
    sockets.u = nlOpen(0, NL_UNRELIABLE);
    cap << (guint16)(sockets.getLocalAddress(false).getPort());
  }

  int check = sockets.rawWrite(true, cap.getData(), (NLint)cap.getPosition());
  //The write should succeed and have sent all of our data.
  if (check != cap.getPosition())
    throw Error::createLowLevelError(Error::Write);
}

//##ModelId=3C5CED0502D8
void ServerConnection::getUnreliableInfo() throw (Error) {
  gbyte* buf = new gbyte[RawPacket::RAW_PACKET_LEN];
  int check = sockets.rawRead(true, buf, RawPacket::RAW_PACKET_LEN);
  if (check != sizeof(guint16)) {
    delete[] buf;
    if (check == NL_INVALID) {
      gnedbgo(1, "nlRead error when trying to get unreliable info.");
      throw Error::createLowLevelError(Error::Read);
    } else {
      gnedbgo2(1, "Protocol violation trying to get unrel info.  Got %d bytes expected %d",
        check, sizeof(guint16));
      throw Error(Error::ProtocolViolation);
    }
  }

  RawPacket raw(buf);
  guint16 portNum;
  raw >> portNum;

  Address uDest = sockets.getRemoteAddress(true);
  uDest.setPort((int)portNum);
  NLaddress temp = uDest.getAddress();
  nlSetRemoteAddr(sockets.u, &temp);

  delete[] buf;
}

}
<|endoftext|>


<commit_before>/*
 * The Apache Software License, Version 1.1
 *
 * Copyright (c) 1999-2000 The Apache Software Foundation.  All rights
 * reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *
 * 3. The end-user documentation included with the redistribution,
 *    if any, must include the following acknowledgment:
 *       "This product includes software developed by the
 *        Apache Software Foundation (http://www.apache.org/)."
 *    Alternately, this acknowledgment may appear in the software itself,
 *    if and wherever such third-party acknowledgments normally appear.
 *
 * 4. The names "Xerces" and "Apache Software Foundation" must
 *    not be used to endorse or promote products derived from this
 *    software without prior written permission. For written
 *    permission, please contact apache\@apache.org.
 *
 * 5. Products derived from this software may not be called "Apache",
 *    nor may "Apache" appear in their name, without prior written
 *    permission of the Apache Software Foundation.
 *
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 * SUCH DAMAGE.
 * ====================================================================
 *
 * This software consists of voluntary contributions made by many
 * individuals on behalf of the Apache Software Foundation, and was
 * originally based on software copyright (c) 1999, International
 * Business Machines, Inc., http://www.ibm.com .  For more information
 * on the Apache Software Foundation, please see
 * <http://www.apache.org/>.
 */

/*
 * $Log$
 * Revision 1.1  2002/02/01 22:22:21  peiyongz
 * Initial revision
 *
 * Revision 1.5  2000/03/28 19:43:21  roddey
 * Fixes for signed/unsigned warnings. New work for two way transcoding
 * stuff.
 *
 * Revision 1.4  2000/03/02 19:55:15  roddey
 * This checkin includes many changes done while waiting for the
 * 1.1.0 code to be finished. I can't list them all here, but a list is
 * available elsewhere.
 *
 * Revision 1.3  2000/02/06 07:48:22  rahulj
 * Year 2K copyright swat.
 *
 * Revision 1.2  1999/12/03 00:48:47  rahulj
 * Removed byteswapping logic as its not needed for InMemory message loading.
 *
 * Revision 1.1.1.1  1999/11/09 01:07:19  twl
 * Initial checkin
 *
 * Revision 1.4  1999/11/08 20:45:26  rahul
 * Swat for adding in Product name and CVS comment log variable.
 *
 */

// ---------------------------------------------------------------------------
//  Includes
// ---------------------------------------------------------------------------
#include <xercesc/util/XercesDefs.hpp>
#include <xercesc/util/BitOps.hpp>
#include <xercesc/util/PlatformUtils.hpp>
#include <xercesc/util/XMLMsgLoader.hpp>
#include <xercesc/util/XMLString.hpp>
#include <xercesc/util/XMLUni.hpp>
#include "InMemMsgLoader.hpp"
#include "CppErrMsgs_EN_US.hpp"

// ---------------------------------------------------------------------------
//  Public Constructors and Destructor
// ---------------------------------------------------------------------------
InMemMsgLoader::InMemMsgLoader(const XMLCh* const msgDomain) :

    fMsgDomain(0)
{
    fMsgDomain = XMLString::replicate(msgDomain);

    if (XMLString::compareString(fMsgDomain, XMLUni::fgXMLErrDomain)
    &&  XMLString::compareString(fMsgDomain, XMLUni::fgExceptDomain)
    &&  XMLString::compareString(fMsgDomain, XMLUni::fgValidityDomain))
    {
        XMLPlatformUtils::panic(XMLPlatformUtils::Panic_UnknownMsgDomain);
    }
}

InMemMsgLoader::~InMemMsgLoader()
{
    delete [] fMsgDomain;
}

// ---------------------------------------------------------------------------
//  Implementation of the virtual message loader API
// ---------------------------------------------------------------------------
bool InMemMsgLoader::loadMsg(const  XMLMsgLoader::XMLMsgId  msgToLoad
                            ,       XMLCh* const            toFill
                            , const unsigned int            maxChars)
{
    //
    //  Just use the id to map into the correct array of messages. Then
    //  copy that to the caller's buffer.
    //
    //  NOTE:   The source text is in little endian form. So, if we are a
    //          big endian machine, flip them in the process.
    //
    XMLCh* endPtr = toFill + maxChars;
    XMLCh* outPtr = toFill;
    if (!XMLString::compareString(fMsgDomain, XMLUni::fgXMLErrDomain))
    {
        const XMLCh* srcPtr = gXMLErrArray[msgToLoad - 1];
        while (*srcPtr && (outPtr < endPtr))
        {
            *outPtr++ = *srcPtr++;
        }
        *outPtr = 0;
    }
     else if (!XMLString::compareString(fMsgDomain, XMLUni::fgExceptDomain))
    {
        const XMLCh* srcPtr = gXMLExceptArray[msgToLoad - 1];
        while (*srcPtr && (outPtr < endPtr))
        {
            *outPtr++ = *srcPtr++;
        }
        *outPtr = 0;
    }
     else if (!XMLString::compareString(fMsgDomain, XMLUni::fgValidityDomain))
    {
        const XMLCh* srcPtr = gXMLValidityArray[msgToLoad - 1];
        while (*srcPtr && (outPtr < endPtr))
        {
            *outPtr++ = *srcPtr++;
        }
        *outPtr = 0;
    }
     else
    {
        return false;
    }
    return true;
}

bool InMemMsgLoader::loadMsg(const  XMLMsgLoader::XMLMsgId  msgToLoad
                            ,       XMLCh* const            toFill
                            , const unsigned int            maxChars
                            , const XMLCh* const            repText1
                            , const XMLCh* const            repText2
                            , const XMLCh* const            repText3
                            , const XMLCh* const            repText4)
{
    // Call the other version to load up the message
    if (!loadMsg(msgToLoad, toFill, maxChars))
        return false;

    // And do the token replacement
    XMLString::replaceTokens(toFill, maxChars, repText1, repText2, repText3, repText4);
    return true;
}

bool InMemMsgLoader::loadMsg(const  XMLMsgLoader::XMLMsgId  msgToLoad
                            ,       XMLCh* const            toFill
                            , const unsigned int            maxChars
                            , const char* const             repText1
                            , const char* const             repText2
                            , const char* const             repText3
                            , const char* const             repText4)
{
    //
    //  Transcode the provided parameters and call the other version,
    //  which will do the replacement work.
    //
    XMLCh* tmp1 = 0;
    XMLCh* tmp2 = 0;
    XMLCh* tmp3 = 0;
    XMLCh* tmp4 = 0;

    bool bRet = false;
    if (repText1)
        tmp1 = XMLString::transcode(repText1);
    if (repText2)
        tmp2 = XMLString::transcode(repText2);
    if (repText3)
        tmp3 = XMLString::transcode(repText3);
    if (repText4)
        tmp4 = XMLString::transcode(repText4);

    bRet = loadMsg(msgToLoad, toFill, maxChars, tmp1, tmp2, tmp3, tmp4);

    if (tmp1)
        delete [] tmp1;
    if (tmp2)
        delete [] tmp2;
    if (tmp3)
        delete [] tmp3;
    if (tmp4)
        delete [] tmp4;

    return bRet;
}
<commit_msg>Code sharing and Array boundary checking added<commit_after>/*
 * The Apache Software License, Version 1.1
 *
 * Copyright (c) 1999-2000 The Apache Software Foundation.  All rights
 * reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *
 * 3. The end-user documentation included with the redistribution,
 *    if any, must include the following acknowledgment:
 *       "This product includes software developed by the
 *        Apache Software Foundation (http://www.apache.org/)."
 *    Alternately, this acknowledgment may appear in the software itself,
 *    if and wherever such third-party acknowledgments normally appear.
 *
 * 4. The names "Xerces" and "Apache Software Foundation" must
 *    not be used to endorse or promote products derived from this
 *    software without prior written permission. For written
 *    permission, please contact apache\@apache.org.
 *
 * 5. Products derived from this software may not be called "Apache",
 *    nor may "Apache" appear in their name, without prior written
 *    permission of the Apache Software Foundation.
 *
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESSED OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
 * DISCLAIMED.  IN NO EVENT SHALL THE APACHE SOFTWARE FOUNDATION OR
 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
 * SUCH DAMAGE.
 * ====================================================================
 *
 * This software consists of voluntary contributions made by many
 * individuals on behalf of the Apache Software Foundation, and was
 * originally based on software copyright (c) 1999, International
 * Business Machines, Inc., http://www.ibm.com .  For more information
 * on the Apache Software Foundation, please see
 * <http://www.apache.org/>.
 */

/*
 * $Log$
 * Revision 1.2  2002/09/23 22:14:37  peiyongz
 * Code sharing and Array boundary checking added
 *
 * Revision 1.1.1.1  2002/02/01 22:22:21  peiyongz
 * sane_include
 *
 * Revision 1.5  2000/03/28 19:43:21  roddey
 * Fixes for signed/unsigned warnings. New work for two way transcoding
 * stuff.
 *
 * Revision 1.4  2000/03/02 19:55:15  roddey
 * This checkin includes many changes done while waiting for the
 * 1.1.0 code to be finished. I can't list them all here, but a list is
 * available elsewhere.
 *
 * Revision 1.3  2000/02/06 07:48:22  rahulj
 * Year 2K copyright swat.
 *
 * Revision 1.2  1999/12/03 00:48:47  rahulj
 * Removed byteswapping logic as its not needed for InMemory message loading.
 *
 * Revision 1.1.1.1  1999/11/09 01:07:19  twl
 * Initial checkin
 *
 * Revision 1.4  1999/11/08 20:45:26  rahul
 * Swat for adding in Product name and CVS comment log variable.
 *
 */

// ---------------------------------------------------------------------------
//  Includes
// ---------------------------------------------------------------------------
#include <xercesc/util/XercesDefs.hpp>
#include <xercesc/util/BitOps.hpp>
#include <xercesc/util/PlatformUtils.hpp>
#include <xercesc/util/XMLMsgLoader.hpp>
#include <xercesc/util/XMLString.hpp>
#include <xercesc/util/XMLUni.hpp>
#include "InMemMsgLoader.hpp"
#include "CppErrMsgs_EN_US.hpp"

// ---------------------------------------------------------------------------
//  Public Constructors and Destructor
// ---------------------------------------------------------------------------
InMemMsgLoader::InMemMsgLoader(const XMLCh* const msgDomain)
:fMsgDomain(0)
{
    if (XMLString::compareString(msgDomain, XMLUni::fgXMLErrDomain)
    &&  XMLString::compareString(msgDomain, XMLUni::fgExceptDomain)
    &&  XMLString::compareString(msgDomain, XMLUni::fgValidityDomain))
    {
        XMLPlatformUtils::panic(XMLPlatformUtils::Panic_UnknownMsgDomain);
    }

    fMsgDomain = XMLString::replicate(msgDomain);
}

InMemMsgLoader::~InMemMsgLoader()
{
    delete [] fMsgDomain;
}

// ---------------------------------------------------------------------------
//  Implementation of the virtual message loader API
// ---------------------------------------------------------------------------
bool InMemMsgLoader::loadMsg(const  XMLMsgLoader::XMLMsgId  msgToLoad
                            ,       XMLCh* const            toFill
                            , const unsigned int            maxChars)
{
    //
    //  Just use the id to map into the correct array of messages. Then
    //  copy that to the caller's buffer.
    //
    //  NOTE:   The source text is in little endian form. So, if we are a
    //          big endian machine, flip them in the process.
    //
    XMLCh* endPtr = toFill + maxChars;
    XMLCh* outPtr = toFill;
    const XMLCh* srcPtr = 0;

    if (!XMLString::compareString(fMsgDomain, XMLUni::fgXMLErrDomain))
    {
        if ( msgToLoad > gXMLErrArraySize)
            return false;
        else
            srcPtr = gXMLErrArray[msgToLoad - 1];
    }
     else if (!XMLString::compareString(fMsgDomain, XMLUni::fgExceptDomain))
    {
         if ( msgToLoad > gXMLExceptArraySize)
            return false;
         else
             srcPtr = gXMLExceptArray[msgToLoad - 1];
    }
     else if (!XMLString::compareString(fMsgDomain, XMLUni::fgValidityDomain))
    {
         if ( msgToLoad > gXMLValidityArraySize)
            return false;
         else
             srcPtr = gXMLValidityArray[msgToLoad - 1];
    }

     while (*srcPtr && (outPtr < endPtr))
     {
         *outPtr++ = *srcPtr++;
     }
     *outPtr = 0;

     return true;
}

bool InMemMsgLoader::loadMsg(const  XMLMsgLoader::XMLMsgId  msgToLoad
                            ,       XMLCh* const            toFill
                            , const unsigned int            maxChars
                            , const XMLCh* const            repText1
                            , const XMLCh* const            repText2
                            , const XMLCh* const            repText3
                            , const XMLCh* const            repText4)
{
    // Call the other version to load up the message
    if (!loadMsg(msgToLoad, toFill, maxChars))
        return false;

    // And do the token replacement
    XMLString::replaceTokens(toFill, maxChars, repText1, repText2, repText3, repText4);
    return true;
}

bool InMemMsgLoader::loadMsg(const  XMLMsgLoader::XMLMsgId  msgToLoad
                            ,       XMLCh* const            toFill
                            , const unsigned int            maxChars
                            , const char* const             repText1
                            , const char* const             repText2
                            , const char* const             repText3
                            , const char* const             repText4)
{
    //
    //  Transcode the provided parameters and call the other version,
    //  which will do the replacement work.
    //
    XMLCh* tmp1 = 0;
    XMLCh* tmp2 = 0;
    XMLCh* tmp3 = 0;
    XMLCh* tmp4 = 0;

    bool bRet = false;
    if (repText1)
        tmp1 = XMLString::transcode(repText1);
    if (repText2)
        tmp2 = XMLString::transcode(repText2);
    if (repText3)
        tmp3 = XMLString::transcode(repText3);
    if (repText4)
        tmp4 = XMLString::transcode(repText4);

    bRet = loadMsg(msgToLoad, toFill, maxChars, tmp1, tmp2, tmp3, tmp4);

    if (tmp1)
        delete [] tmp1;
    if (tmp2)
        delete [] tmp2;
    if (tmp3)
        delete [] tmp3;
    if (tmp4)
        delete [] tmp4;

    return bRet;
}
<|endoftext|>


<commit_before>//Jordan Cazamias
//9-19-2012

#include <iostream>
#include <string>
#include <sstream>
#include <fstream>
#include <vector>
#include <assert.h>
#include <stdlib.h>

using namespace std;

int main(int argc, char *argv[]) {

	ifstream input;
	stringstream ss;
	const int IGNORE_LINES = 3; //Number of initial lines to ignore

	input.open("test_input.txt");
	if(argc <= 1)
	{
		cerr << "Error: " << argv[0] << " requires one argument" << endl;
		cerr << " <Revision Num>" << endl;
		return 1;
	}

	////cout << "Revision " << argv[1] << endl;

	//Ignore first n lines- they don't hold any useful data
	for(int i = 0; i < IGNORE_LINES; i++)
	{
		string dummy;
		getline(input, dummy);
	}

	vector<string> names;
	vector<float> times;

	//Extract name and execution time from each line
	while(!input.eof())
	{
		string curr_line;
		getline(input, curr_line);
		////cout << curr_line << endl;
		if(curr_line == "")
			continue;

		//Looking for a number that ends with 's'
		int last_s = curr_line.rfind('s');
		//In case 's' is not used in the future
		assert(isdigit(curr_line[last_s - 1])); // Test: s preceded by number

		//Find time string and convert to double
		int num_start = last_s - 1;
		while(isdigit(curr_line[num_start]) || curr_line[num_start] == '.')
			num_start--;
		string timestr = curr_line.substr(num_start+1, last_s - num_start);
		////cout << timestr << endl;
		double time = (double)atof(timestr.substr(0,timestr.size()-1).c_str());
		////cout << time << endl;
		times.push_back(time);
	}

	//Output individual times
	cout << argv[1];
	for(int i = 0; i < times.size(); i++)
		cout << " " << times[i];

	cout << endl;

	return 0;
}
<commit_msg>Small fixes to get_times program<commit_after>//Jordan Cazamias
//9-19-2012

#include <iostream>
#include <string>
#include <sstream>
#include <fstream>
#include <vector>
#include <assert.h>
#include <stdlib.h>

using namespace std;

int main(int argc, char *argv[]) {

	ifstream input;
	stringstream ss;
	const int IGNORE_LINES = 3; //Number of initial lines to ignore

	input.open("temp.txt");
	if(argc <= 1)
	{
		cerr << "Error: " << argv[0] << " requires one argument" << endl;
		cerr << " <Revision Num>" << endl;
		return 1;
	}

	////cout << "Revision " << argv[1] << endl;

	//Ignore first n lines- they don't hold any useful data
	for(int i = 0; i < IGNORE_LINES; i++)
	{
		string dummy;
		getline(input, dummy);
	}

	vector<string> names;
	vector<double> times;

	//Extract name and execution time from each line
	while(!input.eof())
	{
		string curr_line;
		getline(input, curr_line);
		////cout << curr_line << endl;
		if(curr_line == "")
			continue;

		//Looking for a number that ends with 's'
		int last_s = curr_line.rfind('s');
		//In case 's' is not used in the future
		assert(isdigit(curr_line[last_s - 1])); // Test: s preceded by number

		//Find time string and convert to double
		int num_start = last_s - 1;
		while(curr_line[num_start] != ' ')//isdigit(curr_line[num_start]) || curr_line[num_start] == '.')
			num_start--;
		string timestr = curr_line.substr(num_start+1, last_s - num_start);
		////cout << timestr << endl;
		double time = (double)atof(timestr.substr(0,timestr.size()-1).c_str());
		////cout << time << endl;
		times.push_back(time);
	}

	//Output individual times
	cout << argv[1];
	for(int i = 0; i < times.size(); i++)
		cout << " " << times[i];

	cout << endl;

	return 0;
}
<|endoftext|>