<commit_before>#include <znc/main.h>
#include <znc/User.h>
#include <znc/IRCNetwork.h>
#include <znc/Modules.h>
#include <znc/Nick.h>
#include <znc/Chan.h>
#include <znc/IRCSock.h>

#include "twitchtmi.h"
#include "jload.h"

TwitchTMI::~TwitchTMI()
{

}

bool TwitchTMI::OnLoad(const CString& sArgsi, CString& sMessage)
{
	OnBoot();

	if(GetNetwork())
	{
		for(CChan *ch: GetNetwork()->GetChans())
		{
			ch->SetTopic(CString());

			CString chname = ch->GetName().substr(1);
			CThreadPool::Get().addJob(new TwitchTMIJob(this, chname));
		}
	}

	PutIRC("CAP REQ :twitch.tv/membership");

	return true;
}

bool TwitchTMI::OnBoot()
{
	initCurl();

	timer = new TwitchTMIUpdateTimer(this);
	AddTimer(timer);

	return true;
}

void TwitchTMI::OnIRCConnected()
{
	PutIRC("CAP REQ :twitch.tv/membership");
}

CModule::EModRet TwitchTMI::OnUserRaw(CString &sLine)
{
	if(sLine.Left(5).Equals("WHO #"))
		return CModule::HALT;

	if(sLine.Left(5).Equals("AWAY "))
		return CModule::HALT;

	if(sLine.Left(12).Equals("TWITCHCLIENT"))
		return CModule::HALT;

	if(sLine.Left(9).Equals("JTVCLIENT"))
		return CModule::HALT;

	return CModule::CONTINUE;
}

CModule::EModRet TwitchTMI::OnUserJoin(CString& sChannel, CString& sKey)
{
	CString chname = sChannel.substr(1);
	CThreadPool::Get().addJob(new TwitchTMIJob(this, chname));

	return CModule::CONTINUE;
}

CModule::EModRet TwitchTMI::OnPrivMsg(CNick& nick, CString& sMessage)
{
	if(nick.GetNick().Equals("jtv", true))
		return CModule::HALT;

	return CModule::CONTINUE;
}

CModule::EModRet TwitchTMI::OnChanMsg(CNick& nick, CChan& channel, CString& sMessage)
{
	if(nick.GetNick().Equals("jtv", true))
		return CModule::HALT;

	if(sMessage == "FrankerZ" && std::time(nullptr) - lastFrankerZ > 10)
	{
		std::stringstream ss1, ss2;
		CString mynick = GetNetwork()->GetIRCNick().GetNickMask();

		ss1 << "PRIVMSG " << channel.GetName() << " :FrankerZ";
		ss2 << ":" << mynick << " PRIVMSG " << channel.GetName() << " :";

		PutIRC(ss1.str());
		CString s2 = ss2.str();

		CThreadPool::Get().addJob(new GenericJob([]() {}, [this, s2, &channel]()
		{
			PutUser(s2 + "FrankerZ");

			if(!channel.AutoClearChanBuffer() || !GetNetwork()->IsUserOnline() || channel.IsDetached()) {
				channel.AddBuffer(s2+ "{text}", "FrankerZ");
			}
		}));

		lastFrankerZ = std::time(nullptr);
	}

	return CModule::CONTINUE;
}

bool TwitchTMI::OnServerCapAvailable(const CString &sCap)
{
	if(sCap == "twitch.tv/membership")
	{
		CUtils::PrintMessage("TwitchTMI: Requesting twitch.tv/membership cap");
		return true;
	}

	CUtils::PrintMessage(CString("TwitchTMI: Not requesting ") + sCap + " cap");

	return false;
}

TwitchTMIUpdateTimer::TwitchTMIUpdateTimer(TwitchTMI *tmod)
	:CTimer(tmod, 30, 0, "TwitchTMIUpdateTimer", "Downloads Twitch information")
	,mod(tmod)
{
}

void TwitchTMIUpdateTimer::RunJob()
{
	if(!mod->GetNetwork())
		return;

	for(CChan *chan: mod->GetNetwork()->GetChans())
	{
		CString chname = chan->GetName().substr(1);
		CThreadPool::Get().addJob(new TwitchTMIJob(mod, chname));
	}
}

void TwitchTMIJob::runThread()
{
	std::stringstream ss;
	ss << "https://api.twitch.tv/kraken/channels/" << channel;

	CString url = ss.str();

	Json::Value root = getJsonFromUrl(url.c_str(), "Accept: application/vnd.twitchtv.v3+json");

	if(root.isNull())
	{
		return;
	}

	Json::Value &titleVal = root["status"];

	if(!titleVal.isString())
		titleVal = root["title"];

	if(!titleVal.isString())
		return;

	title = titleVal.asString();
}

void TwitchTMIJob::runMain()
{
	if(title.empty())
		return;

	CChan *chan = mod->GetNetwork()->FindChan(CString("#") + channel);

	if(!chan)
		return;

	if(!chan->GetTopic().Equals(title, true))
	{
		chan->SetTopic(title);
		chan->SetTopicOwner("jtv");
		chan->SetTopicDate((unsigned long)time(nullptr));

		std::stringstream ss;
		ss << ":jtv TOPIC #" << channel << " :" << title;

		mod->PutUser(ss.str());
	}
}

template<> void TModInfo<TwitchTMI>(CModInfo &info)
{
	info.SetWikiPage("Twitch");
	info.SetHasArgs(false);
}

NETWORKMODULEDEFS(TwitchTMI, "Twitch IRC helper module")
<commit_msg>Improve title handling<commit_after>#include <znc/main.h>
#include <znc/User.h>
#include <znc/IRCNetwork.h>
#include <znc/Modules.h>
#include <znc/Nick.h>
#include <znc/Chan.h>
#include <znc/IRCSock.h>

#include "twitchtmi.h"
#include "jload.h"

TwitchTMI::~TwitchTMI()
{

}

bool TwitchTMI::OnLoad(const CString& sArgsi, CString& sMessage)
{
	OnBoot();

	if(GetNetwork())
	{
		for(CChan *ch: GetNetwork()->GetChans())
		{
			ch->SetTopic(CString());

			CString chname = ch->GetName().substr(1);
			CThreadPool::Get().addJob(new TwitchTMIJob(this, chname));
		}
	}

	PutIRC("CAP REQ :twitch.tv/membership");

	return true;
}

bool TwitchTMI::OnBoot()
{
	initCurl();

	timer = new TwitchTMIUpdateTimer(this);
	AddTimer(timer);

	return true;
}

void TwitchTMI::OnIRCConnected()
{
	PutIRC("CAP REQ :twitch.tv/membership");
}

CModule::EModRet TwitchTMI::OnUserRaw(CString &sLine)
{
	if(sLine.Left(5).Equals("WHO #"))
		return CModule::HALT;

	if(sLine.Left(5).Equals("AWAY "))
		return CModule::HALT;

	if(sLine.Left(12).Equals("TWITCHCLIENT"))
		return CModule::HALT;

	if(sLine.Left(9).Equals("JTVCLIENT"))
		return CModule::HALT;

	return CModule::CONTINUE;
}

CModule::EModRet TwitchTMI::OnUserJoin(CString& sChannel, CString& sKey)
{
	CString chname = sChannel.substr(1);
	CThreadPool::Get().addJob(new TwitchTMIJob(this, chname));

	return CModule::CONTINUE;
}

CModule::EModRet TwitchTMI::OnPrivMsg(CNick& nick, CString& sMessage)
{
	if(nick.GetNick().Equals("jtv", true))
		return CModule::HALT;

	return CModule::CONTINUE;
}

CModule::EModRet TwitchTMI::OnChanMsg(CNick& nick, CChan& channel, CString& sMessage)
{
	if(nick.GetNick().Equals("jtv", true))
		return CModule::HALT;

	if(sMessage == "FrankerZ" && std::time(nullptr) - lastFrankerZ > 10)
	{
		std::stringstream ss1, ss2;
		CString mynick = GetNetwork()->GetIRCNick().GetNickMask();

		ss1 << "PRIVMSG " << channel.GetName() << " :FrankerZ";
		ss2 << ":" << mynick << " PRIVMSG " << channel.GetName() << " :";

		PutIRC(ss1.str());
		CString s2 = ss2.str();

		CThreadPool::Get().addJob(new GenericJob([]() {}, [this, s2, &channel]()
		{
			PutUser(s2 + "FrankerZ");

			if(!channel.AutoClearChanBuffer() || !GetNetwork()->IsUserOnline() || channel.IsDetached()) {
				channel.AddBuffer(s2+ "{text}", "FrankerZ");
			}
		}));

		lastFrankerZ = std::time(nullptr);
	}

	return CModule::CONTINUE;
}

bool TwitchTMI::OnServerCapAvailable(const CString &sCap)
{
	if(sCap == "twitch.tv/membership")
	{
		CUtils::PrintMessage("TwitchTMI: Requesting twitch.tv/membership cap");
		return true;
	}

	CUtils::PrintMessage(CString("TwitchTMI: Not requesting ") + sCap + " cap");

	return false;
}

TwitchTMIUpdateTimer::TwitchTMIUpdateTimer(TwitchTMI *tmod)
	:CTimer(tmod, 30, 0, "TwitchTMIUpdateTimer", "Downloads Twitch information")
	,mod(tmod)
{
}

void TwitchTMIUpdateTimer::RunJob()
{
	if(!mod->GetNetwork())
		return;

	for(CChan *chan: mod->GetNetwork()->GetChans())
	{
		CString chname = chan->GetName().substr(1);
		CThreadPool::Get().addJob(new TwitchTMIJob(mod, chname));
	}
}

void TwitchTMIJob::runThread()
{
	std::stringstream ss;
	ss << "https://api.twitch.tv/kraken/channels/" << channel;

	CString url = ss.str();

	Json::Value root = getJsonFromUrl(url.c_str(), "Accept: application/vnd.twitchtv.v3+json");

	if(root.isNull())
	{
		return;
	}

	Json::Value &titleVal = root["status"];
	title = CString();

	if(!titleVal.isString())
		titleVal = root["title"];

	if(!titleVal.isString())
		return;

	title = titleVal.asString();
	title.Trim();
}

void TwitchTMIJob::runMain()
{
	if(title.empty())
		return;

	CChan *chan = mod->GetNetwork()->FindChan(CString("#") + channel);

	if(!chan)
		return;

	if(chan->GetTopic() != title)
	{
		chan->SetTopic(title);
		chan->SetTopicOwner("jtv");
		chan->SetTopicDate((unsigned long)time(nullptr));

		std::stringstream ss;
		ss << ":jtv TOPIC #" << channel << " :" << title;

		mod->PutUser(ss.str());
	}
}

template<> void TModInfo<TwitchTMI>(CModInfo &info)
{
	info.SetWikiPage("Twitch");
	info.SetHasArgs(false);
}

NETWORKMODULEDEFS(TwitchTMI, "Twitch IRC helper module")
<|endoftext|>


<commit_before>/*!
  \copyright (c) RDO-Team, 2011
  \file      info.cpp
  \author      (rdo@rk9.bmstu.ru)
  \date      09.04.2011
  \brief
  \indent    4T
*/

// ---------------------------------------------------------------------------- PCH
#include "simulator/compiler/parser/pch.h"
// ----------------------------------------------------------------------- INCLUDES
// ----------------------------------------------------------------------- SYNOPSIS
#include "simulator/runtime/rdo_fuzzy.h"
#include "simulator/compiler/parser/type/info.h"
#include "simulator/compiler/parser/rdo_value.h"
#include "simulator/compiler/parser/rdoparser.h"
// --------------------------------------------------------------------------------

OPEN_RDO_PARSER_NAMESPACE

// --------------------------------------------------------------------------------
// -------------------- TypeInfo
// --------------------------------------------------------------------------------
TypeInfo::TypeInfo(CREF(LPTypeInfo) pTypeInfo)
	: m_pType  (pTypeInfo->m_pType  )
	, m_srcInfo(pTypeInfo->m_srcInfo)
{
	init();
}

TypeInfo::TypeInfo(CREF(LPRDOType) pType, CREF(RDOParserSrcInfo) srcInfo)
	: m_pType  (pType  )
	, m_srcInfo(srcInfo)
{
	init();
}

void TypeInfo::init()
{
	if (m_pType->type())
	{
		if (m_pType->type()->typeID() == rdoRuntime::RDOType::t_enum ||
			 m_pType->type().object_dynamic_cast<rdoRuntime::RDOFuzzyType>())
		{
			RDOParser::s_parser()->insertPreCastType(this);
		}
	}
}

LPTypeInfo TypeInfo::type_cast(CREF(LPTypeInfo) pFrom, CREF(RDOParserSrcInfo) src_info) const
{
	/// @todo TypeInfo    src_info()
	LPRDOType pType = type()->type_cast(pFrom->type(), pFrom->src_info(src_info), this->src_info(src_info), src_info);
	ASSERT(pType);
	LPTypeInfo pTypeInfo = rdo::Factory<TypeInfo>::create(pType, this->src_info(src_info));
	ASSERT(pTypeInfo);
	return pTypeInfo;
}

LPRDOValue TypeInfo::value_cast(CREF(LPRDOValue) pValue) const
{
	return m_pType->value_cast(pValue, m_srcInfo.get(), pValue->src_info());
}

CLOSE_RDO_PARSER_NAMESPACE
<commit_msg> - форматирование<commit_after>/*!
  \copyright (c) RDO-Team, 2011
  \file      info.cpp
  \author      (rdo@rk9.bmstu.ru)
  \date      09.04.2011
  \brief
  \indent    4T
*/

// ---------------------------------------------------------------------------- PCH
#include "simulator/compiler/parser/pch.h"
// ----------------------------------------------------------------------- INCLUDES
// ----------------------------------------------------------------------- SYNOPSIS
#include "simulator/runtime/rdo_fuzzy.h"
#include "simulator/compiler/parser/type/info.h"
#include "simulator/compiler/parser/rdo_value.h"
#include "simulator/compiler/parser/rdoparser.h"
// --------------------------------------------------------------------------------

OPEN_RDO_PARSER_NAMESPACE

// --------------------------------------------------------------------------------
// -------------------- TypeInfo
// --------------------------------------------------------------------------------
TypeInfo::TypeInfo(CREF(LPTypeInfo) pTypeInfo)
	: m_pType  (pTypeInfo->m_pType  )
	, m_srcInfo(pTypeInfo->m_srcInfo)
{
	init();
}

TypeInfo::TypeInfo(CREF(LPRDOType) pType, CREF(RDOParserSrcInfo) srcInfo)
	: m_pType  (pType  )
	, m_srcInfo(srcInfo)
{
	init();
}

void TypeInfo::init()
{
	if (m_pType->type())
	{
		if (m_pType->type()->typeID() == rdoRuntime::RDOType::t_enum ||
		    m_pType->type().object_dynamic_cast<rdoRuntime::RDOFuzzyType>())
		{
			RDOParser::s_parser()->insertPreCastType(this);
		}
	}
}

LPTypeInfo TypeInfo::type_cast(CREF(LPTypeInfo) pFrom, CREF(RDOParserSrcInfo) src_info) const
{
	/// @todo TypeInfo    src_info()
	LPRDOType pType = type()->type_cast(pFrom->type(), pFrom->src_info(src_info), this->src_info(src_info), src_info);
	ASSERT(pType);
	LPTypeInfo pTypeInfo = rdo::Factory<TypeInfo>::create(pType, this->src_info(src_info));
	ASSERT(pTypeInfo);
	return pTypeInfo;
}

LPRDOValue TypeInfo::value_cast(CREF(LPRDOValue) pValue) const
{
	return m_pType->value_cast(pValue, m_srcInfo.get(), pValue->src_info());
}

CLOSE_RDO_PARSER_NAMESPACE
<|endoftext|>


<commit_before>/***************************************************************************
 *  @file       main.cpp
 *  @author     Alan.W
 *  @date       27  Jan 2014
 *  @remark     This code is for the exercises from C++ Primer 5th Edition
 *  @note
 ***************************************************************************/
//!
//! Exercise 15.26:
//! Define the Quote and Bulk_quote copy-control members to do the same job
//! as the synthesized versions. Give them and the other constructors print
//! statements that identify which function is running. Write programs using
//! these classes and predict what objects will be created and destroyed.
//! Compare your predictions with the output and continue experimenting
//! until your predictions are reliably correct.
//!

#include <iostream>
#include <string>

#include "quote.h"
#include "bulk_quote.h"
#include "limit_quote.h"
#include "disc_quote.h"

int main()
{
    Bulk_quote bq1;
    Bulk_quote bq2("ss",2.05,12,0.3);
    bq2 = std::move(bq2);

    return 0;
}
<commit_msg>Update main.cpp<commit_after>//!
//! Exercise 15.26:
//! Define the Quote and Bulk_quote copy control members to do the same job
//! as the synthesized versions. Give them and the other constructors print
//! statements that identify which function is running. Write programs using
//! these classes and predict what objects will be created and destroyed.
//! Compare your predictions with the output and continue experimenting
//! until your predictions are reliably correct.
//!

#include "Quote.h"
#include "Disc_quote.h"
#include "Bulk_quote.h"
#include "Limit_quote.h"
using namespace std;

int main()
{
    Bulk_quote bq1;
    Bulk_quote bq2("ss", 2.05, 12, 0.3);
    bq2=std::move(bq2);
}
<|endoftext|>


<commit_before>// you can use includes, for example:
// #include <algorithm>

// you can write to stdout for debugging purposes, e.g.
// cout << "this is a debug message" << endl;

int solution(vector<int> &A, vector<int> &B) {
    // write your code in C++11
    vector<int> C;
    unsigned int i(0);
    while( i<A.size() ) {
        if( C.empty() ) {
            C.push_back(i);
            i++;
        }
        else {
            if( B[ C.back() ]==1 && B[i]==0 ) {
                if( A[ C.back() ]<A[i] ) {
                    C.pop_back();
                    if( C.empty() )
                        continue;
                }
                else {
                    i++;
                }
            }
            else {
                C.push_back(i);
                i++;
            }
        }
    }
    return C.size();
}
<commit_msg>Update solution.cpp<commit_after>/*
You are given two non-empty zero-indexed arrays A and B consisting of N integers. Arrays A and B represent N voracious fish in a river, ordered downstream along the flow of the river.

The fish are numbered from 0 to N − 1. If P and Q are two fish and P < Q, then fish P is initially upstream of fish Q. Initially, each fish has a unique position.

Fish number P is represented by A[P] and B[P]. Array A contains the sizes of the fish. All its elements are unique. Array B contains the directions of the fish. It contains only 0s and/or 1s, where:

0 represents a fish flowing upstream,
1 represents a fish flowing downstream.
If two fish move in opposite directions and there are no other (living) fish between them, they will eventually meet each other. Then only one fish can stay alive − the larger fish eats the smaller one. More precisely, we say that two fish P and Q meet each other when P < Q, B[P] = 1 and B[Q] = 0, and there are no living fish between them. After they meet:

If A[P] > A[Q] then P eats Q, and P will still be flowing downstream,
If A[Q] > A[P] then Q eats P, and Q will still be flowing upstream.
We assume that all the fish are flowing at the same speed. That is, fish moving in the same direction never meet. The goal is to calculate the number of fish that will stay alive.

For example, consider arrays A and B such that:

  A[0] = 4    B[0] = 0
  A[1] = 3    B[1] = 1
  A[2] = 2    B[2] = 0
  A[3] = 1    B[3] = 0
  A[4] = 5    B[4] = 0
Initially all the fish are alive and all except fish number 1 are moving upstream. Fish number 1 meets fish number 2 and eats it, then it meets fish number 3 and eats it too. Finally, it meets fish number 4 and is eaten by it. The remaining two fish, number 0 and 4, never meet and therefore stay alive.

Write a function:

int solution(vector<int> &A, vector<int> &B);

that, given two non-empty zero-indexed arrays A and B consisting of N integers, returns the number of fish that will stay alive.

For example, given the arrays shown above, the function should return 2, as explained above.

Assume that:

N is an integer within the range [1..100,000];
each element of array A is an integer within the range [0..1,000,000,000];
each element of array B is an integer that can have one of the following values: 0, 1;
the elements of A are all distinct.
Complexity:

expected worst-case time complexity is O(N);
expected worst-case space complexity is O(N), beyond input storage (not counting the storage required for input arguments).
Elements of input arrays can be modified.

Copyright 2009–2015 by Codility Limited. All Rights Reserved. Unauthorized copying, publication or disclosure prohibited.
*/

// you can use includes, for example:
// #include <algorithm>

// you can write to stdout for debugging purposes, e.g.
// cout << "this is a debug message" << endl;

int solution(vector<int> &A, vector<int> &B) {
    // write your code in C++11
    vector<int> C;
    unsigned int i(0);
    while( i<A.size() ) {
        if( C.empty() ) {
            C.push_back(i);
            i++;
        }
        else {
            if( B[ C.back() ]==1 && B[i]==0 ) {
                if( A[ C.back() ]<A[i] ) {
                    C.pop_back();
                    if( C.empty() )
                        continue;
                }
                else {
                    i++;
                }
            }
            else {
                C.push_back(i);
                i++;
            }
        }
    }
    return C.size();
}
<|endoftext|>


<commit_before>//=======================================================================
// Copyright Baptiste Wicht 2013-2016.
// Distributed under the terms of the MIT License.
// (See accompanying file LICENSE or copy at
//  http://www.opensource.org/licenses/MIT)
//=======================================================================

#include "drivers/hpet.hpp"

#include "conc/int_lock.hpp"

#include "acpica.hpp"
#include "virtual_debug.hpp"
#include "logging.hpp"
#include "mmap.hpp"
#include "kernel.hpp" // For suspend_kernel
#include "scheduler.hpp" // For async init
#include "timer.hpp"     // For setting the frequency

#include "drivers/pit.hpp" // For uninstalling it

// TODO Ideally, we should run in periodic mode
// However, I've not been able to make it work (no interrupt are generated)

namespace {

// Offset of the registers inside the hpet memory
constexpr const size_t CAPABILITIES_REGISTER = 0x0;
constexpr const size_t GENERAL_CONFIG_REGISTER = 0x10 / 8;
constexpr const size_t GENERAL_INTERRUPT_REGISTER = 0x20 / 8;
constexpr const size_t MAIN_COUNTER = 0xF0 / 8;

constexpr const size_t GENERAL_CONFIG_ENABLE = 1 << 0;
constexpr const size_t GENERAL_CONFIG_LEGACY = 1 << 1;

constexpr const size_t CAPABILITIES_LEGACY = 1 << 15;
constexpr const size_t CAPABILITIES_64 = 1 << 13;

constexpr const size_t TIMER_CONFIG_ENABLE = 1 << 2;
constexpr const size_t TIMER_CONFIG_PERIODIC = 1 << 3;
constexpr const size_t TIMER_CONFIG_PERIODIC_CAP = 1 << 5;
constexpr const size_t TIMER_CONFIG_64 = 1 << 5;

constexpr const size_t TIMER_FREQUENCY_GOAL = 10000; // 1 tick every 100 microseconds

ACPI_TABLE_HPET* hpet_table;
uint64_t* hpet_map;
volatile uint64_t comparator_update;

uint64_t timer_configuration_reg(uint64_t n){
    return (0x100 + 0x20 * n) / 8;
}

uint64_t timer_comparator_reg(uint64_t n){
    return (0x108 + 0x20 * n) / 8;
}

uint64_t timer_interrupt_reg(uint64_t n){
    return (0x110 + 0x20 * n) / 8;
}

uint64_t read_register(size_t reg){
    return hpet_map[reg];
}

void write_register(size_t reg, uint64_t value){
    hpet_map[reg] = value;
}

void set_register_bits(size_t reg, uint64_t bits){
    write_register(reg, read_register(reg) | bits);
}

void clear_register_bits(size_t reg, uint64_t bits){
    write_register(reg, read_register(reg) & ~bits);
}

void timer_handler(interrupt::syscall_regs*, void*){
    // Clears Tn_INT_STS
    set_register_bits(GENERAL_INTERRUPT_REGISTER, 1 << 0);

    // Sets the next event to fire an IRQ
    write_register(timer_comparator_reg(0), read_register(MAIN_COUNTER) + comparator_update);

    timer::tick();
}

} //End of anonymous namespace

void hpet::init(){
    // HPET needs ACPI
    scheduler::queue_async_init_task(hpet::late_install);
}

bool hpet::install(){
    // For now, we disable HPET on bochs, because it does not work
    // normally
    if(is_bochs_e9()){
        logging::logf(logging::log_level::TRACE, "hpet: Detected bochs, disabling HPET\n");
        return 9;
    }

    // Find the HPET table
    auto status = AcpiGetTable(ACPI_SIG_HPET, 0, reinterpret_cast<ACPI_TABLE_HEADER **>(&hpet_table));
    if (ACPI_FAILURE(status)){
        return false;
    }

    logging::logf(logging::log_level::TRACE, "hpet: Found ACPI HPET table\n");
    logging::logf(logging::log_level::TRACE, "hpet: HPET Address: %h\n", hpet_table->Address.Address);

    hpet_map = static_cast<uint64_t*>(mmap_phys(hpet_table->Address.Address, 1024)); //TODO Check the size

    auto capabilities = read_register(CAPABILITIES_REGISTER);

    logging::logf(logging::log_level::TRACE, "hpet: HPET Capabilities: %B\n", capabilities);

    if(!(capabilities & CAPABILITIES_LEGACY)){
        logging::logf(logging::log_level::TRACE, "hpet: HPET is not able to handle legacy replacement mode\n");
        return false;
    }

    if(!(capabilities & CAPABILITIES_64)){
         logging::logf(logging::log_level::TRACE, "hpet: HPET is not able to handle 64-bit counter\n");
        return false;
    }

    if(!(read_register(timer_configuration_reg(0)) & TIMER_CONFIG_64)){
         logging::logf(logging::log_level::TRACE, "hpet: HPET Timer #0 is not 64-bit\n");
        return false;
    }

    return true;
}

void hpet::late_install(){
    if(hpet::install()){
        logging::logf(logging::log_level::TRACE, "hpet: Late install suceeded\n");

        // Disable interrupts: We should not be interrupted from this point on
        direct_int_lock lock;

        // Disable before configuration
        clear_register_bits(GENERAL_CONFIG_REGISTER, GENERAL_CONFIG_ENABLE);

        // Get the frequency of the main counter

        auto hpet_period = read_register(CAPABILITIES_REGISTER) >> 32;
        auto hpet_frequency = 1000000000000000 / hpet_period;

        uint64_t current_frequency;
        if(hpet_frequency >= TIMER_FREQUENCY_GOAL){
            current_frequency = TIMER_FREQUENCY_GOAL;
        } else {
            current_frequency = hpet_frequency;
        }

        comparator_update = hpet_frequency / current_frequency;

        logging::logf(logging::log_level::TRACE, "hpet: period %u\n", hpet_period);
        logging::logf(logging::log_level::TRACE, "hpet: frequency %uHz\n", hpet_frequency);
        logging::logf(logging::log_level::TRACE, "hpet: IRQ frequency %uHz\n", current_frequency);
        logging::logf(logging::log_level::TRACE, "hpet: Comparator update %u\n", comparator_update);

        // Update the current frequency (this will update the sleeping task as well)
        timer::timer_frequency(current_frequency);

        // Give information about the counter
        timer::counter_fun(hpet::counter);
        timer::counter_frequency(hpet_frequency);

        // Uninstall the PIT driver
        pit::remove();

        // Register the IRQ handler
        if(!interrupt::register_irq_handler(0, timer_handler, nullptr)){
            logging::logf(logging::log_level::ERROR, "Unable to register HPET IRQ handler 0\n");
            // TODO At this point, we should reinstall the PIT driver
            suspend_kernel();
            return;
        }

        // Clear the main counter
        write_register(MAIN_COUNTER, 0);

        // Initialize timer #0
        clear_register_bits(timer_configuration_reg(0), TIMER_CONFIG_PERIODIC);
        set_register_bits(timer_configuration_reg(0), TIMER_CONFIG_ENABLE);
        write_register(timer_comparator_reg(0), comparator_update);

        // Enable HPET in legacy mode
        set_register_bits(GENERAL_CONFIG_REGISTER, GENERAL_CONFIG_LEGACY | GENERAL_CONFIG_ENABLE);
    }
}

uint64_t hpet::counter(){
    return read_register(MAIN_COUNTER);
}
<commit_msg>Fix HPET Bug with mmap memory<commit_after>//=======================================================================
// Copyright Baptiste Wicht 2013-2016.
// Distributed under the terms of the MIT License.
// (See accompanying file LICENSE or copy at
//  http://www.opensource.org/licenses/MIT)
//=======================================================================

#include "drivers/hpet.hpp"

#include "conc/int_lock.hpp"

#include "acpica.hpp"
#include "virtual_debug.hpp"
#include "logging.hpp"
#include "mmap.hpp"
#include "kernel.hpp" // For suspend_kernel
#include "scheduler.hpp" // For async init
#include "timer.hpp"     // For setting the frequency

#include "drivers/pit.hpp" // For uninstalling it

// TODO Ideally, we should run in periodic mode
// However, I've not been able to make it work (no interrupt are generated)

namespace {

// Offset of the registers inside the hpet memory
constexpr const size_t CAPABILITIES_REGISTER = 0x0;
constexpr const size_t GENERAL_CONFIG_REGISTER = 0x10 / 8;
constexpr const size_t GENERAL_INTERRUPT_REGISTER = 0x20 / 8;
constexpr const size_t MAIN_COUNTER = 0xF0 / 8;

constexpr const size_t GENERAL_CONFIG_ENABLE = 1 << 0;
constexpr const size_t GENERAL_CONFIG_LEGACY = 1 << 1;

constexpr const size_t CAPABILITIES_LEGACY = 1 << 15;
constexpr const size_t CAPABILITIES_64 = 1 << 13;

constexpr const size_t TIMER_CONFIG_ENABLE = 1 << 2;
constexpr const size_t TIMER_CONFIG_PERIODIC = 1 << 3;
constexpr const size_t TIMER_CONFIG_PERIODIC_CAP = 1 << 5;
constexpr const size_t TIMER_CONFIG_64 = 1 << 5;

constexpr const size_t TIMER_FREQUENCY_GOAL = 10000; // 1 tick every 100 microseconds

ACPI_TABLE_HPET* hpet_table;
volatile uint64_t* hpet_map;
volatile uint64_t comparator_update;

uint64_t timer_configuration_reg(uint64_t n){
    return (0x100 + 0x20 * n) / 8;
}

uint64_t timer_comparator_reg(uint64_t n){
    return (0x108 + 0x20 * n) / 8;
}

uint64_t timer_interrupt_reg(uint64_t n){
    return (0x110 + 0x20 * n) / 8;
}

uint64_t read_register(size_t reg){
    return hpet_map[reg];
}

void write_register(size_t reg, uint64_t value){
    hpet_map[reg] = value;
}

void set_register_bits(size_t reg, uint64_t bits){
    write_register(reg, read_register(reg) | bits);
}

void clear_register_bits(size_t reg, uint64_t bits){
    write_register(reg, read_register(reg) & ~bits);
}

void timer_handler(interrupt::syscall_regs*, void*){
    // Clears Tn_INT_STS
    set_register_bits(GENERAL_INTERRUPT_REGISTER, 1 << 0);

    // Sets the next event to fire an IRQ
    write_register(timer_comparator_reg(0), read_register(MAIN_COUNTER) + comparator_update);

    timer::tick();
}

} //End of anonymous namespace

void hpet::init(){
    // HPET needs ACPI
    scheduler::queue_async_init_task(hpet::late_install);
}

bool hpet::install(){
    // For now, we disable HPET on bochs, because it does not work
    // normally
    if(is_bochs_e9()){
        logging::logf(logging::log_level::TRACE, "hpet: Detected bochs, disabling HPET\n");
        return 9;
    }

    // Find the HPET table
    auto status = AcpiGetTable(ACPI_SIG_HPET, 0, reinterpret_cast<ACPI_TABLE_HEADER **>(&hpet_table));
    if (ACPI_FAILURE(status)){
        return false;
    }

    logging::logf(logging::log_level::TRACE, "hpet: Found ACPI HPET table\n");
    logging::logf(logging::log_level::TRACE, "hpet: HPET Address: %h\n", hpet_table->Address.Address);

    hpet_map = static_cast<volatile uint64_t*>(mmap_phys(hpet_table->Address.Address, 1024)); //TODO Check the size

    auto capabilities = read_register(CAPABILITIES_REGISTER);

    logging::logf(logging::log_level::TRACE, "hpet: HPET Capabilities: %B\n", capabilities);

    if(!(capabilities & CAPABILITIES_LEGACY)){
        logging::logf(logging::log_level::TRACE, "hpet: HPET is not able to handle legacy replacement mode\n");
        return false;
    }

    if(!(capabilities & CAPABILITIES_64)){
         logging::logf(logging::log_level::TRACE, "hpet: HPET is not able to handle 64-bit counter\n");
        return false;
    }

    if(!(read_register(timer_configuration_reg(0)) & TIMER_CONFIG_64)){
         logging::logf(logging::log_level::TRACE, "hpet: HPET Timer #0 is not 64-bit\n");
        return false;
    }

    return true;
}

void hpet::late_install(){
    if(hpet::install()){
        logging::logf(logging::log_level::TRACE, "hpet: Late install suceeded\n");

        // Disable interrupts: We should not be interrupted from this point on
        direct_int_lock lock;

        // Disable before configuration
        clear_register_bits(GENERAL_CONFIG_REGISTER, GENERAL_CONFIG_ENABLE);

        // Get the frequency of the main counter

        auto hpet_period = read_register(CAPABILITIES_REGISTER) >> 32;
        auto hpet_frequency = 1000000000000000 / hpet_period;

        uint64_t current_frequency;
        if(hpet_frequency >= TIMER_FREQUENCY_GOAL){
            current_frequency = TIMER_FREQUENCY_GOAL;
        } else {
            current_frequency = hpet_frequency;
        }

        comparator_update = hpet_frequency / current_frequency;

        logging::logf(logging::log_level::TRACE, "hpet: period %u\n", hpet_period);
        logging::logf(logging::log_level::TRACE, "hpet: frequency %uHz\n", hpet_frequency);
        logging::logf(logging::log_level::TRACE, "hpet: IRQ frequency %uHz\n", current_frequency);
        logging::logf(logging::log_level::TRACE, "hpet: Comparator update %u\n", comparator_update);

        // Update the current frequency (this will update the sleeping task as well)
        timer::timer_frequency(current_frequency);

        // Give information about the counter
        timer::counter_fun(hpet::counter);
        timer::counter_frequency(hpet_frequency);

        // Uninstall the PIT driver
        pit::remove();

        // Register the IRQ handler
        if(!interrupt::register_irq_handler(0, timer_handler, nullptr)){
            logging::logf(logging::log_level::ERROR, "Unable to register HPET IRQ handler 0\n");
            // TODO At this point, we should reinstall the PIT driver
            suspend_kernel();
            return;
        }

        // Clear the main counter
        write_register(MAIN_COUNTER, 0);

        // Initialize timer #0
        clear_register_bits(timer_configuration_reg(0), TIMER_CONFIG_PERIODIC);
        set_register_bits(timer_configuration_reg(0), TIMER_CONFIG_ENABLE);
        write_register(timer_comparator_reg(0), comparator_update);

        // Enable HPET in legacy mode
        set_register_bits(GENERAL_CONFIG_REGISTER, GENERAL_CONFIG_LEGACY | GENERAL_CONFIG_ENABLE);
    }
}

uint64_t hpet::counter(){
    return read_register(MAIN_COUNTER);
}
<|endoftext|>


<commit_before>#ifndef UTENSOR_TENSOR_H
#define UTENSOR_TENSOR_H

#include <initializer_list>
#include <iostream>
#include <memory>
#include <vector>
#include "stdlib.h"
#include "uTensor_util.hpp"

enum class DType : char {
  uint8,
  int8,
  uint16,
  int32,
  flt,
  dbl,
};

class uTensor {
 public:
  virtual void inFocus(){};
  virtual void deFocus(){};
  virtual ~uTensor() = 0;
};

uTensor::~uTensor() {}
class TensorBase {
 public:
  std::vector<uint32_t> shape;
  void* data;
  uint32_t total_size;
  DType dtype;
  uint16_t ref_count;
  bool allow_runtime_ref_inc;  //to support compile-time ref count

  ~TensorBase() {
    if (data != nullptr) {
      free(data);
      DEBUG("TensorBase memory freed..\r\n");
    }
  }
};

class Tensor : public uTensor {
  virtual void* read(size_t offset, size_t ele) { return nullptr; }
  virtual void* write(size_t offset, size_t ele) { return nullptr; }

 protected:
  std::shared_ptr<TensorBase> s;  // short for states
 public:
  Tensor(void) {}

  // returns how far a given dimension is apart
  size_t getStride(size_t dim_index) {
    unsigned int size_accm = 1;
    for (auto it = s->shape.begin() + dim_index + 1; it != s->shape.end();
         it++) {
      size_accm *= *it;
    }

    return (size_t)size_accm;
  }
  template <class T>
  void init(std::vector<uint32_t>& v) {
    s = std::make_shared<TensorBase>();
    s->total_size = 0;

    for (auto i : v) {
      s->shape.push_back(i);
      if (s->total_size == 0) {
        s->total_size = i;
      } else {
        s->total_size *= i;
      }
    }

    s->data = (void*)malloc(unit_size() * s->total_size);
    if (s->data == NULL)
      ERR_EXIT("ran out of memory for %lu malloc", unit_size() * s->total_size);

    s->ref_count = 0;
    s->allow_runtime_ref_inc = false;
  }

  std::vector<uint32_t> getShape(void) { return s->shape; }

  uint32_t getSize(void) { return s->total_size; }

  virtual uint16_t unit_size(void) { return 0; }

  uint32_t getSize_in_bytes(void) { return s->total_size * unit_size(); }

  // returns the number of dimensions in the tensor
  size_t getDim(void) { return s->shape.size(); }

  template <class T>
  T* read(size_t offset, size_t ele) {
    return (T*)read(offset, ele);
  }

  template <class T>
  T* write(size_t offset, size_t ele) {
    return (const T*)write(offset, ele);
  }

  DType getDType(void) {
    return s->dtype;
  }

  uint16_t incrRef() {
    if(s->allow_runtime_ref_inc) {
      s->ref_count += 1;
    }

    return s->ref_count;
  }

  uint16_t dcrRef() {
    s->ref_count -= 1;
    return s->ref_count;
  }

  uint16_t getRef() {
    return s->ref_count;
  }

  bool is_ref_runtime(void) {
    return s->allow_runtime_ref_inc;
  }

  ~Tensor() {
    s = nullptr;
    DEBUG("Tensor Destructed\r\n");
  }
};

template <class T>
class RamTensor : public Tensor {
  // need deep copy
 public:
  RamTensor() : Tensor() {
    std::vector<uint32_t> v(3, 3);  ///NT: why (3,3)?
    Tensor::init<T>(v);
    cursor = nullptr;
    //dtype = something...
  }

  RamTensor(std::initializer_list<uint32_t> l) : Tensor() {
    std::vector<uint32_t> v;
    for (auto i : l) {
      v.push_back(i);
    }

    Tensor::init<T>(v);
  }

  RamTensor(std::vector<uint32_t>& v) : Tensor() {
    Tensor::init<T>(v);
  }

  // PRE:      l, initization list, specifying the element/dimension
  // POST:     When a degenerative index is supplied, the pointer
  //          lowest specified dimension is returned.
  //          Otherwise, return the pointer to the specific element.
  virtual void* read(size_t offset, size_t ele) override {
    return (void *)((T*)s->data + offset);
  }
  virtual void* write(size_t offset, size_t ele) override {
    return (void*)((T*)s->data + offset);
  }

  /*virtual void* read(std::initializer_list<uint32_t> l) override {
    size_t p_offset = 0;
    signed short current_dim = 0;
    for (auto i : l) {
      p_offset += i * getStride(current_dim);
      current_dim++;
    }

    // printf("p_offset: %d\r\n", p_offset);
    return (void*)((T*)s->data + p_offset);
  }

    T* getPointer(std::vector<uint32_t> v) {
      size_t p_offset = 0;
      signed short current_dim = 0;
      for (auto i : v) {
        p_offset += i * getStride(current_dim);
        current_dim++;
      }

      printf("p_offset: %d\r\n", p_offset);

      return s->data + p_offset;
    }*/
  // virtual void* read(size_t offset, size_t ele) override{};
  virtual uint16_t unit_size(void) override {
    return sizeof(T);
  }
  ~RamTensor() {}

 private:
  T* cursor;
};

template <typename Tin, typename Tout>
Tensor* TensorCast(Tensor* input) {
  Tensor* output = new RamTensor<Tout>(input->getShape());
  Tin* inputPrt = input->read<Tin>(0, 0);
  Tout* outputPrt = output->read<Tout>({});

  for (uint32_t i = 0; i < input->getSize(); i++) {
    outputPrt[i] = static_cast<Tout>(inputPrt[i]);
  }

  return output;
}

template <typename T>
Tensor* TensorConstant(std::vector<uint32_t> shape, T c) {
  Tensor* output = new RamTensor<T>(shape);
  T* outPrt = output->read<T>(0, 0);

  for (uint32_t i = 0; i < output->getSize(); i++) {
    outPrt[i] = c;
  }

  return output;
}

template <typename T>
Tensor* TensorConstant(std::initializer_list<uint32_t> l, T c) {
  std::vector<uint32_t> v;
  for (auto i : l) {
    v.push_back(i);
  }

  return TensorConstant<T>(v, c);
}

//
// permuteIndexTransform trans(inputTensor.getShape(), permute);
//
// Tensor<int> outputTensor(trans.getNewShape());  //of shape {100,40,10,10}
// size_t output_buffer_index = trans[input_buffer_index];

class permuteIndexTransform {
 private:
  std::vector<uint8_t> permute;
  std::vector<uint8_t> depermute;
  Shape in_shape;
  Shape in_stride;
  Shape out_shape;
  Shape out_stride;

  void computeOutputShape(void) {
    out_stride.clear();
    if (in_shape.empty()) ERR_EXIT("input shape not set");
    if (permute.empty() || permute.size() != in_shape.size())
      ERR_EXIT("invalid permute vector");

    for (auto&& curr_axis : permute) {
      out_shape.push_back(in_shape[curr_axis]);
    }
  }

  size_t evalStride(size_t dim_index, Shape s) {
    unsigned int size_accm = 1;
    for (auto it = s.begin() + dim_index + 1; it != s.end(); it++) {
      size_accm *= *it;
    }

    return (size_t)size_accm;
  }

  void computeInputStride(void) {
    in_stride.clear();
    for (uint32_t i = 0; i < in_shape.size(); i++) {
      in_stride.push_back(evalStride(i, in_shape));
    }
  }
  void computeOutputStride(void) {
    out_stride.clear();
    for (uint32_t i = 0; i < out_shape.size(); i++) {
      out_stride.push_back(evalStride(i, out_shape));
    }
  }

 public:
  permuteIndexTransform(Shape input_shape, std::vector<uint8_t> permute) {
    setInputShape(input_shape);
    setPermute(permute);
    apply();
  }

  std::vector<uint8_t> getPermute(void) { return permute; }
  void setPermute(std::vector<uint8_t>& _permute) {
    permute = _permute;
    depermute.resize(permute.size());
    uint8_t i = 0;
    for (auto a : permute) {
      depermute[a] = i;
      i++;
    }
  }

  void setInputShape(Shape s) { in_shape = s; }
  Shape getNewShape(void) { return out_shape; }

  void apply(void) {
    computeOutputShape();
    computeOutputStride();
    computeInputStride();
  }

  size_t operator[](const size_t index) {
    size_t out_index = 0;
    size_t rem = index;

    for (size_t curr_dim = 0; curr_dim < in_shape.size(); curr_dim++) {
      size_t curr_stride = in_stride[curr_dim];
      out_index += (rem / curr_stride) * out_stride[depermute[curr_dim]];
      rem = rem % curr_stride;
    }

    out_index += rem;

    return out_index;
  }
};

template <typename T>
void printDim(Tensor* t) {
  printf("Dimension: ");
  Shape s = t->getShape();
  for (auto d : s) {
    printf("[%lu] ", d);
  }
  printf("\r\n");
}

template <typename T>
void tensorChkAlloc(Tensor* t, Shape dim) {
  if (t->getSize() == 0) {
    t = new RamTensor<T>(dim);
  } else if (t->getShape() != dim) {
    ERR_EXIT("Dim mismatched...\r\n");
  }
}
#endif
<commit_msg>  1. remove unnecessary private member   2. remove temporary function in ramtensor constructor   3. fix constructor parameter type<commit_after>#ifndef UTENSOR_TENSOR_H
#define UTENSOR_TENSOR_H

#include <initializer_list>
#include <iostream>
#include <memory>
#include <vector>
#include "stdlib.h"
#include "uTensor_util.hpp"

enum class DType : char {
  uint8,
  int8,
  uint16,
  int32,
  flt,
  dbl,
};

class uTensor {
 public:
  virtual void inFocus(){};
  virtual void deFocus(){};
  virtual ~uTensor() = 0;
};

uTensor::~uTensor() {}
class TensorBase {
 public:
  std::vector<uint32_t> shape;
  void* data;
  uint32_t total_size;
  DType dtype;
  uint16_t ref_count;
  bool allow_runtime_ref_inc;  //to support compile-time ref count

  ~TensorBase() {
    if (data != nullptr) {
      free(data);
      DEBUG("TensorBase memory freed..\r\n");
    }
  }
};

class Tensor : public uTensor {
  virtual void* read(size_t offset, size_t ele) { return nullptr; }
  virtual void* write(size_t offset, size_t ele) { return nullptr; }

 protected:
  std::shared_ptr<TensorBase> s;  // short for states
 public:
  Tensor(void) {}

  // returns how far a given dimension is apart
  size_t getStride(size_t dim_index) {
    unsigned int size_accm = 1;
    for (auto it = s->shape.begin() + dim_index + 1; it != s->shape.end();
         it++) {
      size_accm *= *it;
    }

    return (size_t)size_accm;
  }
  template <class T>
  void init(std::vector<uint32_t>& v) {
    s = std::make_shared<TensorBase>();
    s->total_size = 0;

    for (auto i : v) {
      s->shape.push_back(i);
      if (s->total_size == 0) {
        s->total_size = i;
      } else {
        s->total_size *= i;
      }
    }

    s->data = (void*)malloc(unit_size() * s->total_size);
    if (s->data == NULL)
      ERR_EXIT("ran out of memory for %lu malloc", unit_size() * s->total_size);

    s->ref_count = 0;
    s->allow_runtime_ref_inc = false;
  }

  std::vector<uint32_t> getShape(void) { return s->shape; }

  uint32_t getSize(void) { return s->total_size; }

  virtual uint16_t unit_size(void) { return 0; }

  uint32_t getSize_in_bytes(void) { return s->total_size * unit_size(); }

  // returns the number of dimensions in the tensor
  size_t getDim(void) { return s->shape.size(); }

  template <class T>
  T* read(size_t offset, size_t ele) {
    return (T*)read(offset, ele);
  }

  template <class T>
  T* write(size_t offset, size_t ele) {
    return (T*)write(offset, ele);
  }

  DType getDType(void) {
    return s->dtype;
  }

  uint16_t incrRef() {
    if(s->allow_runtime_ref_inc) {
      s->ref_count += 1;
    }

    return s->ref_count;
  }

  uint16_t dcrRef() {
    s->ref_count -= 1;
    return s->ref_count;
  }

  uint16_t getRef() {
    return s->ref_count;
  }

  bool is_ref_runtime(void) {
    return s->allow_runtime_ref_inc;
  }

  ~Tensor() {
    s = nullptr;
    DEBUG("Tensor Destructed\r\n");
  }
};

template <class T>
class RamTensor : public Tensor {
  // need deep copy
 public:
  RamTensor() : Tensor() {
    //dtype = something...
  }

  RamTensor(std::initializer_list<uint32_t> l) : Tensor() {
    std::vector<uint32_t> v;
    for (auto i : l) {
      v.push_back(i);
    }

    Tensor::init<T>(v);
  }

  RamTensor(std::vector<uint32_t> v) : Tensor() {
    Tensor::init<T>(v);
  }

  // PRE:      l, initization list, specifying the element/dimension
  // POST:     When a degenerative index is supplied, the pointer
  //          lowest specified dimension is returned.
  //          Otherwise, return the pointer to the specific element.
  virtual void* read(size_t offset, size_t ele) override {
    return (void *)((T*)s->data + offset);
  }
  virtual void* write(size_t offset, size_t ele) override {
    return (void*)((T*)s->data + offset);
  }

  /*virtual void* read(std::initializer_list<uint32_t> l) override {
    size_t p_offset = 0;
    signed short current_dim = 0;
    for (auto i : l) {
      p_offset += i * getStride(current_dim);
      current_dim++;
    }

    // printf("p_offset: %d\r\n", p_offset);
    return (void*)((T*)s->data + p_offset);
  }

    T* getPointer(std::vector<uint32_t> v) {
      size_t p_offset = 0;
      signed short current_dim = 0;
      for (auto i : v) {
        p_offset += i * getStride(current_dim);
        current_dim++;
      }

      printf("p_offset: %d\r\n", p_offset);

      return s->data + p_offset;
    }*/
  // virtual void* read(size_t offset, size_t ele) override{};
  virtual uint16_t unit_size(void) override {
    return sizeof(T);
  }
  ~RamTensor() {}

};

template <typename Tin, typename Tout>
Tensor* TensorCast(Tensor* input) {
  Tensor* output = new RamTensor<Tout>(input->getShape());
  Tin* inputPrt = input->read<Tin>(0, 0);
  Tout* outputPrt = output->read<Tout>({});

  for (uint32_t i = 0; i < input->getSize(); i++) {
    outputPrt[i] = static_cast<Tout>(inputPrt[i]);
  }

  return output;
}

template <typename T>
Tensor* TensorConstant(std::vector<uint32_t> shape, T c) {
  Tensor* output = new RamTensor<T>(shape);
  T* outPrt = output->read<T>(0, 0);

  for (uint32_t i = 0; i < output->getSize(); i++) {
    outPrt[i] = c;
  }

  return output;
}

template <typename T>
Tensor* TensorConstant(std::initializer_list<uint32_t> l, T c) {
  std::vector<uint32_t> v;
  for (auto i : l) {
    v.push_back(i);
  }

  return TensorConstant<T>(v, c);
}

//
// permuteIndexTransform trans(inputTensor.getShape(), permute);
//
// Tensor<int> outputTensor(trans.getNewShape());  //of shape {100,40,10,10}
// size_t output_buffer_index = trans[input_buffer_index];

class permuteIndexTransform {
 private:
  std::vector<uint8_t> permute;
  std::vector<uint8_t> depermute;
  Shape in_shape;
  Shape in_stride;
  Shape out_shape;
  Shape out_stride;

  void computeOutputShape(void) {
    out_stride.clear();
    if (in_shape.empty()) ERR_EXIT("input shape not set");
    if (permute.empty() || permute.size() != in_shape.size())
      ERR_EXIT("invalid permute vector");

    for (auto&& curr_axis : permute) {
      out_shape.push_back(in_shape[curr_axis]);
    }
  }

  size_t evalStride(size_t dim_index, Shape s) {
    unsigned int size_accm = 1;
    for (auto it = s.begin() + dim_index + 1; it != s.end(); it++) {
      size_accm *= *it;
    }

    return (size_t)size_accm;
  }

  void computeInputStride(void) {
    in_stride.clear();
    for (uint32_t i = 0; i < in_shape.size(); i++) {
      in_stride.push_back(evalStride(i, in_shape));
    }
  }
  void computeOutputStride(void) {
    out_stride.clear();
    for (uint32_t i = 0; i < out_shape.size(); i++) {
      out_stride.push_back(evalStride(i, out_shape));
    }
  }

 public:
  permuteIndexTransform(Shape input_shape, std::vector<uint8_t> permute) {
    setInputShape(input_shape);
    setPermute(permute);
    apply();
  }

  std::vector<uint8_t> getPermute(void) { return permute; }
  void setPermute(std::vector<uint8_t>& _permute) {
    permute = _permute;
    depermute.resize(permute.size());
    uint8_t i = 0;
    for (auto a : permute) {
      depermute[a] = i;
      i++;
    }
  }

  void setInputShape(Shape s) { in_shape = s; }
  Shape getNewShape(void) { return out_shape; }

  void apply(void) {
    computeOutputShape();
    computeOutputStride();
    computeInputStride();
  }

  size_t operator[](const size_t index) {
    size_t out_index = 0;
    size_t rem = index;

    for (size_t curr_dim = 0; curr_dim < in_shape.size(); curr_dim++) {
      size_t curr_stride = in_stride[curr_dim];
      out_index += (rem / curr_stride) * out_stride[depermute[curr_dim]];
      rem = rem % curr_stride;
    }

    out_index += rem;

    return out_index;
  }
};

template <typename T>
void printDim(Tensor* t) {
  printf("Dimension: ");
  Shape s = t->getShape();
  for (auto d : s) {
    printf("[%lu] ", d);
  }
  printf("\r\n");
}

template <typename T>
void tensorChkAlloc(Tensor* t, Shape dim) {
  if (t->getSize() == 0) {
    t = new RamTensor<T>(dim);
  } else if (t->getShape() != dim) {
    ERR_EXIT("Dim mismatched...\r\n");
  }
}
#endif
<|endoftext|>


<commit_before>/*=========================================================================

  Library:   CTK

  Copyright (c) 2010  Kitware Inc.

  Licensed under the Apache License, Version 2.0 (the "License");
  you may not use this file except in compliance with the License.
  You may obtain a copy of the License at

      http://www.commontk.org/LICENSE

  Unless required by applicable law or agreed to in writing, software
  distributed under the License is distributed on an "AS IS" BASIS,
  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  See the License for the specific language governing permissions and
  limitations under the License.

=========================================================================*/

/// Qt includes
#include <QColor>
#include <QDebug>
#include <QGraphicsSceneMouseEvent>
#include <QPainter>
#include <QtGlobal>
#include <QVariant>

/// CTK includes
#include "ctkTransferFunction.h"
#include "ctkTransferFunctionBarsItem.h"
#include "ctkTransferFunctionRepresentation.h"
#include "ctkTransferFunctionScene.h"

// std includes
#include <cmath>

//-----------------------------------------------------------------------------
class ctkTransferFunctionBarsItemPrivate: public ctkPrivate<ctkTransferFunctionBarsItem>
{
public:
  ctkTransferFunctionBarsItemPrivate();
  qreal  BarWidth;
  QColor BarColor;
  bool   LogMode;
};

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItemPrivate::ctkTransferFunctionBarsItemPrivate()
{
  this->BarWidth = 0.6180; // golden ratio... why not.
  this->BarColor = QColor(191, 191, 191, 127);
  this->LogMode = ctkTransferFunctionBarsItem::AutoLog;
}

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItem::ctkTransferFunctionBarsItem(QGraphicsItem* parentGraphicsItem)
  :ctkTransferFunctionItem(parentGraphicsItem)
{
  CTK_INIT_PRIVATE(ctkTransferFunctionBarsItem);
}

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItem::ctkTransferFunctionBarsItem(
  ctkTransferFunction* transferFunc, QGraphicsItem* parentItem)
  :ctkTransferFunctionItem(transferFunc, parentItem)
{
  CTK_INIT_PRIVATE(ctkTransferFunctionBarsItem);
}

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItem::~ctkTransferFunctionBarsItem()
{
}

//-----------------------------------------------------------------------------
void ctkTransferFunctionBarsItem::setBarWidth(qreal newBarWidth)
{
  CTK_D(ctkTransferFunctionBarsItem);
  newBarWidth = qBound(0., newBarWidth, 1.);
  if (d->BarWidth == newBarWidth)
    {
    return;
    }
  d->BarWidth = newBarWidth;
  this->update();
}

//-----------------------------------------------------------------------------
qreal ctkTransferFunctionBarsItem::barWidth()const
{
  CTK_D(const ctkTransferFunctionBarsItem);
  return d->BarWidth;
}

//-----------------------------------------------------------------------------
void ctkTransferFunctionBarsItem::setBarColor(const QColor& color)
{
  CTK_D(ctkTransferFunctionBarsItem);
  d->BarColor = color;
}

//-----------------------------------------------------------------------------
QColor ctkTransferFunctionBarsItem::barColor()const
{
  CTK_D(const ctkTransferFunctionBarsItem);
  return d->BarColor;
}

//-----------------------------------------------------------------------------
void ctkTransferFunctionBarsItem::paint(
  QPainter * painter, const QStyleOptionGraphicsItem * option, QWidget * widget)
{
  Q_UNUSED(option);
  Q_UNUSED(widget);
  CTK_D(ctkTransferFunctionBarsItem);
  int count = this->transferFunction() ? this->transferFunction()->count() : 0;
  if (count <= 0)
    {
    return;
    }

  ctkTransferFunctionRepresentation* tfRep = this->transferFunction()->representation();
  //ctkTransferFunctionScene* tfScene = dynamic_cast<ctkTransferFunctionScene*>(this->scene());
  //Q_ASSERT(tfScene);
  //const QList<QPointF>& points = tfScene->points();
  const QList<QPointF>& points = tfRep->points();

  QPainterPath bars;
  QPen pen( QColor(255, 255, 255, 191), 1);
  pen.setCosmetic(true);
  if (qFuzzyCompare(d->BarWidth, 1.))
    {
    pen = QPen(QBrush(), 0, Qt::NoPen);
    }
  painter->setPen(pen);
  painter->setBrush(QBrush(d->BarColor));

  qreal barWidth = d->BarWidth * (this->rect().width() / (points.size() - 1));
  bool useLog = false;
  switch (d->LogMode)
    {
    case ctkTransferFunctionBarsItem::AutoLog:
      useLog = this->transferFunction()->maxValue().toReal() - this->transferFunction()->minValue().toReal() > 1000.;
      break;
    case ctkTransferFunctionBarsItem::UseLog:
      useLog = true;
      break;
    default:
    case ctkTransferFunctionBarsItem::NoLog:
      useLog = false;
    }
  foreach(const QPointF& point, points)
    {
    qreal barHeight = point.y();
    if (useLog && barHeight != 1.)
      {
      //barHeight = this->rect().height() - log( tfScene->mapYFromScene(barHeight) )/log(this->transferFunction()->maxValue().toReal());// 1. - (-log(barHeight)/100.);
      barHeight = this->rect().height() - log( tfRep->mapYFromScene(barHeight) )/log(this->transferFunction()->maxValue().toReal());// 1. - (-log(barHeight)/100.);
      }
    bars.addRect(point.x() - barWidth/2, this->rect().height(),
                 barWidth, barHeight - this->rect().height() );
    }
  painter->drawPath(bars);
}

<commit_msg>COMP: variable LogMode is of type LogMode not bool<commit_after>/*=========================================================================

  Library:   CTK

  Copyright (c) 2010  Kitware Inc.

  Licensed under the Apache License, Version 2.0 (the "License");
  you may not use this file except in compliance with the License.
  You may obtain a copy of the License at

      http://www.commontk.org/LICENSE

  Unless required by applicable law or agreed to in writing, software
  distributed under the License is distributed on an "AS IS" BASIS,
  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  See the License for the specific language governing permissions and
  limitations under the License.

=========================================================================*/

/// Qt includes
#include <QColor>
#include <QDebug>
#include <QGraphicsSceneMouseEvent>
#include <QPainter>
#include <QtGlobal>
#include <QVariant>

/// CTK includes
#include "ctkTransferFunction.h"
#include "ctkTransferFunctionBarsItem.h"
#include "ctkTransferFunctionRepresentation.h"
#include "ctkTransferFunctionScene.h"

// std includes
#include <cmath>

//-----------------------------------------------------------------------------
class ctkTransferFunctionBarsItemPrivate: public ctkPrivate<ctkTransferFunctionBarsItem>
{
public:
  ctkTransferFunctionBarsItemPrivate();
  qreal  BarWidth;
  QColor BarColor;
  ctkTransferFunctionBarsItem::LogMode   LogMode;
};

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItemPrivate::ctkTransferFunctionBarsItemPrivate()
{
  this->BarWidth = 0.6180; // golden ratio... why not.
  this->BarColor = QColor(191, 191, 191, 127);
  this->LogMode = ctkTransferFunctionBarsItem::AutoLog;
}

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItem::ctkTransferFunctionBarsItem(QGraphicsItem* parentGraphicsItem)
  :ctkTransferFunctionItem(parentGraphicsItem)
{
  CTK_INIT_PRIVATE(ctkTransferFunctionBarsItem);
}

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItem::ctkTransferFunctionBarsItem(
  ctkTransferFunction* transferFunc, QGraphicsItem* parentItem)
  :ctkTransferFunctionItem(transferFunc, parentItem)
{
  CTK_INIT_PRIVATE(ctkTransferFunctionBarsItem);
}

//-----------------------------------------------------------------------------
ctkTransferFunctionBarsItem::~ctkTransferFunctionBarsItem()
{
}

//-----------------------------------------------------------------------------
void ctkTransferFunctionBarsItem::setBarWidth(qreal newBarWidth)
{
  CTK_D(ctkTransferFunctionBarsItem);
  newBarWidth = qBound(0., newBarWidth, 1.);
  if (d->BarWidth == newBarWidth)
    {
    return;
    }
  d->BarWidth = newBarWidth;
  this->update();
}

//-----------------------------------------------------------------------------
qreal ctkTransferFunctionBarsItem::barWidth()const
{
  CTK_D(const ctkTransferFunctionBarsItem);
  return d->BarWidth;
}

//-----------------------------------------------------------------------------
void ctkTransferFunctionBarsItem::setBarColor(const QColor& color)
{
  CTK_D(ctkTransferFunctionBarsItem);
  d->BarColor = color;
}

//-----------------------------------------------------------------------------
QColor ctkTransferFunctionBarsItem::barColor()const
{
  CTK_D(const ctkTransferFunctionBarsItem);
  return d->BarColor;
}

//-----------------------------------------------------------------------------
void ctkTransferFunctionBarsItem::paint(
  QPainter * painter, const QStyleOptionGraphicsItem * option, QWidget * widget)
{
  Q_UNUSED(option);
  Q_UNUSED(widget);
  CTK_D(ctkTransferFunctionBarsItem);
  int count = this->transferFunction() ? this->transferFunction()->count() : 0;
  if (count <= 0)
    {
    return;
    }

  ctkTransferFunctionRepresentation* tfRep = this->transferFunction()->representation();
  //ctkTransferFunctionScene* tfScene = dynamic_cast<ctkTransferFunctionScene*>(this->scene());
  //Q_ASSERT(tfScene);
  //const QList<QPointF>& points = tfScene->points();
  const QList<QPointF>& points = tfRep->points();

  QPainterPath bars;
  QPen pen( QColor(255, 255, 255, 191), 1);
  pen.setCosmetic(true);
  if (qFuzzyCompare(d->BarWidth, 1.))
    {
    pen = QPen(QBrush(), 0, Qt::NoPen);
    }
  painter->setPen(pen);
  painter->setBrush(QBrush(d->BarColor));

  qreal barWidth = d->BarWidth * (this->rect().width() / (points.size() - 1));
  bool useLog = false;
  switch (d->LogMode)
    {
    case ctkTransferFunctionBarsItem::AutoLog:
      useLog = this->transferFunction()->maxValue().toReal() - this->transferFunction()->minValue().toReal() > 1000.;
      break;
    case ctkTransferFunctionBarsItem::UseLog:
      useLog = true;
      break;
    default:
    case ctkTransferFunctionBarsItem::NoLog:
      useLog = false;
    }
  foreach(const QPointF& point, points)
    {
    qreal barHeight = point.y();
    if (useLog && barHeight != 1.)
      {
      //barHeight = this->rect().height() - log( tfScene->mapYFromScene(barHeight) )/log(this->transferFunction()->maxValue().toReal());// 1. - (-log(barHeight)/100.);
      barHeight = this->rect().height() - log( tfRep->mapYFromScene(barHeight) )/log(this->transferFunction()->maxValue().toReal());// 1. - (-log(barHeight)/100.);
      }
    bars.addRect(point.x() - barWidth/2, this->rect().height(),
                 barWidth, barHeight - this->rect().height() );
    }
  painter->drawPath(bars);
}

<|endoftext|>


<commit_before><commit_msg>Store the proxy's hostname rather than the first site visited via the proxy when storing proxy passwords. BUG=12992 TEST=none<commit_after><|endoftext|>


<commit_before>//
// job_mon.hh - sjm job monitor
//
// Phil Lacroute
// March 2008
//
// Copyright(c) 2008-2012 The Board of Trustees of The Leland Stanford
// Junior University.  All Rights Reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
//     * Redistributions of source code must retain the above copyright
//       notice, this list of conditions and the following disclaimer.
//
//     * Redistributions in binary form must reproduce the above
//       copyright notice, this list of conditions and the following
//       disclaimer in the documentation and/or other materials provided
//       with the distribution.
//
//     * Neither the name of Stanford University nor the names of its
//       contributors may be used to endorse or promote products derived
//       from this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL STANFORD
// UNIVERSITY 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.
//
// $Id: job_mon.hh 240 2009-03-19 21:51:09Z lacroute $
//

#ifndef JOB_MON_H
#define JOB_MON_H

#include <iostream>
#include <fstream>
#include <vector>
#include <list>
#include <string>
#include <boost/regex.hpp>

#include "job_graph.hh"
#include "batch.hh"

#if defined(HAVE_SGE)
#include "sge.hh"
#elif defined(HAVE_LSF)
#include "lsf.hh"
#endif

using std::ofstream;

class RateLimiter {
public:
    RateLimiter();
    void init(unsigned tokens, unsigned intervalSeconds,
	      unsigned currentTime);
    unsigned updateTime(unsigned currentTime);
    bool transmitOk();
    bool empty();

private:
    unsigned maxTokens_;
    unsigned intervalSeconds_;
    unsigned tokensLeft_;
    unsigned nextIncrementTime_;
};

class JobMonitor {
public:
    typedef enum {
	LogVerbose = 1,
	LogInfo,
	LogWarning,
	LogError,
	LogAlways
    } LogLevel;

    JobMonitor();
    bool submit(const std::string& jobFile, const std::string& outFile,
		const std::string& logFile, bool interactive,
		const std::vector<std::string>& mailAddr);
    bool render(const std::string& jobFile, const std::string& outFile);
    void setDispatchCount(unsigned dispatchCount);
    void setDispatchInterval(unsigned dispatchInterval);
    void setPendingJobLimit(unsigned pendingJobLimit);
    void setRunningJobLimit(unsigned runningJobLimit);
    void setCheckJobInterval(unsigned checkJobInterval);
    void setSaveInterval(unsigned saveInterval);
    void setLogInterval(unsigned logInterval);
    void setMaxStatusErr(unsigned maxStatusErr);
    void setLogLevel(LogLevel level);
    void sendEmail(const std::vector<std::string>& mailAddr,
		   const std::string& subject,
		   const std::string& message);

private:
    // default job dispatch limits
    static const unsigned defDispatchCount = 15; // max jobs per interval
    static const unsigned defPendingJobLimit = 100; // max pending jobs
    static const unsigned defMaxStatusErr = 3; // give up after this many
				// status-collection errors

    // default time intervals in seconds
    static const unsigned defDispatchInterval = 30; // dispatch interval
    static const unsigned defCheckJobInterval = 5*60; // check job status
    static const unsigned defSaveInterval = 10*60; // save job status to disk
    static const unsigned defLogInterval = 10*60; // log status message

    static const boost::regex filenameRE;

    bool verbose_;
    unsigned dispatchCount_;
    unsigned dispatchInterval_;
    unsigned pendingJobLimit_;
    unsigned runningJobLimit_;
    unsigned checkJobInterval_;
    unsigned saveInterval_;
    unsigned logInterval_;
    unsigned maxStatusErr_;
    JobGraph jobs_;		// job dependency graph
    RateLimiter dispatchRateLimiter_; // rate limiter for job dispatch
#if defined(HAVE_SGE)
    SgeBatchSystem batch_;
#elif defined(HAVE_LSF)
    LsfBatchSystem batch_;
#else
    StubBatchSystem batch_;
#endif
    unsigned startTime_;
    unsigned nextRateUpdateTime_;
    unsigned nextCheckDispatchedTime_;
    unsigned nextCheckJobTime_;
    unsigned nextSaveTime_;
    unsigned nextLogTime_;
    std::string statusFile_;
    std::string backupFile_;
    std::string logFile_;
    std::ofstream logOfs_;
    std::ostream* logOs_;
    bool interactive_;
    LogLevel logLevel_;

    void processEvents();
    bool submitJob();
    bool waitForEvent();
    void computeTimeout(unsigned nextTime, unsigned now, unsigned& timeout);
    bool checkJobs(JobGraph::JobList& jobList);
    void initFiles(const std::string& jobfile, const std::string& outFile,
		   const std::string& logFile);
    void saveStatus(bool backup);
    void logStatus();
    void collectStatus(std::ostringstream& msg);
    void printJobCount(std::ostream& os, const JobGraph::JobList& list,
		       Job::Status status, bool& first);
    void logResults();
    void logJobs(JobGraph::JobList& jobList, bool logStats);
    bool checkSignals();
    void kill();
    bool runLocalJob(Job& job);
    bool checkLocalJob(Job& job);
    void killLocalJob(Job& job);

    unsigned currentTime();
    void log(LogLevel level, const std::string& msg);
};

#endif // JOB_MON_H
<commit_msg>Updated src/job_mon.hh such that the time itervals are shorter - from 10 minutes to 20 seconds<commit_after>//
// job_mon.hh - sjm job monitor
//
// Phil Lacroute
// March 2008
//
// Copyright(c) 2008-2012 The Board of Trustees of The Leland Stanford
// Junior University.  All Rights Reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
//     * Redistributions of source code must retain the above copyright
//       notice, this list of conditions and the following disclaimer.
//
//     * Redistributions in binary form must reproduce the above
//       copyright notice, this list of conditions and the following
//       disclaimer in the documentation and/or other materials provided
//       with the distribution.
//
//     * Neither the name of Stanford University nor the names of its
//       contributors may be used to endorse or promote products derived
//       from this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL STANFORD
// UNIVERSITY 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.
//
// $Id: job_mon.hh 240 2009-03-19 21:51:09Z lacroute $
//

#ifndef JOB_MON_H
#define JOB_MON_H

#include <iostream>
#include <fstream>
#include <vector>
#include <list>
#include <string>
#include <boost/regex.hpp>

#include "job_graph.hh"
#include "batch.hh"

#if defined(HAVE_SGE)
#include "sge.hh"
#elif defined(HAVE_LSF)
#include "lsf.hh"
#endif

using std::ofstream;

class RateLimiter {
public:
    RateLimiter();
    void init(unsigned tokens, unsigned intervalSeconds,
	      unsigned currentTime);
    unsigned updateTime(unsigned currentTime);
    bool transmitOk();
    bool empty();

private:
    unsigned maxTokens_;
    unsigned intervalSeconds_;
    unsigned tokensLeft_;
    unsigned nextIncrementTime_;
};

class JobMonitor {
public:
    typedef enum {
	LogVerbose = 1,
	LogInfo,
	LogWarning,
	LogError,
	LogAlways
    } LogLevel;

    JobMonitor();
    bool submit(const std::string& jobFile, const std::string& outFile,
		const std::string& logFile, bool interactive,
		const std::vector<std::string>& mailAddr);
    bool render(const std::string& jobFile, const std::string& outFile);
    void setDispatchCount(unsigned dispatchCount);
    void setDispatchInterval(unsigned dispatchInterval);
    void setPendingJobLimit(unsigned pendingJobLimit);
    void setRunningJobLimit(unsigned runningJobLimit);
    void setCheckJobInterval(unsigned checkJobInterval);
    void setSaveInterval(unsigned saveInterval);
    void setLogInterval(unsigned logInterval);
    void setMaxStatusErr(unsigned maxStatusErr);
    void setLogLevel(LogLevel level);
    void sendEmail(const std::vector<std::string>& mailAddr,
		   const std::string& subject,
		   const std::string& message);

private:
    // default job dispatch limits
    static const unsigned defDispatchCount = 15; // max jobs per interval
    static const unsigned defPendingJobLimit = 100; // max pending jobs
    static const unsigned defMaxStatusErr = 3; // give up after this many
				// status-collection errors

    // default time intervals in seconds
    static const unsigned defDispatchInterval = 10; // dispatch interval
    static const unsigned defCheckJobInterval = 10; // check job status
    static const unsigned defSaveInterval = 20; // save job status to disk
    static const unsigned defLogInterval = 20; // log status message

    static const boost::regex filenameRE;

    bool verbose_;
    unsigned dispatchCount_;
    unsigned dispatchInterval_;
    unsigned pendingJobLimit_;
    unsigned runningJobLimit_;
    unsigned checkJobInterval_;
    unsigned saveInterval_;
    unsigned logInterval_;
    unsigned maxStatusErr_;
    JobGraph jobs_;		// job dependency graph
    RateLimiter dispatchRateLimiter_; // rate limiter for job dispatch
#if defined(HAVE_SGE)
    SgeBatchSystem batch_;
#elif defined(HAVE_LSF)
    LsfBatchSystem batch_;
#else
    StubBatchSystem batch_;
#endif
    unsigned startTime_;
    unsigned nextRateUpdateTime_;
    unsigned nextCheckDispatchedTime_;
    unsigned nextCheckJobTime_;
    unsigned nextSaveTime_;
    unsigned nextLogTime_;
    std::string statusFile_;
    std::string backupFile_;
    std::string logFile_;
    std::ofstream logOfs_;
    std::ostream* logOs_;
    bool interactive_;
    LogLevel logLevel_;

    void processEvents();
    bool submitJob();
    bool waitForEvent();
    void computeTimeout(unsigned nextTime, unsigned now, unsigned& timeout);
    bool checkJobs(JobGraph::JobList& jobList);
    void initFiles(const std::string& jobfile, const std::string& outFile,
		   const std::string& logFile);
    void saveStatus(bool backup);
    void logStatus();
    void collectStatus(std::ostringstream& msg);
    void printJobCount(std::ostream& os, const JobGraph::JobList& list,
		       Job::Status status, bool& first);
    void logResults();
    void logJobs(JobGraph::JobList& jobList, bool logStats);
    bool checkSignals();
    void kill();
    bool runLocalJob(Job& job);
    bool checkLocalJob(Job& job);
    void killLocalJob(Job& job);

    unsigned currentTime();
    void log(LogLevel level, const std::string& msg);
};

#endif // JOB_MON_H
<|endoftext|>


<commit_before>/**************************************************************************
 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
 *                                                                        *
 * Author: The ALICE Off-line Project.                                    *
 * Contributors are mentioned in the code where appropriate.              *
 *                                                                        *
 * Permission to use, copy, modify and distribute this software and its   *
 * documentation strictly for non-commercial purposes is hereby granted   *
 * without fee, provided that the above copyright notice appears in all   *
 * copies and that both the copyright notice and this permission notice   *
 * appear in the supporting documentation. The authors make no claims     *
 * about the suitability of this software for any purpose. It is          *
 * provided "as is" without express or implied warranty.                  *
 **************************************************************************/

/* $Id$ */
//===========================================================
//  Segmentation classes for MUON Detection Elements
//        Gines MARTINEZ, SUBATECH July 04
//  This class interfaces with the mapping and segmentation
//  files MUON.
//  This files are placed by default in
//  $ALICE_ROOT/MUON/mapping/data/Stationxxx/yyy_plane/
//  There are in tracking 23 types of detection elements
//  8 SectorSt1, 8 SectorSt2, 2 122000SR1, 2 122000NR1, 4 112200SR2, 4 112200NR2
//  4 122200S, 4 122200N, 8 222000N,8 220000N,  8 330000N, 4 122300N, 8 112230NR3
//  8 112230N, 8 222330N, 8 223300N, 16 333000N, 4  122330N, 8 112233NR3, 8 112233N
//  8 222333N, 8 223330N, 8 333300N
//  Detailed information in Alice Technical Note xxxxxxxx (2004)
//===========================================================

#include <Riostream.h>

#include "TClonesArray.h"
#include "TMap.h"
#include "TMath.h"

#include "AliMUONSegmentationDetectionElement.h"
#include "AliMUONSegmentManuIndex.h"
#include "AliMUONSegmentPosition.h"
#include "AliMUONSegmentIndex.h"

//___________________________________________
ClassImp(AliMUONSegmentationDetectionElement)

//static data member
const TString AliMUONSegmentationDetectionElement::fgkDefaultTop =getenv("ALICE_ROOT") ;
const TString AliMUONSegmentationDetectionElement::fgkStationDir = "/MUON/mapping/data/station";
const TString AliMUONSegmentationDetectionElement::fgkBendingDir= "/bending_plane";
const TString AliMUONSegmentationDetectionElement::fgkNonBendingDir= "/non-bending_plane";
const TString AliMUONSegmentationDetectionElement::fgkFileExt = ".map";
const TString AliMUONSegmentationDetectionElement::fgkBendingExt = ".Bending";
const TString AliMUONSegmentationDetectionElement::fgkNonBendingExt = ".NonBending";

//___________________________________________

AliMUONSegmentationDetectionElement::AliMUONSegmentationDetectionElement() : TObject()
{
  //Default constructor
  fWireD  = 0.25; // wire pitch in cm
  fWireX0 = 0.;  // X0 position of the 1st wire
  fMapManuIndexIndex= 0x0;
  fMapIndexManuIndex= 0x0;
  fMapIndexPosition= 0x0;
  fMapPositionIndex=0X0;
}

// AliMUONSegmentationDetectionElement::AliMUONSegmentationDetectionElement(const char* ElementType)
// {

//   fMapManuIndexIndex= 0x0;
//   fMapIndexManuIndex= 0x0;
//   fMapIndexPosition= 0x0;
// }

//________________________________________________
AliMUONSegmentationDetectionElement::AliMUONSegmentationDetectionElement(const AliMUONSegmentationDetectionElement& rhs): TObject(rhs)
{
// Protected copy constructor

  Fatal("AliMUONSegmentationDetectionElementModule", "Not implemented.");
}
//_________________________________________________
AliMUONSegmentationDetectionElement::~AliMUONSegmentationDetectionElement(){
  //Class destructor
  fListOfIndexes->Delete();
  fListOfManuIndexes->Delete();
  fListOfPositions->Delete();
  fMapManuIndexIndex->Clear();
  fMapIndexManuIndex->Clear();
  fMapIndexPosition->Clear();
  fMapPositionIndex->Clear();
}

//__________________________________________________
AliMUONSegmentIndex *  AliMUONSegmentationDetectionElement::FindIndexFromPosition(Float_t x, Float_t y, Int_t cathode)
{
  // Finding x_wire corresponding to x
  Float_t x_wire = GetAnod(x);

  //Finding pad corresponding to the position (x_wire, y) in a zone of size 3cm x 10cm or 10cm x 3cm depending on cathode plane
  //
  Int_t ix_max = (cathode==0) ? TMath::Nint(5./AliMUONSegmentPosition::GetUnit())  :  TMath::Nint(1.5/AliMUONSegmentPosition::GetUnit());
  Int_t iy_max = (cathode==0) ? TMath::Nint(1.5/AliMUONSegmentPosition::GetUnit()) :  TMath::Nint(5./AliMUONSegmentPosition::GetUnit());

  AliMUONSegmentIndex * segmentindex =0x0;
  AliMUONSegmentIndex * foundsegmentindex =0x0;
  AliMUONSegmentPosition * segmentposition=0x0;
  Int_t   ix, iy;
  Float_t xt,yt;
  Float_t distance = 99999999.;
  //printf("%d %d \n",ix_max, iy_max);

  for(ix=-ix_max; ix<ix_max; ix++) {
    xt = x_wire + ((Float_t)ix)*AliMUONSegmentPosition::GetUnit();
    for(iy=-iy_max; iy<iy_max; iy++) {
      yt = y + ((Float_t)iy)*AliMUONSegmentPosition::GetUnit();
      segmentindex = GetIndexFromPosition( xt, yt, cathode);
      if ( segmentindex ) {
	// segmentindex->Print();
	segmentposition = GetPosition(segmentindex->GetName());
	if ( segmentposition->Distance(x_wire, y) < distance ) {
	  //printf("adfafa xt %f yt %f distance %f \n", xt, yt, segmentposition->Distance(xt,yt) );
	  distance = segmentposition->Distance(x_wire,y);
	  foundsegmentindex = segmentindex;
	}
      }
    }
  }
 if (!foundsegmentindex) {
   Warning("FindIndexFromPosition","Not found Index for position x=%5.2f y=%5.2f \n",x,y);
 }
 return foundsegmentindex;
}

//____________________________________________________-
Float_t AliMUONSegmentationDetectionElement::GetAnod(Float_t xhit) const
{
  // Returns for a hit position xhit the position of the nearest anode wire
  Float_t wire= ( (xhit- fWireX0)>0 ) ?
    Int_t( (xhit- fWireX0)/fWireD )+0.5 :
    Int_t( (xhit- fWireX0)/fWireD )-0.5;
  return fWireD*wire+fWireX0;
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndex(Int_t manu, Int_t channel) const
{
  // Getting AliMUONSegmentIndex from ManuIndex
  return GetIndex( AliMUONSegmentManuIndex::Name(manu, channel).Data() ) ;
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndex( const char * SegmentManuIndexName) const
{
  // Getting AliMUONSegmentIndex from name of AliMUONSegmentManuIndex
  if (fMapManuIndexIndex) return  (AliMUONSegmentIndex*)  fMapManuIndexIndex->GetValue(SegmentManuIndexName);
  else {
    Warning("GetIndex","SegmentManuIndex %s out of DetectionElement Mapping %s",
	    SegmentManuIndexName,fDetectionElementType.Data());
    return 0x0;
  }
}
//_________________________________________________
AliMUONSegmentManuIndex * AliMUONSegmentationDetectionElement::GetManuIndex(Int_t padx, Int_t pady, Int_t cathode ) const
{
  // Getting ManuIndex from Index
  return GetManuIndex( AliMUONSegmentIndex::Name(padx, pady, cathode).Data() );
}
//_________________________________________________
AliMUONSegmentManuIndex * AliMUONSegmentationDetectionElement::GetManuIndex( const char * SegmentIndexName) const
{
  // Getting ManuIndex from manuname
  if (fMapIndexManuIndex) return (AliMUONSegmentManuIndex*) fMapIndexManuIndex->GetValue(SegmentIndexName);
  else {
    Warning("GetManuIndex","SegmentIndex %s out of Detection Element mapping %s",
	    SegmentIndexName,fDetectionElementType.Data());
    return 0x0;
  }
}
//__________________________________________________
void  AliMUONSegmentationDetectionElement::GetPadC(Int_t ix, Int_t iy, Int_t cathode, Float_t &x, Float_t &y )
{
  x = GetPosition(ix,iy,cathode)->GetXlocal();
  y = GetPosition(ix,iy,cathode)->GetYlocal();
}
//__________________________________________________
void  AliMUONSegmentationDetectionElement::GetPadI(Float_t x, Float_t y, Int_t cathode, Int_t &padx, Int_t &pady)
{

  AliMUONSegmentIndex * segmentindex = FindIndexFromPosition(x,y,cathode);

  if (segmentindex) {
    padx = segmentindex->GetPadX();
    pady = segmentindex->GetPadX();
  }
  else {
    Warning("GetPadI","Not found Index for position x=%5.2f y=%5.2f \n",x,y);
  }
}
//_________________________________________________
AliMUONSegmentPosition  * AliMUONSegmentationDetectionElement::GetPosition(Int_t padx, Int_t pady, Int_t cathode ) const
{
  //Getting position from index
  return GetPosition(  AliMUONSegmentIndex::Name(padx, pady, cathode).Data() );
}
//_________________________________________________
AliMUONSegmentPosition  * AliMUONSegmentationDetectionElement::GetPosition( const char * SegmentIndexName) const
{
  // Getting position from indexname
  if (fMapIndexPosition) return (AliMUONSegmentPosition*) fMapIndexPosition->GetValue(SegmentIndexName);
  else {
    Warning("GetPosition","SegmentIndex %s out of DetectionElement mapping %s",
	    SegmentIndexName, fDetectionElementType.Data());
    return 0x0;
  }
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndexFromPosition(Float_t x, Float_t y, Int_t cathode) const
{
  // Getting Index from position if position is a center pad position
  return GetIndexFromPosition( AliMUONSegmentPosition::Name(x, y, cathode).Data() );
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndexFromPosition( const char * PositionName) const
{
  // Getting index form positionname
  if (fMapPositionIndex) return  (AliMUONSegmentIndex*)  fMapPositionIndex->GetValue(PositionName);
  else {
    Warning("GetIndexFromPosition","SegmentPosition %s out of DetectionElement Mapping %s",
	    PositionName,fDetectionElementType.Data());
    return 0x0;
  }
}

//_________________________________________________
AliMUONSegmentManuIndex * AliMUONSegmentationDetectionElement::FindManuIndex( const char* ManuIndexName)const
{
  // Getting AliMUONSegmentManuIndex objecto from manu index
  if (fMapManuIndexIndex) return (AliMUONSegmentManuIndex*) fMapManuIndexIndex->FindObject(ManuIndexName);
  else  {
    Warning("FindManuIndex","SegmentManuIndex %s out of DetectionElement mapping %s",
	    ManuIndexName,fDetectionElementType.Data());
    return 0x0;
  }
}

//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::FindIndex(const char* IndexName) const
{
  // Getting
  if (fMapIndexPosition) return (AliMUONSegmentIndex *) fMapIndexPosition->FindObject(IndexName);
  else {
    Warning("FindIndex","SegmentIndex %s out of DetectionElement mapping %s",
	    IndexName,fDetectionElementType.Data());
    return 0x0;
  }
}
//_________________________________________________
void    AliMUONSegmentationDetectionElement::Init(const char * DetectionElementType)
{
  TString elementType(DetectionElementType);
  fSegmentationMappingFileBending = fgkDefaultTop+fgkStationDir+"345"
    +fgkBendingDir+"/"+elementType+fgkBendingExt+fgkFileExt;
  fSegmentationMappingFileNonBending = fgkDefaultTop+fgkStationDir+"345"
    +fgkNonBendingDir+"/"+elementType+fgkNonBendingExt+fgkFileExt;

  if (fMapManuIndexIndex==0x0) {
    fListOfIndexes = new TObjArray(15000);
    fListOfManuIndexes =new TObjArray(15000);
    fListOfPositions =new TObjArray(15000);
    fMapManuIndexIndex= new TMap();
    fMapIndexManuIndex = new TMap();
    fMapIndexPosition = new TMap();
    fMapPositionIndex = new TMap();
  }
  else {
    fListOfIndexes->Delete();
    fListOfManuIndexes->Delete();
    fListOfPositions->Delete();
    fMapManuIndexIndex->Clear();
    fMapIndexManuIndex->Clear();
    fMapIndexPosition->Clear();
    fMapPositionIndex->Clear();
  }
  Int_t icathode;
  //Bendingplane
  icathode=0;
  Info("ReadingSegmentationMappingFile","%s", fSegmentationMappingFileBending.Data());
  ReadingSegmentationMappingFile(fSegmentationMappingFileBending ,icathode);
  //NonBendingplane
  icathode=1;
  Info("Init","Reading mapping file is %s\n", fSegmentationMappingFileNonBending.Data());
  ReadingSegmentationMappingFile(fSegmentationMappingFileNonBending,icathode);

}
//_______________________________________________________________
void AliMUONSegmentationDetectionElement::ReadingSegmentationMappingFile(TString infile, Int_t cathode)
{
  ifstream in( infile,  ios::in);
  if (!in) {
    Error("ReadingSegmentationMappingFile", "File not found.");
  }
  else {
    Int_t id, ix, iy, idmanu, idchannel;
    Float_t x, y;
    do {
      in >> id >> ix >> iy >> x >> y >> idmanu >> idchannel;
      //     printf("id=%d ix=%d iy=%d x=%f y=%f idmanu=%d and idchannel=%d\n",id, ix, iy,  x, y,idmanu, idchannel);

      fListOfIndexes->AddAt(     new AliMUONSegmentIndex(id,ix,iy,cathode), id);
      fListOfManuIndexes->AddAt( new AliMUONSegmentManuIndex(id,idmanu,0,idchannel), id);;
      fListOfPositions->AddAt(   new AliMUONSegmentPosition(id, x, y,cathode), id);;

      //( (AliMUONSegmentIndex* )fListOfIndexes->At(id))->Print();
      //( (AliMUONSegmentManuIndex*)fListOfManuIndexes->At(id))->Print();
      //( (AliMUONSegmentPosition*)fListOfPositions->At(id))->Print();

      fMapManuIndexIndex->Add( fListOfManuIndexes->At(id), fListOfIndexes->At(id));
      fMapIndexManuIndex->Add( fListOfIndexes->At(id),     fListOfManuIndexes->At(id));
      fMapIndexPosition->Add(  fListOfIndexes->At(id),     fListOfPositions->At(id));
      fMapPositionIndex->Add(  fListOfPositions->At(id),   fListOfIndexes->At(id) );
    }
    while ( !in.eof());
  }
  in.close();
}
<commit_msg>Adding #include <stdlib.h> for getenv as proposed by Yuri<commit_after>/**************************************************************************
 * Copyright(c) 1998-1999, ALICE Experiment at CERN, All rights reserved. *
 *                                                                        *
 * Author: The ALICE Off-line Project.                                    *
 * Contributors are mentioned in the code where appropriate.              *
 *                                                                        *
 * Permission to use, copy, modify and distribute this software and its   *
 * documentation strictly for non-commercial purposes is hereby granted   *
 * without fee, provided that the above copyright notice appears in all   *
 * copies and that both the copyright notice and this permission notice   *
 * appear in the supporting documentation. The authors make no claims     *
 * about the suitability of this software for any purpose. It is          *
 * provided "as is" without express or implied warranty.                  *
 **************************************************************************/

/* $Id$ */
//===========================================================
//  Segmentation classes for MUON Detection Elements
//        Gines MARTINEZ, SUBATECH July 04
//  This class interfaces with the mapping and segmentation
//  files MUON.
//  This files are placed by default in
//  $ALICE_ROOT/MUON/mapping/data/Stationxxx/yyy_plane/
//  There are in tracking 23 types of detection elements
//  8 SectorSt1, 8 SectorSt2, 2 122000SR1, 2 122000NR1, 4 112200SR2, 4 112200NR2
//  4 122200S, 4 122200N, 8 222000N,8 220000N,  8 330000N, 4 122300N, 8 112230NR3
//  8 112230N, 8 222330N, 8 223300N, 16 333000N, 4  122330N, 8 112233NR3, 8 112233N
//  8 222333N, 8 223330N, 8 333300N
//  Detailed information in Alice Technical Note xxxxxxxx (2004)
//===========================================================

#include <Riostream.h>
#include <stdlib.h>

#include "TClonesArray.h"
#include "TMap.h"
#include "TMath.h"

#include "AliMUONSegmentationDetectionElement.h"
#include "AliMUONSegmentManuIndex.h"
#include "AliMUONSegmentPosition.h"
#include "AliMUONSegmentIndex.h"

//___________________________________________
ClassImp(AliMUONSegmentationDetectionElement)

//static data member
const TString AliMUONSegmentationDetectionElement::fgkDefaultTop =getenv("ALICE_ROOT") ;
const TString AliMUONSegmentationDetectionElement::fgkStationDir = "/MUON/mapping/data/station";
const TString AliMUONSegmentationDetectionElement::fgkBendingDir= "/bending_plane";
const TString AliMUONSegmentationDetectionElement::fgkNonBendingDir= "/non-bending_plane";
const TString AliMUONSegmentationDetectionElement::fgkFileExt = ".map";
const TString AliMUONSegmentationDetectionElement::fgkBendingExt = ".Bending";
const TString AliMUONSegmentationDetectionElement::fgkNonBendingExt = ".NonBending";

//___________________________________________

AliMUONSegmentationDetectionElement::AliMUONSegmentationDetectionElement() : TObject()
{
  //Default constructor
  fWireD  = 0.25; // wire pitch in cm
  fWireX0 = 0.;  // X0 position of the 1st wire
  fMapManuIndexIndex= 0x0;
  fMapIndexManuIndex= 0x0;
  fMapIndexPosition= 0x0;
  fMapPositionIndex=0X0;
}

// AliMUONSegmentationDetectionElement::AliMUONSegmentationDetectionElement(const char* ElementType)
// {

//   fMapManuIndexIndex= 0x0;
//   fMapIndexManuIndex= 0x0;
//   fMapIndexPosition= 0x0;
// }

//________________________________________________
AliMUONSegmentationDetectionElement::AliMUONSegmentationDetectionElement(const AliMUONSegmentationDetectionElement& rhs): TObject(rhs)
{
// Protected copy constructor

  Fatal("AliMUONSegmentationDetectionElementModule", "Not implemented.");
}
//_________________________________________________
AliMUONSegmentationDetectionElement::~AliMUONSegmentationDetectionElement(){
  //Class destructor
  fListOfIndexes->Delete();
  fListOfManuIndexes->Delete();
  fListOfPositions->Delete();
  fMapManuIndexIndex->Clear();
  fMapIndexManuIndex->Clear();
  fMapIndexPosition->Clear();
  fMapPositionIndex->Clear();
}

//__________________________________________________
AliMUONSegmentIndex *  AliMUONSegmentationDetectionElement::FindIndexFromPosition(Float_t x, Float_t y, Int_t cathode)
{
  // Finding x_wire corresponding to x
  Float_t x_wire = GetAnod(x);

  //Finding pad corresponding to the position (x_wire, y) in a zone of size 3cm x 10cm or 10cm x 3cm depending on cathode plane
  //
  Int_t ix_max = (cathode==0) ? TMath::Nint(5./AliMUONSegmentPosition::GetUnit())  :  TMath::Nint(1.5/AliMUONSegmentPosition::GetUnit());
  Int_t iy_max = (cathode==0) ? TMath::Nint(1.5/AliMUONSegmentPosition::GetUnit()) :  TMath::Nint(5./AliMUONSegmentPosition::GetUnit());

  AliMUONSegmentIndex * segmentindex =0x0;
  AliMUONSegmentIndex * foundsegmentindex =0x0;
  AliMUONSegmentPosition * segmentposition=0x0;
  Int_t   ix, iy;
  Float_t xt,yt;
  Float_t distance = 99999999.;
  //printf("%d %d \n",ix_max, iy_max);

  for(ix=-ix_max; ix<ix_max; ix++) {
    xt = x_wire + ((Float_t)ix)*AliMUONSegmentPosition::GetUnit();
    for(iy=-iy_max; iy<iy_max; iy++) {
      yt = y + ((Float_t)iy)*AliMUONSegmentPosition::GetUnit();
      segmentindex = GetIndexFromPosition( xt, yt, cathode);
      if ( segmentindex ) {
	// segmentindex->Print();
	segmentposition = GetPosition(segmentindex->GetName());
	if ( segmentposition->Distance(x_wire, y) < distance ) {
	  //printf("adfafa xt %f yt %f distance %f \n", xt, yt, segmentposition->Distance(xt,yt) );
	  distance = segmentposition->Distance(x_wire,y);
	  foundsegmentindex = segmentindex;
	}
      }
    }
  }
 if (!foundsegmentindex) {
   Warning("FindIndexFromPosition","Not found Index for position x=%5.2f y=%5.2f \n",x,y);
 }
 return foundsegmentindex;
}

//____________________________________________________-
Float_t AliMUONSegmentationDetectionElement::GetAnod(Float_t xhit) const
{
  // Returns for a hit position xhit the position of the nearest anode wire
  Float_t wire= ( (xhit- fWireX0)>0 ) ?
    Int_t( (xhit- fWireX0)/fWireD )+0.5 :
    Int_t( (xhit- fWireX0)/fWireD )-0.5;
  return fWireD*wire+fWireX0;
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndex(Int_t manu, Int_t channel) const
{
  // Getting AliMUONSegmentIndex from ManuIndex
  return GetIndex( AliMUONSegmentManuIndex::Name(manu, channel).Data() ) ;
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndex( const char * SegmentManuIndexName) const
{
  // Getting AliMUONSegmentIndex from name of AliMUONSegmentManuIndex
  if (fMapManuIndexIndex) return  (AliMUONSegmentIndex*)  fMapManuIndexIndex->GetValue(SegmentManuIndexName);
  else {
    Warning("GetIndex","SegmentManuIndex %s out of DetectionElement Mapping %s",
	    SegmentManuIndexName,fDetectionElementType.Data());
    return 0x0;
  }
}
//_________________________________________________
AliMUONSegmentManuIndex * AliMUONSegmentationDetectionElement::GetManuIndex(Int_t padx, Int_t pady, Int_t cathode ) const
{
  // Getting ManuIndex from Index
  return GetManuIndex( AliMUONSegmentIndex::Name(padx, pady, cathode).Data() );
}
//_________________________________________________
AliMUONSegmentManuIndex * AliMUONSegmentationDetectionElement::GetManuIndex( const char * SegmentIndexName) const
{
  // Getting ManuIndex from manuname
  if (fMapIndexManuIndex) return (AliMUONSegmentManuIndex*) fMapIndexManuIndex->GetValue(SegmentIndexName);
  else {
    Warning("GetManuIndex","SegmentIndex %s out of Detection Element mapping %s",
	    SegmentIndexName,fDetectionElementType.Data());
    return 0x0;
  }
}
//__________________________________________________
void  AliMUONSegmentationDetectionElement::GetPadC(Int_t ix, Int_t iy, Int_t cathode, Float_t &x, Float_t &y )
{
  x = GetPosition(ix,iy,cathode)->GetXlocal();
  y = GetPosition(ix,iy,cathode)->GetYlocal();
}
//__________________________________________________
void  AliMUONSegmentationDetectionElement::GetPadI(Float_t x, Float_t y, Int_t cathode, Int_t &padx, Int_t &pady)
{

  AliMUONSegmentIndex * segmentindex = FindIndexFromPosition(x,y,cathode);

  if (segmentindex) {
    padx = segmentindex->GetPadX();
    pady = segmentindex->GetPadX();
  }
  else {
    Warning("GetPadI","Not found Index for position x=%5.2f y=%5.2f \n",x,y);
  }
}
//_________________________________________________
AliMUONSegmentPosition  * AliMUONSegmentationDetectionElement::GetPosition(Int_t padx, Int_t pady, Int_t cathode ) const
{
  //Getting position from index
  return GetPosition(  AliMUONSegmentIndex::Name(padx, pady, cathode).Data() );
}
//_________________________________________________
AliMUONSegmentPosition  * AliMUONSegmentationDetectionElement::GetPosition( const char * SegmentIndexName) const
{
  // Getting position from indexname
  if (fMapIndexPosition) return (AliMUONSegmentPosition*) fMapIndexPosition->GetValue(SegmentIndexName);
  else {
    Warning("GetPosition","SegmentIndex %s out of DetectionElement mapping %s",
	    SegmentIndexName, fDetectionElementType.Data());
    return 0x0;
  }
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndexFromPosition(Float_t x, Float_t y, Int_t cathode) const
{
  // Getting Index from position if position is a center pad position
  return GetIndexFromPosition( AliMUONSegmentPosition::Name(x, y, cathode).Data() );
}
//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::GetIndexFromPosition( const char * PositionName) const
{
  // Getting index form positionname
  if (fMapPositionIndex) return  (AliMUONSegmentIndex*)  fMapPositionIndex->GetValue(PositionName);
  else {
    Warning("GetIndexFromPosition","SegmentPosition %s out of DetectionElement Mapping %s",
	    PositionName,fDetectionElementType.Data());
    return 0x0;
  }
}

//_________________________________________________
AliMUONSegmentManuIndex * AliMUONSegmentationDetectionElement::FindManuIndex( const char* ManuIndexName)const
{
  // Getting AliMUONSegmentManuIndex objecto from manu index
  if (fMapManuIndexIndex) return (AliMUONSegmentManuIndex*) fMapManuIndexIndex->FindObject(ManuIndexName);
  else  {
    Warning("FindManuIndex","SegmentManuIndex %s out of DetectionElement mapping %s",
	    ManuIndexName,fDetectionElementType.Data());
    return 0x0;
  }
}

//_________________________________________________
AliMUONSegmentIndex * AliMUONSegmentationDetectionElement::FindIndex(const char* IndexName) const
{
  // Getting
  if (fMapIndexPosition) return (AliMUONSegmentIndex *) fMapIndexPosition->FindObject(IndexName);
  else {
    Warning("FindIndex","SegmentIndex %s out of DetectionElement mapping %s",
	    IndexName,fDetectionElementType.Data());
    return 0x0;
  }
}
//_________________________________________________
void    AliMUONSegmentationDetectionElement::Init(const char * DetectionElementType)
{
  TString elementType(DetectionElementType);
  fSegmentationMappingFileBending = fgkDefaultTop+fgkStationDir+"345"
    +fgkBendingDir+"/"+elementType+fgkBendingExt+fgkFileExt;
  fSegmentationMappingFileNonBending = fgkDefaultTop+fgkStationDir+"345"
    +fgkNonBendingDir+"/"+elementType+fgkNonBendingExt+fgkFileExt;

  if (fMapManuIndexIndex==0x0) {
    fListOfIndexes = new TObjArray(15000);
    fListOfManuIndexes =new TObjArray(15000);
    fListOfPositions =new TObjArray(15000);
    fMapManuIndexIndex= new TMap();
    fMapIndexManuIndex = new TMap();
    fMapIndexPosition = new TMap();
    fMapPositionIndex = new TMap();
  }
  else {
    fListOfIndexes->Delete();
    fListOfManuIndexes->Delete();
    fListOfPositions->Delete();
    fMapManuIndexIndex->Clear();
    fMapIndexManuIndex->Clear();
    fMapIndexPosition->Clear();
    fMapPositionIndex->Clear();
  }
  Int_t icathode;
  //Bendingplane
  icathode=0;
  Info("ReadingSegmentationMappingFile","%s", fSegmentationMappingFileBending.Data());
  ReadingSegmentationMappingFile(fSegmentationMappingFileBending ,icathode);
  //NonBendingplane
  icathode=1;
  Info("Init","Reading mapping file is %s\n", fSegmentationMappingFileNonBending.Data());
  ReadingSegmentationMappingFile(fSegmentationMappingFileNonBending,icathode);

}
//_______________________________________________________________
void AliMUONSegmentationDetectionElement::ReadingSegmentationMappingFile(TString infile, Int_t cathode)
{
  ifstream in( infile,  ios::in);
  if (!in) {
    Error("ReadingSegmentationMappingFile", "File not found.");
  }
  else {
    Int_t id, ix, iy, idmanu, idchannel;
    Float_t x, y;
    do {
      in >> id >> ix >> iy >> x >> y >> idmanu >> idchannel;
      //     printf("id=%d ix=%d iy=%d x=%f y=%f idmanu=%d and idchannel=%d\n",id, ix, iy,  x, y,idmanu, idchannel);

      fListOfIndexes->AddAt(     new AliMUONSegmentIndex(id,ix,iy,cathode), id);
      fListOfManuIndexes->AddAt( new AliMUONSegmentManuIndex(id,idmanu,0,idchannel), id);;
      fListOfPositions->AddAt(   new AliMUONSegmentPosition(id, x, y,cathode), id);;

      //( (AliMUONSegmentIndex* )fListOfIndexes->At(id))->Print();
      //( (AliMUONSegmentManuIndex*)fListOfManuIndexes->At(id))->Print();
      //( (AliMUONSegmentPosition*)fListOfPositions->At(id))->Print();

      fMapManuIndexIndex->Add( fListOfManuIndexes->At(id), fListOfIndexes->At(id));
      fMapIndexManuIndex->Add( fListOfIndexes->At(id),     fListOfManuIndexes->At(id));
      fMapIndexPosition->Add(  fListOfIndexes->At(id),     fListOfPositions->At(id));
      fMapPositionIndex->Add(  fListOfPositions->At(id),   fListOfIndexes->At(id) );
    }
    while ( !in.eof());
  }
  in.close();
}
<|endoftext|>