<commit_before>/******************************************************************************
 *
 * C++11 wrapper for EJDB (http://ejdb.org)
 * Copyright (C) 2013 Christian Manning
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301
 * USA
 *****************************************************************************/

#include <array>

#include <boost/optional.hpp>
#include <boost/range/adaptor/transformed.hpp>

#include <jbson/document.hpp>
#include <jbson/json_reader.hpp>

#include <ejpp/c_ejdb.hpp>
#include <ejpp/ejdb.hpp>

namespace ejdb {

using namespace jbson::literal;

struct ejdb_deleter {
    void operator()(EJDB* ptr) const { c_ejdb::del(ptr); }
};

void query::eqry_deleter::operator()(EJQ* ptr) const { c_ejdb::querydel(ptr); }

ejdb::ejdb() : m_db(c_ejdb::newdb(), ejdb_deleter()) {}

ejdb::operator bool() const noexcept { return static_cast<bool>(m_db); }

std::error_code ejdb::error() const noexcept {
    assert(m_db);
    return make_error_code(c_ejdb::ecode(m_db.get()));
}

bool ejdb::open(const std::string& path, int mode, std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::open(m_db.get(), path.c_str(), mode);
    if(!r)
        ec = error();
    return r;
}

bool ejdb::is_open() const noexcept {
    assert(m_db);
    return c_ejdb::isopen(m_db.get());
}

bool ejdb::close(std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::closedb(m_db.get());
    if(!r)
        ec = error();
    return r;
}

collection ejdb::get_collection(const std::string& name, std::error_code& ec) const noexcept {
    assert(m_db);
    const auto r = c_ejdb::getcoll(m_db.get(), name.c_str());
    if(!r)
        ec = error();
    return {m_db, r};
}

collection ejdb::create_collection(const std::string& name, std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::createcoll(m_db.get(), name.c_str(), nullptr);
    if(!r)
        ec = error();
    return {m_db, r};
}

bool ejdb::remove_collection(const std::string& name, bool unlink_file, std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::rmcoll(m_db.get(), name.c_str(), unlink_file);
    if(!r)
        ec = error();
    return r;
}

const std::deque<collection> ejdb::get_collections() const noexcept {
    assert(m_db);
    auto colls = c_ejdb::getcolls(m_db.get());
    auto range = boost::adaptors::transform(colls, [this](EJCOLL* c) { return collection{m_db, c}; });
    return {range.begin(), range.end()};
}

query ejdb::create_query(const jbson::document& doc, std::error_code& ec) noexcept {
    assert(m_db);
    try {
        const auto r = c_ejdb::createquery(m_db.get(), doc.data().data());
        if(!r)
            ec = error();
        return {m_db, r};
    }
    catch(jbson::jbson_error&) {
        ec = make_error_code(9001);
        return query{};
    }
}

bool ejdb::sync(std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::syncdb(m_db.get());
    if(!r)
        ec = error();
    return r;
}

boost::optional<jbson::document> ejdb::metadata() noexcept {
    assert(m_db);
    auto r = c_ejdb::metadb(m_db.get());
    return r.empty() ? boost::optional<jbson::document>{boost::none} : jbson::document{std::move(r)};
}

collection::collection(std::weak_ptr<EJDB> db, EJCOLL* coll) noexcept : m_db(db), m_coll(coll) {}

collection::operator bool() const noexcept { return !m_db.expired() && m_coll != nullptr; }

boost::optional<std::array<char, 12>> collection::save_document(const jbson::document& data,
                                                                std::error_code& ec) noexcept {
    return save_document(data, false, ec);
}

boost::optional<std::array<char, 12>> collection::save_document(const jbson::document& doc, bool merge,
                                                                std::error_code& ec) noexcept {
    assert(m_coll);
    auto db = m_db.lock();
    if(!db && (ec = std::make_error_code(std::errc::owner_dead)))
        return {};
    std::array<char, 12> oid;
    const auto r = c_ejdb::savebson2(m_coll, doc.data().data(), oid.data(), merge);
    ec = make_error_code(!r ? c_ejdb::ecode(db.get()) : 0);
    return r ? oid : boost::optional<std::array<char, 12>>{boost::none};
}

boost::optional<jbson::document> collection::load_document(std::array<char, 12> oid, std::error_code& ec) const
    noexcept {
    assert(m_coll);
    auto r = c_ejdb::loadbson(m_coll, oid.data());
    auto db = m_db.lock();
    ec = make_error_code(r.empty() && db ? c_ejdb::ecode(db.get()) : 0);
    if(!ec)
        return boost::none;
    return jbson::document(std::move(r));
}

bool collection::remove_document(std::array<char, 12> oid, std::error_code& ec) noexcept {
    assert(m_coll);
    const auto r = c_ejdb::rmbson(m_coll, oid.data());
    auto db = m_db.lock();
    if(!r && db)
        ec = make_error_code(c_ejdb::ecode(db.get()));
    return r;
}

std::vector<jbson::document> collection::execute_query(const query& qry, int sm) noexcept {
    assert(m_coll);
    if(!qry)
        return {};
    assert(qry.m_qry);
    uint32_t s{0};
    const auto list = c_ejdb::qryexecute(m_coll, qry.m_qry.get(), &s, sm);
    if(list == nullptr)
        return {};
    assert(s == static_cast<decltype(s)>(c_ejdb::qresultnum(list)));
    std::vector<jbson::document> r;
    r.reserve(s);
    int ns{0};
    for(uint32_t i = 0; i < s; i++) {
        auto data = reinterpret_cast<const char*>(c_ejdb::qresultbsondata(list, i, &ns));
        if(data == nullptr) {
            s--;
            continue;
        }
        r.emplace_back(data, data + ns);
    }
    assert(r.size() == s);
    c_ejdb::qresultdispose(list);
    return std::move(r);
}

std::vector<jbson::document> collection::get_all() noexcept {
    auto db = m_db.lock();
    auto vec = "{}"_json_doc.data();
    auto q = query{m_db, c_ejdb::createquery(db.get(), vec.data())};
    return execute_query(q);
}

bool collection::sync(std::error_code& ec) noexcept {
    assert(m_coll);
    const auto r = c_ejdb::syncoll(m_coll);
    auto db = m_db.lock();
    if(!r && db)
        ec = make_error_code(c_ejdb::ecode(db.get()));
    return r;
}

boost::string_ref collection::name() const noexcept {
    assert(m_coll);
    return c_ejdb::collection_name(m_coll);
}

query::query(std::weak_ptr<EJDB> db, EJQ* qry) noexcept : m_db(db), m_qry(qry) {}

query::~query() noexcept {}

query& query::operator|=(const jbson::document& obj) noexcept {
    assert(m_qry);
    auto db = m_db.lock();
    if(!db)
        return *this;

    auto q = c_ejdb::queryaddor(db.get(), m_qry.get(), obj.data().data());
    if(q != m_qry.get())
        m_qry.reset(q);

    return *this;
}

query& query::set_hints(const jbson::document& obj) noexcept {
    assert(m_qry);
    auto db = m_db.lock();
    if(!db)
        return *this;
    auto q = c_ejdb::queryhints(db.get(), m_qry.get(), obj.data().data());
    if(q != m_qry.get())
        m_qry.reset(q);

    return *this;
}

query::operator bool() const noexcept { return !m_db.expired() && m_qry != nullptr; }

class error_category : public std::error_category {
  public:
    constexpr error_category() noexcept = default;

    const char* name() const noexcept override { return "EJDB"; }

    std::string message(int ecode) const noexcept override { return c_ejdb::errmsg(ecode); }
};

inline std::error_code make_error_code(int ecode) {
    static const error_category ecat{};
    return std::error_code{ecode, ecat};
}

} // namespace ejdb
<commit_msg>Fix load_document<commit_after>/******************************************************************************
 *
 * C++11 wrapper for EJDB (http://ejdb.org)
 * Copyright (C) 2013 Christian Manning
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301
 * USA
 *****************************************************************************/

#include <array>

#include <boost/optional.hpp>
#include <boost/range/adaptor/transformed.hpp>

#include <jbson/document.hpp>
#include <jbson/json_reader.hpp>

#include <ejpp/c_ejdb.hpp>
#include <ejpp/ejdb.hpp>

namespace ejdb {

using namespace jbson::literal;

struct ejdb_deleter {
    void operator()(EJDB* ptr) const { c_ejdb::del(ptr); }
};

void query::eqry_deleter::operator()(EJQ* ptr) const { c_ejdb::querydel(ptr); }

ejdb::ejdb() : m_db(c_ejdb::newdb(), ejdb_deleter()) {}

ejdb::operator bool() const noexcept { return static_cast<bool>(m_db); }

std::error_code ejdb::error() const noexcept {
    assert(m_db);
    return make_error_code(c_ejdb::ecode(m_db.get()));
}

bool ejdb::open(const std::string& path, int mode, std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::open(m_db.get(), path.c_str(), mode);
    if(!r)
        ec = error();
    return r;
}

bool ejdb::is_open() const noexcept {
    assert(m_db);
    return c_ejdb::isopen(m_db.get());
}

bool ejdb::close(std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::closedb(m_db.get());
    if(!r)
        ec = error();
    return r;
}

collection ejdb::get_collection(const std::string& name, std::error_code& ec) const noexcept {
    assert(m_db);
    const auto r = c_ejdb::getcoll(m_db.get(), name.c_str());
    if(!r)
        ec = error();
    return {m_db, r};
}

collection ejdb::create_collection(const std::string& name, std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::createcoll(m_db.get(), name.c_str(), nullptr);
    if(!r)
        ec = error();
    return {m_db, r};
}

bool ejdb::remove_collection(const std::string& name, bool unlink_file, std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::rmcoll(m_db.get(), name.c_str(), unlink_file);
    if(!r)
        ec = error();
    return r;
}

const std::deque<collection> ejdb::get_collections() const noexcept {
    assert(m_db);
    auto colls = c_ejdb::getcolls(m_db.get());
    auto range = boost::adaptors::transform(colls, [this](EJCOLL* c) { return collection{m_db, c}; });
    return {range.begin(), range.end()};
}

query ejdb::create_query(const jbson::document& doc, std::error_code& ec) noexcept {
    assert(m_db);
    try {
        const auto r = c_ejdb::createquery(m_db.get(), doc.data().data());
        if(!r)
            ec = error();
        return {m_db, r};
    }
    catch(jbson::jbson_error&) {
        ec = make_error_code(9001);
        return query{};
    }
}

bool ejdb::sync(std::error_code& ec) noexcept {
    assert(m_db);
    const auto r = c_ejdb::syncdb(m_db.get());
    if(!r)
        ec = error();
    return r;
}

boost::optional<jbson::document> ejdb::metadata() noexcept {
    assert(m_db);
    auto r = c_ejdb::metadb(m_db.get());
    return r.empty() ? boost::optional<jbson::document>{boost::none} : jbson::document{std::move(r)};
}

collection::collection(std::weak_ptr<EJDB> db, EJCOLL* coll) noexcept : m_db(db), m_coll(coll) {}

collection::operator bool() const noexcept { return !m_db.expired() && m_coll != nullptr; }

boost::optional<std::array<char, 12>> collection::save_document(const jbson::document& data,
                                                                std::error_code& ec) noexcept {
    return save_document(data, false, ec);
}

boost::optional<std::array<char, 12>> collection::save_document(const jbson::document& doc, bool merge,
                                                                std::error_code& ec) noexcept {
    assert(m_coll);
    auto db = m_db.lock();
    if(!db && (ec = std::make_error_code(std::errc::owner_dead)))
        return {};
    std::array<char, 12> oid;
    const auto r = c_ejdb::savebson2(m_coll, doc.data().data(), oid.data(), merge);
    ec = make_error_code(!r ? c_ejdb::ecode(db.get()) : 0);
    return r ? oid : boost::optional<std::array<char, 12>>{boost::none};
}

boost::optional<jbson::document> collection::load_document(std::array<char, 12> oid, std::error_code& ec) const
    noexcept {
    assert(m_coll);
    auto r = c_ejdb::loadbson(m_coll, oid.data());
    auto db = m_db.lock();
    ec = make_error_code(r.empty() && db ? c_ejdb::ecode(db.get()) : 0);
    if(ec)
        return boost::none;
    return jbson::document(std::move(r));
}

bool collection::remove_document(std::array<char, 12> oid, std::error_code& ec) noexcept {
    assert(m_coll);
    const auto r = c_ejdb::rmbson(m_coll, oid.data());
    auto db = m_db.lock();
    if(!r && db)
        ec = make_error_code(c_ejdb::ecode(db.get()));
    return r;
}

std::vector<jbson::document> collection::execute_query(const query& qry, int sm) noexcept {
    assert(m_coll);
    if(!qry)
        return {};
    assert(qry.m_qry);
    uint32_t s{0};
    const auto list = c_ejdb::qryexecute(m_coll, qry.m_qry.get(), &s, sm);
    if(list == nullptr)
        return {};
    assert(s == static_cast<decltype(s)>(c_ejdb::qresultnum(list)));
    std::vector<jbson::document> r;
    r.reserve(s);
    int ns{0};
    for(uint32_t i = 0; i < s; i++) {
        auto data = reinterpret_cast<const char*>(c_ejdb::qresultbsondata(list, i, &ns));
        if(data == nullptr) {
            s--;
            continue;
        }
        r.emplace_back(data, data + ns);
    }
    assert(r.size() == s);
    c_ejdb::qresultdispose(list);
    return std::move(r);
}

std::vector<jbson::document> collection::get_all() noexcept {
    auto db = m_db.lock();
    auto vec = "{}"_json_doc.data();
    auto q = query{m_db, c_ejdb::createquery(db.get(), vec.data())};
    return execute_query(q);
}

bool collection::sync(std::error_code& ec) noexcept {
    assert(m_coll);
    const auto r = c_ejdb::syncoll(m_coll);
    auto db = m_db.lock();
    if(!r && db)
        ec = make_error_code(c_ejdb::ecode(db.get()));
    return r;
}

boost::string_ref collection::name() const noexcept {
    assert(m_coll);
    return c_ejdb::collection_name(m_coll);
}

query::query(std::weak_ptr<EJDB> db, EJQ* qry) noexcept : m_db(db), m_qry(qry) {}

query::~query() noexcept {}

query& query::operator|=(const jbson::document& obj) noexcept {
    assert(m_qry);
    auto db = m_db.lock();
    if(!db)
        return *this;

    auto q = c_ejdb::queryaddor(db.get(), m_qry.get(), obj.data().data());
    if(q != m_qry.get())
        m_qry.reset(q);

    return *this;
}

query& query::set_hints(const jbson::document& obj) noexcept {
    assert(m_qry);
    auto db = m_db.lock();
    if(!db)
        return *this;
    auto q = c_ejdb::queryhints(db.get(), m_qry.get(), obj.data().data());
    if(q != m_qry.get())
        m_qry.reset(q);

    return *this;
}

query::operator bool() const noexcept { return !m_db.expired() && m_qry != nullptr; }

class error_category : public std::error_category {
  public:
    constexpr error_category() noexcept = default;

    const char* name() const noexcept override { return "EJDB"; }

    std::string message(int ecode) const noexcept override { return c_ejdb::errmsg(ecode); }
};

inline std::error_code make_error_code(int ecode) {
    static const error_category ecat{};
    return std::error_code{ecode, ecat};
}

} // namespace ejdb
<|endoftext|>


<commit_before><commit_msg>dbaccess: RowSet.cxx: update m_bIsInsertRow<commit_after><|endoftext|>


<commit_before>//	Copyright 2017 Adam Smith
//	Licensed under the Apache License, Version 2.0 (the "License");
//	you may not use this file except in compliance with the License.
//	You may obtain a copy of the License at
//
//	http://www.apache.org/licenses/LICENSE-2.0
//
//	Unless required by applicable law or agreed to in writing, software
//	distributed under the License is distributed on an "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.

#include "asmith/serial/json.hpp"

namespace asmith { namespace serial {
	void json_format::write_serial(const value& aType, std::ostream& aStream) {
		const value::type tBuf = aType.get_type();

		switch(tBuf) {
		case value::NULL_T:
			aStream << "null";
			break;
		case value::BOOl_T:
			aStream << (aType.get_bool() ? "true" : "false");
			break;
		case value::CHAR_T:
			aStream << '"' << aType.get_char() << '"';
			break;
		case value::NUMBER_T:
			aStream << aType.get_number();
			break;
		case value::STRING_T:
			aStream << '"' << aType.get_string() << '"';
			break;
		case value::ARRAY_T:
			{
				aStream << '[';
				const value::array_t tmp = aType.get_array();
				const size_t s = tmp.size();
				for(size_t i = 0; i < s; ++i) {
					write_serial(tmp[i], aStream);
					if(i + 1 < s) aStream << ',';
				}
				aStream << ']';
			}
			break;
		case value::OBJECT_T:
		{
			aStream << '{';
			const value::object_t tmp = aType.get_object();
			const size_t s = tmp.size();
			size_t i = 0;
			for(const auto& v : tmp) {
				aStream << '"' << v.first<< '"' << ':';
				write_serial(v.second, aStream);
				if(i + 1 < s) aStream << ',';
				++i;
			}
			aStream << '}';
		}
		break;
		default:
			throw std::runtime_error("json_format : Invalid serial type");
			break;
		}
	}

	value json_format::read_serial(std::istream& aStream) {
		//! \todo Implement
		return value();
	}
}}<commit_msg>Partial implementation of JSON reading<commit_after>//	Copyright 2017 Adam Smith
//	Licensed under the Apache License, Version 2.0 (the "License");
//	you may not use this file except in compliance with the License.
//	You may obtain a copy of the License at
//
//	http://www.apache.org/licenses/LICENSE-2.0
//
//	Unless required by applicable law or agreed to in writing, software
//	distributed under the License is distributed on an "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.

#include "asmith/serial/json.hpp"
#include <cctype>

namespace asmith { namespace serial {

	void json_skip_whitespace(std::istream& aStream) {
		char c = aStream.peek();
		while(std::isspace(c)) {
			aStream.read(&c, 1);
		}
	}

	value::type json_determine_type(std::istream& aStream) {
		json_skip_whitespace(aStream);
		char c = aStream.peek();
		switch(c) {
		case 'n':
			return value::NULL_T;
		case 't':
		case 'f':
			return value::BOOl_T;
		case '0':
		case '1':
		case '2':
		case '3':
		case '4':
		case '5':
		case '6':
		case '7':
		case '8':
		case '9':
			return value::NUMBER_T;
		case '"':
			return value::STRING_T;
		case '[':
			return value::ARRAY_T;
		case '{':
			return value::OBJECT_T;
		default:
			throw std::runtime_error("asmith::json_format::read_serial : Could not determin JSON type");
		}
	}

	value json_read_value(std::istream&);

	value json_read_null(std::istream& aStream) {

	}

	value json_read_bool(std::istream& aStream) {

	}

	value json_read_number(std::istream& aStream) {

	}

	value json_read_string(std::istream& aStream) {

	}

	value json_read_array(std::istream& aStream) {

	}

	value json_read_object(std::istream& aStream) {

	}

	value json_read_value(std::istream& aStream) {
		switch(json_determine_type(aStream)) {
		case value::NULL_T:
			return json_read_null(aStream);
		case value::BOOl_T:
			return json_read_bool(aStream);
		case value::NUMBER_T:
			return json_read_number(aStream);
		case value::STRING_T:
			return json_read_string(aStream);
		case value::ARRAY_T:
			return json_read_array(aStream);
		case value::OBJECT_T:
			return json_read_object(aStream);
		default:
			throw std::runtime_error("asmith::json_format::read_serial : Could not determin JSON type");
		}
	}

	void json_format::write_serial(const value& aType, std::ostream& aStream) {
		const value::type tBuf = aType.get_type();

		switch(tBuf) {
		case value::NULL_T:
			aStream << "null";
			break;
		case value::BOOl_T:
			aStream << (aType.get_bool() ? "true" : "false");
			break;
		case value::CHAR_T:
			aStream << '"' << aType.get_char() << '"';
			break;
		case value::NUMBER_T:
			aStream << aType.get_number();
			break;
		case value::STRING_T:
			aStream << '"' << aType.get_string() << '"';
			break;
		case value::ARRAY_T:
			{
				aStream << '[';
				const value::array_t tmp = aType.get_array();
				const size_t s = tmp.size();
				for(size_t i = 0; i < s; ++i) {
					write_serial(tmp[i], aStream);
					if(i + 1 < s) aStream << ',';
				}
				aStream << ']';
			}
			break;
		case value::OBJECT_T:
		{
			aStream << '{';
			const value::object_t tmp = aType.get_object();
			const size_t s = tmp.size();
			size_t i = 0;
			for(const auto& v : tmp) {
				aStream << '"' << v.first<< '"' << ':';
				write_serial(v.second, aStream);
				if(i + 1 < s) aStream << ',';
				++i;
			}
			aStream << '}';
		}
		break;
		default:
			throw std::runtime_error("json_format : Invalid serial type");
			break;
		}
	}

	value json_format::read_serial(std::istream& aStream) {
		//! \todo Implement
		return value();
	}
}}<|endoftext|>


<commit_before>#include "pch.h"
#include "GameManager.h"
#include "ResourceManager.h"
#include "DataManager.h"

Arthas::ResourceManager::ResourceManager()
{

}

Arthas::ResourceManager::~ResourceManager()
{

}

bool Arthas::ResourceManager::init()
{
	return true;
}

cocos2d::Animation* Arthas::ResourceManager::createAnimation(ResourceType animationType)
{
	AnimationInfo animationInfo = GET_DATA_MANAGER()->getAnimationInfo(animationType);
	auto animation = cocos2d::Animation::create();
	animation->setDelayPerUnit(animationInfo.delay);

	for (int i = 0; i < animationInfo.frameNum; ++i)
	{
		auto frame = cocos2d::SpriteFrameCache::getInstance()->getSpriteFrameByName(animationInfo.animationName[i]);

		if (frame == nullptr)
		{
			auto sprite = cocos2d::Sprite::create(animationInfo.animationName[i]);
			animation->addSpriteFrame(sprite->getSpriteFrame());
		}
		else
		{
			animation->addSpriteFrame(frame);
		}
	}
	return animation;
}

cocos2d::Sprite* Arthas::ResourceManager::createSprite(ResourceType spriteType)
{
	SpriteInfo spriteInfo = GET_DATA_MANAGER()->getSpriteInfo(spriteType);
	auto sprite = cocos2d::Sprite::createWithSpriteFrameName(spriteInfo.spriteName);

	if (sprite == nullptr)
	{
		return cocos2d::Sprite::create(spriteInfo.spriteName);
	}
	else
	{
		return sprite;
	}
}

<commit_msg>bug fix<commit_after>#include "pch.h"
#include "GameManager.h"
#include "ResourceManager.h"
#include "DataManager.h"

Arthas::ResourceManager::ResourceManager()
{

}

Arthas::ResourceManager::~ResourceManager()
{

}

bool Arthas::ResourceManager::init()
{
	return true;
}

cocos2d::Animation* Arthas::ResourceManager::createAnimation(ResourceType animationType)
{
	AnimationInfo animationInfo = GET_DATA_MANAGER()->getAnimationInfo(animationType);
	auto animation = cocos2d::Animation::create();
	animation->setDelayPerUnit(animationInfo.delay);

	for (int i = 0; i < animationInfo.frameNum; ++i)
	{
		auto frame = cocos2d::SpriteFrameCache::getInstance()->getSpriteFrameByName(animationInfo.animationName[i]);

		if (frame == nullptr)
		{
			char name[256] = { 0, };

			sprintf(name, "Graphic/%s", animationInfo.animationName[i]);
			auto sprite = cocos2d::Sprite::create(name);
			animation->addSpriteFrame(sprite->getSpriteFrame());
		}
		else
		{
			animation->addSpriteFrame(frame);
		}
	}
	return animation;
}

cocos2d::Sprite* Arthas::ResourceManager::createSprite(ResourceType spriteType)
{
	SpriteInfo spriteInfo = GET_DATA_MANAGER()->getSpriteInfo(spriteType);
	auto sprite = cocos2d::Sprite::createWithSpriteFrameName(spriteInfo.spriteName);

	if (sprite == nullptr)
	{
		char name[256] = { 0, };

		sprintf(name, "Graphic/%s", spriteInfo.spriteName);
		return cocos2d::Sprite::create(name);
	}
	else
	{
		return sprite;
	}
}

<|endoftext|>


<commit_before>#pragma once

#include <atomic>
#include <utility>

class spin_lock {
    std::atomic_flag _flag = ATOMIC_FLAG_INIT;
public:
    void lock() {
        while (_flag.test_and_set(std::memory_order_acquire));
    }

    template <typename F, typename... Args>
    void lock(F func, Args... args) {
        while (_flag.test_and_set(std::memory_order_acquire)) {
            F(std::forward<Args...>(args...));
        }
    }

    bool try_lock() {
        return !_flag.test_and_set(std::memory_order_acquire);
    }

    void unlock() {
        _flag.clear(std::memory_order_release);
    }
};
<commit_msg>Added spinlock with exponential backoff.<commit_after>#pragma once

#include <atomic>
#include <utility>

class spin_lock {
    std::atomic_flag _flag = ATOMIC_FLAG_INIT;
public:
    void lock() {
        while (_flag.test_and_set(std::memory_order_acq_rel))
            asm volatile("pause");
    }

    bool try_lock() {
        return !_flag.test_and_set(std::memory_order_acq_rel);
    }

    void unlock() {
        _flag.clear(std::memory_order_release);
    }
};

class spin_lock_backoff {
    std::atomic_flag _flag = ATOMIC_FLAG_INIT;
public:
    void lock() {
        unsigned backoff = 0;
        while (_flag.test_and_set(std::memory_order_acq_rel)) {
            for(unsigned i = 0; i < (1u << backoff); i++) {
                asm volatile("pause");
            }
            backoff++;
        }
    }

    bool try_lock() {
        return !_flag.test_and_set(std::memory_order_acq_rel);
    }

    void unlock() {
        _flag.clear(std::memory_order_release);
    }
};

<|endoftext|>


<commit_before>/*
 -----------------------------------------------------------------------------
 This source file is part of OGRE
 (Object-oriented Graphics Rendering Engine)
 For the latest info, see http://www.ogre3d.org/

 Copyright (c) 2000-2012 Torus Knot Software Ltd

 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal
 in the Software without restriction, including without limitation the rights
 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 copies of the Software, and to permit persons to whom the Software is
 furnished to do so, subject to the following conditions:

 The above copyright notice and this permission notice shall be included in
 all copies or substantial portions of the Software.

 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 THE SOFTWARE.
 -----------------------------------------------------------------------------
 */
#include "OgrePlatform.h"

#include "SampleBrowser.h"

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
#include "OgreString.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_APPLE
#include "SampleBrowser_OSX.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_APPLE_IOS
#include "SampleBrowser_iOS.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_NACL
#include "SampleBrowser_NaCl.h"
#endif

#if OGRE_PLATFORM != OGRE_PLATFORM_NACL

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
INT WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR cmdLine, INT)
#else
int main(int argc, char *argv[])
#endif
{
#if OGRE_PLATFORM == OGRE_PLATFORM_APPLE_IOS
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
	int retVal = UIApplicationMain(argc, argv, @"UIApplication", @"AppDelegate");
	[pool release];
	return retVal;
#elif (OGRE_PLATFORM == OGRE_PLATFORM_APPLE) && __LP64__
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];

    mAppDelegate = [[AppDelegate alloc] init];
    [[NSApplication sharedApplication] setDelegate:mAppDelegate];
	int retVal = NSApplicationMain(argc, (const char **) argv);

	[pool release];

	return retVal;
#else

	try
	{
        bool nograb = false;
#if OGRE_PLATFORM != OGRE_PLATFORM_WIN32
        if (argc >= 2 && Ogre::String(argv[1]) == "nograb")
            nograb = true;
#else
        // somewhat hacky, but much simpler than other solutions
        if (Ogre::String(cmdLine).find("nograb") != Ogre::String::npos)
            nograb = true;
#endif
		OgreBites::SampleBrowser sb (nograb);
		sb.go();
	}
	catch (Ogre::Exception& e)
	{
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
		MessageBoxA(NULL, e.getFullDescription().c_str(), "An exception has occurred!", MB_ICONERROR | MB_TASKMODAL);
#else
		std::cerr << "An exception has occurred: " << e.getFullDescription().c_str() << std::endl;
#endif
	}

#endif
	return 0;
}

#endif
<commit_msg>Fix a redeclaration warning<commit_after>/*
 -----------------------------------------------------------------------------
 This source file is part of OGRE
 (Object-oriented Graphics Rendering Engine)
 For the latest info, see http://www.ogre3d.org/

 Copyright (c) 2000-2012 Torus Knot Software Ltd

 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal
 in the Software without restriction, including without limitation the rights
 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 copies of the Software, and to permit persons to whom the Software is
 furnished to do so, subject to the following conditions:

 The above copyright notice and this permission notice shall be included in
 all copies or substantial portions of the Software.

 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 THE SOFTWARE.
 -----------------------------------------------------------------------------
 */
#include "OgrePlatform.h"

#include "SampleBrowser.h"

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
#include "OgreString.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_APPLE
#include "SampleBrowser_OSX.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_APPLE_IOS
#include "SampleBrowser_iOS.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_NACL
#include "SampleBrowser_NaCl.h"
#endif

#if OGRE_PLATFORM != OGRE_PLATFORM_NACL

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
INT WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR cmdLine, INT)
#else
int main(int argc, char *argv[])
#endif
{
#if OGRE_PLATFORM == OGRE_PLATFORM_APPLE_IOS
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
	int retVal = UIApplicationMain(argc, argv, @"UIApplication", @"AppDelegate");
	[pool release];
	return retVal;
#elif (OGRE_PLATFORM == OGRE_PLATFORM_APPLE) && __LP64__
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];

    mAppDelegate = [[AppDelegate alloc] init];
    [[NSApplication sharedApplication] setDelegate:mAppDelegate];
	int retVal = NSApplicationMain(argc, (const char **) argv);

	[pool release];

	return retVal;
#else

	try
	{
        bool nograb = false;
#if OGRE_PLATFORM != OGRE_PLATFORM_WIN32
        if (argc >= 2 && Ogre::String(argv[1]) == "nograb")
            nograb = true;
#else
        // somewhat hacky, but much simpler than other solutions
        if (Ogre::String(cmdLine).find("nograb") != Ogre::String::npos)
            nograb = true;
#endif
		OgreBites::SampleBrowser brows (nograb);
		brows.go();
	}
	catch (Ogre::Exception& e)
	{
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
		MessageBoxA(NULL, e.getFullDescription().c_str(), "An exception has occurred!", MB_ICONERROR | MB_TASKMODAL);
#else
		std::cerr << "An exception has occurred: " << e.getFullDescription().c_str() << std::endl;
#endif
	}

#endif
	return 0;
}

#endif
<|endoftext|>


<commit_before>// Scintilla source code edit control
/** @file LexDMIS.cxx
 ** Lexer for DMIS.
  **/
// Copyright 1998-2005 by Neil Hodgson <neilh@scintilla.org>
// Copyright 2013-2014 by Andreas Tscharner <andy@vis.ethz.ch>
// The License.txt file describes the conditions under which this software may be distributed.

#include <cstdlib>
#include <cassert>
#include <cstring>
#include <cctype>

#include "ILexer.h"
#include "SciLexer.h"
#include "Scintilla.h"

#include "LexerModule.h"
#include "LexAccessor.h"
#include "StyleContext.h"
#include "CharacterSet.h"
#include "WordList.h"

#ifdef SCI_NAMESPACE
using namespace Scintilla;
#endif

static const char *const DMISWordListDesc[] = {
	"DMIS Major Words",
	"DMIS Minor Words",
	"Unsupported DMIS Major Words",
	"Unsupported DMIS Minor Words",
	"Keywords for code folding start",
	"Corresponding keywords for code folding end",
	0
};

class LexerDMIS : public ILexer
{
	private:
		char *m_wordListSets;
		WordList m_majorWords;
		WordList m_minorWords;
		WordList m_unsupportedMajor;
		WordList m_unsupportedMinor;
		WordList m_codeFoldingStart;
		WordList m_codeFoldingEnd;

		char * SCI_METHOD UpperCase(char *item);
		void SCI_METHOD InitWordListSets(void);

	public:
		LexerDMIS(void);
		virtual ~LexerDMIS(void);

		int SCI_METHOD Version() const {
			return lvOriginal;
		}

		void SCI_METHOD Release() {
			delete this;
		}

		const char * SCI_METHOD PropertyNames() {
			return NULL;
		}

		int SCI_METHOD PropertyType(const char *) {
			return -1;
		}

		const char * SCI_METHOD DescribeProperty(const char *) {
			return NULL;
		}

		int SCI_METHOD PropertySet(const char *, const char *) {
			return -1;
		}

		int SCI_METHOD WordListSet(int n, const char *wl);

		void * SCI_METHOD PrivateCall(int, void *) {
			return NULL;
		}

		static ILexer *LexerFactoryDMIS() {
			return new LexerDMIS;
		}

		const char * SCI_METHOD DescribeWordListSets();
		void SCI_METHOD Lex(unsigned int startPos, int lengthDoc, int initStyle, IDocument *pAccess);
		void SCI_METHOD Fold(unsigned int startPos, int lengthDoc, int initStyle, IDocument *pAccess);
};

char * SCI_METHOD LexerDMIS::UpperCase(char *item)
{
	char *itemStart;

	itemStart = item;
	while (item && *item) {
		*item = toupper(*item);
		item++;
	};
	return itemStart;
}

void SCI_METHOD LexerDMIS::InitWordListSets(void)
{
	size_t totalLen = 0;

	for (int i=0; DMISWordListDesc[i]; i++) {
		totalLen += strlen(DMISWordListDesc[i]);
		totalLen++;
	};

	totalLen++;
	this->m_wordListSets = new char[totalLen];
	memset(this->m_wordListSets, 0, totalLen);

	for (int i=0; DMISWordListDesc[i]; i++) {
		strcat(this->m_wordListSets, DMISWordListDesc[i]);
		strcat(this->m_wordListSets, "\n");
	};
}

LexerDMIS::LexerDMIS(void) {
	this->InitWordListSets();

	this->m_majorWords.Clear();
	this->m_minorWords.Clear();
	this->m_unsupportedMajor.Clear();
	this->m_unsupportedMinor.Clear();
	this->m_codeFoldingStart.Clear();
	this->m_codeFoldingEnd.Clear();
}

LexerDMIS::~LexerDMIS(void) {
	delete[] this->m_wordListSets;
}

int SCI_METHOD LexerDMIS::WordListSet(int n, const char *wl)
{
	switch (n) {
		case 0:
			this->m_majorWords.Clear();
			this->m_majorWords.Set(wl);
			break;
		case 1:
			this->m_minorWords.Clear();
			this->m_minorWords.Set(wl);
			break;
		case 2:
			this->m_unsupportedMajor.Clear();
			this->m_unsupportedMajor.Set(wl);
			break;
		case 3:
			this->m_unsupportedMinor.Clear();
			this->m_unsupportedMinor.Set(wl);
			break;
		case 4:
			this->m_codeFoldingStart.Clear();
			this->m_codeFoldingStart.Set(wl);
			break;
		case 5:
			this->m_codeFoldingEnd.Clear();
			this->m_codeFoldingEnd.Set(wl);
			break;
		default:
			return -1;
			break;
	}

	return 0;
}

const char * SCI_METHOD LexerDMIS::DescribeWordListSets()
{
	return this->m_wordListSets;
}

void SCI_METHOD LexerDMIS::Lex(unsigned int startPos, int lengthDoc, int initStyle, IDocument *pAccess)
{
	const unsigned int MAX_STR_LEN = 100;

	LexAccessor styler(pAccess);
	StyleContext scCTX(startPos, lengthDoc, initStyle, styler);
	CharacterSet setDMISNumber(CharacterSet::setDigits, ".-+eE");
	CharacterSet setDMISWordStart(CharacterSet::setAlpha, "-234", 0x80, true);
	CharacterSet setDMISWord(CharacterSet::setAlpha);

	bool isIFLine = false;

	for (; scCTX.More(); scCTX.Forward()) {
		if (scCTX.atLineEnd) {
			isIFLine = false;
		};

		switch (scCTX.state) {
			case SCE_DMIS_DEFAULT:
				if (scCTX.Match('$', '$')) {
					scCTX.SetState(SCE_DMIS_COMMENT);
					scCTX.Forward();
				};
				if (scCTX.Match('\'')) {
					scCTX.SetState(SCE_DMIS_STRING);
				};
				if (IsADigit(scCTX.ch) || ((scCTX.Match('-') || scCTX.Match('+')) && IsADigit(scCTX.chNext))) {
					scCTX.SetState(SCE_DMIS_NUMBER);
					break;
				};
				if (setDMISWordStart.Contains(scCTX.ch)) {
					scCTX.SetState(SCE_DMIS_KEYWORD);
				};
				if (scCTX.Match('(') && (!isIFLine)) {
					scCTX.SetState(SCE_DMIS_LABEL);
				};
				break;

			case SCE_DMIS_COMMENT:
				if (scCTX.atLineEnd) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;

			case SCE_DMIS_STRING:
				if (scCTX.Match('\'')) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;

			case SCE_DMIS_NUMBER:
				if (!setDMISNumber.Contains(scCTX.ch)) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;

			case SCE_DMIS_KEYWORD:
				if (!setDMISWord.Contains(scCTX.ch)) {
					char tmpStr[MAX_STR_LEN];
					memset(tmpStr, 0, MAX_STR_LEN*sizeof(char));
					scCTX.GetCurrent(tmpStr, (MAX_STR_LEN-1));
					strncpy(tmpStr, this->UpperCase(tmpStr), (MAX_STR_LEN-1));

					if (this->m_minorWords.InList(tmpStr)) {
						scCTX.ChangeState(SCE_DMIS_MINORWORD);
					};
					if (this->m_majorWords.InList(tmpStr)) {
						isIFLine = (strcmp(tmpStr, "IF") == 0);
						scCTX.ChangeState(SCE_DMIS_MAJORWORD);
					};
					if (this->m_unsupportedMajor.InList(tmpStr)) {
						scCTX.ChangeState(SCE_DMIS_UNSUPPORTED_MAJOR);
					};
					if (this->m_unsupportedMinor.InList(tmpStr)) {
						scCTX.ChangeState(SCE_DMIS_UNSUPPORTED_MINOR);
					};

					if (scCTX.Match('(') && (isIFLine)) {
						scCTX.SetState(SCE_DMIS_LABEL);
					} else {
						scCTX.SetState(SCE_DMIS_DEFAULT);
					};
				};
				break;

			case SCE_DMIS_LABEL:
				if (scCTX.Match(')')) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;
		};
	};
	scCTX.Complete();
}

void SCI_METHOD LexerDMIS::Fold(unsigned int startPos, int lengthDoc, int, IDocument *pAccess)
{
	const int MAX_STR_LEN = 100;

	LexAccessor styler(pAccess);
	unsigned int endPos = startPos + lengthDoc;
	char chNext = styler[startPos];
	int lineCurrent = styler.GetLine(startPos);
	int levelPrev = styler.LevelAt(lineCurrent) & SC_FOLDLEVELNUMBERMASK;
	int levelCurrent = levelPrev;
	int strPos = 0;
	bool foldWordPossible = false;
	CharacterSet setDMISFoldWord(CharacterSet::setAlpha);
	char *tmpStr;

	tmpStr = new char[MAX_STR_LEN];
	memset(tmpStr, 0, MAX_STR_LEN*sizeof(char));

	for (unsigned int i=startPos; i<endPos; i++) {
		char ch = chNext;
		chNext = styler.SafeGetCharAt(i+1);

		bool atEOL = ((ch == '\r' && chNext != '\n') || (ch == '\n'));

		if (strPos >= (MAX_STR_LEN-1)) {
			strPos = MAX_STR_LEN-1;
		};

		int style = styler.StyleAt(i);
		bool noFoldPos = ((style == SCE_DMIS_COMMENT) || (style == SCE_DMIS_STRING));

		if (foldWordPossible) {
			if (setDMISFoldWord.Contains(ch)) {
				tmpStr[strPos++] = ch;
			} else {
				tmpStr = this->UpperCase(tmpStr);
				if (this->m_codeFoldingStart.InList(tmpStr) && (!noFoldPos)) {
					levelCurrent++;
				};
				if (this->m_codeFoldingEnd.InList(tmpStr) && (!noFoldPos)) {
					levelCurrent--;
				};
				memset(tmpStr, 0, MAX_STR_LEN*sizeof(char));
				strPos = 0;
				foldWordPossible = false;
			};
		} else {
			if (setDMISFoldWord.Contains(ch)) {
				tmpStr[strPos++] = ch;
				foldWordPossible = true;
			};
		};

		if (atEOL || (i == (endPos-1))) {
			int lev = levelPrev;

			if (levelCurrent > levelPrev) {
				lev |= SC_FOLDLEVELHEADERFLAG;
			};
			if (lev != styler.LevelAt(lineCurrent)) {
				styler.SetLevel(lineCurrent, lev);
			};
			lineCurrent++;
			levelPrev = levelCurrent;
		};
	};
	delete[] tmpStr;
}

LexerModule lmDMIS(SCLEX_DMIS, LexerDMIS::LexerFactoryDMIS, "DMIS", DMISWordListDesc);
<commit_msg>Add missing not sign to fix DMIS label highlighting<commit_after>// Scintilla source code edit control
/** @file LexDMIS.cxx
 ** Lexer for DMIS.
  **/
// Copyright 1998-2005 by Neil Hodgson <neilh@scintilla.org>
// Copyright 2013-2014 by Andreas Tscharner <andy@vis.ethz.ch>
// The License.txt file describes the conditions under which this software may be distributed.

#include <cstdlib>
#include <cassert>
#include <cstring>
#include <cctype>

#include "ILexer.h"
#include "SciLexer.h"
#include "Scintilla.h"

#include "LexerModule.h"
#include "LexAccessor.h"
#include "StyleContext.h"
#include "CharacterSet.h"
#include "WordList.h"

#ifdef SCI_NAMESPACE
using namespace Scintilla;
#endif

static const char *const DMISWordListDesc[] = {
	"DMIS Major Words",
	"DMIS Minor Words",
	"Unsupported DMIS Major Words",
	"Unsupported DMIS Minor Words",
	"Keywords for code folding start",
	"Corresponding keywords for code folding end",
	0
};

class LexerDMIS : public ILexer
{
	private:
		char *m_wordListSets;
		WordList m_majorWords;
		WordList m_minorWords;
		WordList m_unsupportedMajor;
		WordList m_unsupportedMinor;
		WordList m_codeFoldingStart;
		WordList m_codeFoldingEnd;

		char * SCI_METHOD UpperCase(char *item);
		void SCI_METHOD InitWordListSets(void);

	public:
		LexerDMIS(void);
		virtual ~LexerDMIS(void);

		int SCI_METHOD Version() const {
			return lvOriginal;
		}

		void SCI_METHOD Release() {
			delete this;
		}

		const char * SCI_METHOD PropertyNames() {
			return NULL;
		}

		int SCI_METHOD PropertyType(const char *) {
			return -1;
		}

		const char * SCI_METHOD DescribeProperty(const char *) {
			return NULL;
		}

		int SCI_METHOD PropertySet(const char *, const char *) {
			return -1;
		}

		int SCI_METHOD WordListSet(int n, const char *wl);

		void * SCI_METHOD PrivateCall(int, void *) {
			return NULL;
		}

		static ILexer *LexerFactoryDMIS() {
			return new LexerDMIS;
		}

		const char * SCI_METHOD DescribeWordListSets();
		void SCI_METHOD Lex(unsigned int startPos, int lengthDoc, int initStyle, IDocument *pAccess);
		void SCI_METHOD Fold(unsigned int startPos, int lengthDoc, int initStyle, IDocument *pAccess);
};

char * SCI_METHOD LexerDMIS::UpperCase(char *item)
{
	char *itemStart;

	itemStart = item;
	while (item && *item) {
		*item = toupper(*item);
		item++;
	};
	return itemStart;
}

void SCI_METHOD LexerDMIS::InitWordListSets(void)
{
	size_t totalLen = 0;

	for (int i=0; DMISWordListDesc[i]; i++) {
		totalLen += strlen(DMISWordListDesc[i]);
		totalLen++;
	};

	totalLen++;
	this->m_wordListSets = new char[totalLen];
	memset(this->m_wordListSets, 0, totalLen);

	for (int i=0; DMISWordListDesc[i]; i++) {
		strcat(this->m_wordListSets, DMISWordListDesc[i]);
		strcat(this->m_wordListSets, "\n");
	};
}

LexerDMIS::LexerDMIS(void) {
	this->InitWordListSets();

	this->m_majorWords.Clear();
	this->m_minorWords.Clear();
	this->m_unsupportedMajor.Clear();
	this->m_unsupportedMinor.Clear();
	this->m_codeFoldingStart.Clear();
	this->m_codeFoldingEnd.Clear();
}

LexerDMIS::~LexerDMIS(void) {
	delete[] this->m_wordListSets;
}

int SCI_METHOD LexerDMIS::WordListSet(int n, const char *wl)
{
	switch (n) {
		case 0:
			this->m_majorWords.Clear();
			this->m_majorWords.Set(wl);
			break;
		case 1:
			this->m_minorWords.Clear();
			this->m_minorWords.Set(wl);
			break;
		case 2:
			this->m_unsupportedMajor.Clear();
			this->m_unsupportedMajor.Set(wl);
			break;
		case 3:
			this->m_unsupportedMinor.Clear();
			this->m_unsupportedMinor.Set(wl);
			break;
		case 4:
			this->m_codeFoldingStart.Clear();
			this->m_codeFoldingStart.Set(wl);
			break;
		case 5:
			this->m_codeFoldingEnd.Clear();
			this->m_codeFoldingEnd.Set(wl);
			break;
		default:
			return -1;
			break;
	}

	return 0;
}

const char * SCI_METHOD LexerDMIS::DescribeWordListSets()
{
	return this->m_wordListSets;
}

void SCI_METHOD LexerDMIS::Lex(unsigned int startPos, int lengthDoc, int initStyle, IDocument *pAccess)
{
	const unsigned int MAX_STR_LEN = 100;

	LexAccessor styler(pAccess);
	StyleContext scCTX(startPos, lengthDoc, initStyle, styler);
	CharacterSet setDMISNumber(CharacterSet::setDigits, ".-+eE");
	CharacterSet setDMISWordStart(CharacterSet::setAlpha, "-234", 0x80, true);
	CharacterSet setDMISWord(CharacterSet::setAlpha);

	bool isIFLine = false;

	for (; scCTX.More(); scCTX.Forward()) {
		if (scCTX.atLineEnd) {
			isIFLine = false;
		};

		switch (scCTX.state) {
			case SCE_DMIS_DEFAULT:
				if (scCTX.Match('$', '$')) {
					scCTX.SetState(SCE_DMIS_COMMENT);
					scCTX.Forward();
				};
				if (scCTX.Match('\'')) {
					scCTX.SetState(SCE_DMIS_STRING);
				};
				if (IsADigit(scCTX.ch) || ((scCTX.Match('-') || scCTX.Match('+')) && IsADigit(scCTX.chNext))) {
					scCTX.SetState(SCE_DMIS_NUMBER);
					break;
				};
				if (setDMISWordStart.Contains(scCTX.ch)) {
					scCTX.SetState(SCE_DMIS_KEYWORD);
				};
				if (scCTX.Match('(') && (!isIFLine)) {
					scCTX.SetState(SCE_DMIS_LABEL);
				};
				break;

			case SCE_DMIS_COMMENT:
				if (scCTX.atLineEnd) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;

			case SCE_DMIS_STRING:
				if (scCTX.Match('\'')) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;

			case SCE_DMIS_NUMBER:
				if (!setDMISNumber.Contains(scCTX.ch)) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;

			case SCE_DMIS_KEYWORD:
				if (!setDMISWord.Contains(scCTX.ch)) {
					char tmpStr[MAX_STR_LEN];
					memset(tmpStr, 0, MAX_STR_LEN*sizeof(char));
					scCTX.GetCurrent(tmpStr, (MAX_STR_LEN-1));
					strncpy(tmpStr, this->UpperCase(tmpStr), (MAX_STR_LEN-1));

					if (this->m_minorWords.InList(tmpStr)) {
						scCTX.ChangeState(SCE_DMIS_MINORWORD);
					};
					if (this->m_majorWords.InList(tmpStr)) {
						isIFLine = (strcmp(tmpStr, "IF") == 0);
						scCTX.ChangeState(SCE_DMIS_MAJORWORD);
					};
					if (this->m_unsupportedMajor.InList(tmpStr)) {
						scCTX.ChangeState(SCE_DMIS_UNSUPPORTED_MAJOR);
					};
					if (this->m_unsupportedMinor.InList(tmpStr)) {
						scCTX.ChangeState(SCE_DMIS_UNSUPPORTED_MINOR);
					};

					if (scCTX.Match('(') && (!isIFLine)) {
						scCTX.SetState(SCE_DMIS_LABEL);
					} else {
						scCTX.SetState(SCE_DMIS_DEFAULT);
					};
				};
				break;

			case SCE_DMIS_LABEL:
				if (scCTX.Match(')')) {
					scCTX.SetState(SCE_DMIS_DEFAULT);
				};
				break;
		};
	};
	scCTX.Complete();
}

void SCI_METHOD LexerDMIS::Fold(unsigned int startPos, int lengthDoc, int, IDocument *pAccess)
{
	const int MAX_STR_LEN = 100;

	LexAccessor styler(pAccess);
	unsigned int endPos = startPos + lengthDoc;
	char chNext = styler[startPos];
	int lineCurrent = styler.GetLine(startPos);
	int levelPrev = styler.LevelAt(lineCurrent) & SC_FOLDLEVELNUMBERMASK;
	int levelCurrent = levelPrev;
	int strPos = 0;
	bool foldWordPossible = false;
	CharacterSet setDMISFoldWord(CharacterSet::setAlpha);
	char *tmpStr;

	tmpStr = new char[MAX_STR_LEN];
	memset(tmpStr, 0, MAX_STR_LEN*sizeof(char));

	for (unsigned int i=startPos; i<endPos; i++) {
		char ch = chNext;
		chNext = styler.SafeGetCharAt(i+1);

		bool atEOL = ((ch == '\r' && chNext != '\n') || (ch == '\n'));

		if (strPos >= (MAX_STR_LEN-1)) {
			strPos = MAX_STR_LEN-1;
		};

		int style = styler.StyleAt(i);
		bool noFoldPos = ((style == SCE_DMIS_COMMENT) || (style == SCE_DMIS_STRING));

		if (foldWordPossible) {
			if (setDMISFoldWord.Contains(ch)) {
				tmpStr[strPos++] = ch;
			} else {
				tmpStr = this->UpperCase(tmpStr);
				if (this->m_codeFoldingStart.InList(tmpStr) && (!noFoldPos)) {
					levelCurrent++;
				};
				if (this->m_codeFoldingEnd.InList(tmpStr) && (!noFoldPos)) {
					levelCurrent--;
				};
				memset(tmpStr, 0, MAX_STR_LEN*sizeof(char));
				strPos = 0;
				foldWordPossible = false;
			};
		} else {
			if (setDMISFoldWord.Contains(ch)) {
				tmpStr[strPos++] = ch;
				foldWordPossible = true;
			};
		};

		if (atEOL || (i == (endPos-1))) {
			int lev = levelPrev;

			if (levelCurrent > levelPrev) {
				lev |= SC_FOLDLEVELHEADERFLAG;
			};
			if (lev != styler.LevelAt(lineCurrent)) {
				styler.SetLevel(lineCurrent, lev);
			};
			lineCurrent++;
			levelPrev = levelCurrent;
		};
	};
	delete[] tmpStr;
}

LexerModule lmDMIS(SCLEX_DMIS, LexerDMIS::LexerFactoryDMIS, "DMIS", DMISWordListDesc);
<|endoftext|>


<commit_before>/*
 -----------------------------------------------------------------------------
 This source file is part of OGRE
 (Object-oriented Graphics Rendering Engine)
 For the latest info, see http://www.ogre3d.org/

 Copyright (c) 2000-2009 Torus Knot Software Ltd

 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal
 in the Software without restriction, including without limitation the rights
 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 copies of the Software, and to permit persons to whom the Software is
 furnished to do so, subject to the following conditions:

 The above copyright notice and this permission notice shall be included in
 all copies or substantial portions of the Software.

 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 THE SOFTWARE.
 -----------------------------------------------------------------------------
 */
#include "OgrePlatform.h"
#if OGRE_PLATFORM == OGRE_PLATFORM_SYMBIAN
#include <coecntrl.h>
#endif

#include "SampleBrowser.h"

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_IPHONE
#import <UIKit/UIKit.h>
#import <QuartzCore/QuartzCore.h>

// To use CADisplayLink for smoother animation on iPhone comment out
// the following line or define it to 1.  Use with caution, it can
// sometimes cause input lag.
#define USE_CADISPLAYLINK 1
#endif

#if OGRE_PLATFORM != OGRE_PLATFORM_SYMBIAN

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
INT WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, INT)
#else
int main(int argc, char *argv[])
#endif
{
#if OGRE_PLATFORM == OGRE_PLATFORM_IPHONE
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
	int retVal = UIApplicationMain(argc, argv, @"UIApplication", @"AppDelegate");
	[pool release];
	return retVal;
#else

	try
	{
		OgreBites::SampleBrowser sb;
		sb.go();
	}
	catch (Ogre::Exception& e)
	{
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
		MessageBoxA(NULL, e.getFullDescription().c_str(), "An exception has occurred!", MB_ICONERROR | MB_TASKMODAL);
#else
		std::cerr << "An exception has occurred: " << e.getFullDescription().c_str() << std::endl;
#endif
	}

#endif
	return 0;
}

#endif // OGRE_PLATFORM != OGRE_PLATFORM_SYMBIAN

#if OGRE_PLATFORM == OGRE_PLATFORM_IPHONE
#   ifdef __OBJC__
@interface AppDelegate : NSObject <UIApplicationDelegate>
{
    NSTimer *mTimer;
    OgreBites::SampleBrowser sb;

    // Use of the CADisplayLink class is the preferred method for controlling your animation timing.
    // CADisplayLink will link to the main display and fire every vsync when added to a given run-loop.
    // The NSTimer class is used only as fallback when running on a pre 3.1 device where CADisplayLink
    // isn't available.
    id mDisplayLink;
    NSDate* mDate;
    NSTimeInterval mLastFrameTime;
    BOOL mDisplayLinkSupported;
}

- (void)go;
- (void)renderOneFrame:(id)sender;

@property (retain) NSTimer *mTimer;
@property (nonatomic) NSTimeInterval mLastFrameTime;

@end

@implementation AppDelegate

@synthesize mTimer;
@dynamic mLastFrameTime;

- (NSTimeInterval)mLastFrameTime
{
    return mLastFrameTime;
}

- (void)setLastFrameTime:(NSTimeInterval)frameInterval
{
    // Frame interval defines how many display frames must pass between each time the
    // display link fires. The display link will only fire 30 times a second when the
    // frame internal is two on a display that refreshes 60 times a second. The default
    // frame interval setting of one will fire 60 times a second when the display refreshes
    // at 60 times a second. A frame interval setting of less than one results in undefined
    // behavior.
    if (frameInterval >= 1)
    {
        mLastFrameTime = frameInterval;
    }
}

- (void)go {

    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];

    try {
        sb.initApp();

        mTimer = [NSTimer scheduledTimerWithTimeInterval:(NSTimeInterval)(1.0f / 60.0f)
                                                  target:self
                                                selector:@selector(renderOneFrame:)
                                                userInfo:nil
                                                 repeats:YES];
    } catch( Ogre::Exception& e ) {
        std::cerr << "An exception has occurred: " <<
        e.getFullDescription().c_str() << std::endl;
    }

    if (mDisplayLinkSupported)
    {
        // CADisplayLink is API new to iPhone SDK 3.1. Compiling against earlier versions will result in a warning, but can be dismissed
        // if the system version runtime check for CADisplayLink exists in -initWithCoder:. The runtime check ensures this code will
        // not be called in system versions earlier than 3.1.
        mDate = [[NSDate alloc] init];
        mLastFrameTime = -[mDate timeIntervalSinceNow];

        mDisplayLink = [NSClassFromString(@"CADisplayLink") displayLinkWithTarget:self selector:@selector(renderOneFrame:)];
        [mDisplayLink setFrameInterval:mLastFrameTime];
        [mDisplayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
    }
    else
    {
        mTimer = [NSTimer scheduledTimerWithTimeInterval:(NSTimeInterval)(1.0f / 60.0f) * mLastFrameTime
                                                  target:self
                                                selector:@selector(renderOneFrame:)
                                                userInfo:nil
                                                 repeats:YES];
    }

    [pool release];
}

- (void)applicationDidFinishLaunching:(UIApplication *)application {
    // Hide the status bar
    [[UIApplication sharedApplication] setStatusBarHidden:YES];

    mDisplayLinkSupported = FALSE;
    mLastFrameTime = 1;
    mDisplayLink = nil;
    mTimer = nil;

    // A system version of 3.1 or greater is required to use CADisplayLink. The NSTimer
    // class is used as fallback when it isn't available.
#if USE_CADISPLAYLINK
    NSString *reqSysVer = @"3.1";
    NSString *currSysVer = [[UIDevice currentDevice] systemVersion];
    if ([currSysVer compare:reqSysVer options:NSNumericSearch] != NSOrderedAscending)
        mDisplayLinkSupported = TRUE;
#endif

    [self go];
}

- (void)renderOneFrame:(id)sender
{
    [sb.mGestureView becomeFirstResponder];

    if (mDisplayLinkSupported)
    {
        // NSTimerInterval is a simple typedef for double
        NSTimeInterval currentFrameTime = -[mDate timeIntervalSinceNow];
        NSTimeInterval differenceInSeconds = currentFrameTime - mLastFrameTime;
        mLastFrameTime = currentFrameTime;

        Root::getSingleton().renderOneFrame((Real)differenceInSeconds);
    }
    else
    {
        Root::getSingleton().renderOneFrame((Real)[mTimer timeInterval]);
    }
}

- (void)applicationWillTerminate:(UIApplication *)application {
    sb.closeApp();
}

- (void)dealloc {
    if (mDisplayLinkSupported)
    {
        [mDate release];
        mDate = nil;

        [mDisplayLink invalidate];
        mDisplayLink = nil;
    }
    else
    {
        [mTimer invalidate];
        mTimer = nil;
    }

    [super dealloc];
}

@end
#   endif

#endif
<commit_msg>iOS: Remove an extra timer init in the sample browser<commit_after>/*
 -----------------------------------------------------------------------------
 This source file is part of OGRE
 (Object-oriented Graphics Rendering Engine)
 For the latest info, see http://www.ogre3d.org/

 Copyright (c) 2000-2009 Torus Knot Software Ltd

 Permission is hereby granted, free of charge, to any person obtaining a copy
 of this software and associated documentation files (the "Software"), to deal
 in the Software without restriction, including without limitation the rights
 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 copies of the Software, and to permit persons to whom the Software is
 furnished to do so, subject to the following conditions:

 The above copyright notice and this permission notice shall be included in
 all copies or substantial portions of the Software.

 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 THE SOFTWARE.
 -----------------------------------------------------------------------------
 */
#include "OgrePlatform.h"
#if OGRE_PLATFORM == OGRE_PLATFORM_SYMBIAN
#include <coecntrl.h>
#endif

#include "SampleBrowser.h"

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
#define WIN32_LEAN_AND_MEAN
#include "windows.h"
#elif OGRE_PLATFORM == OGRE_PLATFORM_IPHONE
#import <UIKit/UIKit.h>
#import <QuartzCore/QuartzCore.h>

// To use CADisplayLink for smoother animation on iPhone comment out
// the following line or define it to 1.  Use with caution, it can
// sometimes cause input lag.
#define USE_CADISPLAYLINK 1
#endif

#if OGRE_PLATFORM != OGRE_PLATFORM_SYMBIAN

#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
INT WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, INT)
#else
int main(int argc, char *argv[])
#endif
{
#if OGRE_PLATFORM == OGRE_PLATFORM_IPHONE
	NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];
	int retVal = UIApplicationMain(argc, argv, @"UIApplication", @"AppDelegate");
	[pool release];
	return retVal;
#else

	try
	{
		OgreBites::SampleBrowser sb;
		sb.go();
	}
	catch (Ogre::Exception& e)
	{
#if OGRE_PLATFORM == OGRE_PLATFORM_WIN32
		MessageBoxA(NULL, e.getFullDescription().c_str(), "An exception has occurred!", MB_ICONERROR | MB_TASKMODAL);
#else
		std::cerr << "An exception has occurred: " << e.getFullDescription().c_str() << std::endl;
#endif
	}

#endif
	return 0;
}

#endif // OGRE_PLATFORM != OGRE_PLATFORM_SYMBIAN

#if OGRE_PLATFORM == OGRE_PLATFORM_IPHONE
#   ifdef __OBJC__
@interface AppDelegate : NSObject <UIApplicationDelegate>
{
    NSTimer *mTimer;
    OgreBites::SampleBrowser sb;

    // Use of the CADisplayLink class is the preferred method for controlling your animation timing.
    // CADisplayLink will link to the main display and fire every vsync when added to a given run-loop.
    // The NSTimer class is used only as fallback when running on a pre 3.1 device where CADisplayLink
    // isn't available.
    id mDisplayLink;
    NSDate* mDate;
    NSTimeInterval mLastFrameTime;
    BOOL mDisplayLinkSupported;
}

- (void)go;
- (void)renderOneFrame:(id)sender;

@property (retain) NSTimer *mTimer;
@property (nonatomic) NSTimeInterval mLastFrameTime;

@end

@implementation AppDelegate

@synthesize mTimer;
@dynamic mLastFrameTime;

- (NSTimeInterval)mLastFrameTime
{
    return mLastFrameTime;
}

- (void)setLastFrameTime:(NSTimeInterval)frameInterval
{
    // Frame interval defines how many display frames must pass between each time the
    // display link fires. The display link will only fire 30 times a second when the
    // frame internal is two on a display that refreshes 60 times a second. The default
    // frame interval setting of one will fire 60 times a second when the display refreshes
    // at 60 times a second. A frame interval setting of less than one results in undefined
    // behavior.
    if (frameInterval >= 1)
    {
        mLastFrameTime = frameInterval;
    }
}

- (void)go {

    NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init];

    try {
        sb.initApp();
    } catch( Ogre::Exception& e ) {
        std::cerr << "An exception has occurred: " <<
        e.getFullDescription().c_str() << std::endl;
    }

    if (mDisplayLinkSupported)
    {
        // CADisplayLink is API new to iPhone SDK 3.1. Compiling against earlier versions will result in a warning, but can be dismissed
        // if the system version runtime check for CADisplayLink exists in -initWithCoder:. The runtime check ensures this code will
        // not be called in system versions earlier than 3.1.
        mDate = [[NSDate alloc] init];
        mLastFrameTime = -[mDate timeIntervalSinceNow];

        mDisplayLink = [NSClassFromString(@"CADisplayLink") displayLinkWithTarget:self selector:@selector(renderOneFrame:)];
        [mDisplayLink setFrameInterval:(1.0f/60.0f)];
        [mDisplayLink addToRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
    }
    else
    {
        mTimer = [NSTimer scheduledTimerWithTimeInterval:(NSTimeInterval)(1.0f / 60.0f) * mLastFrameTime
                                                  target:self
                                                selector:@selector(renderOneFrame:)
                                                userInfo:nil
                                                 repeats:YES];
    }

    [pool release];
}

- (void)applicationDidFinishLaunching:(UIApplication *)application {
    // Hide the status bar
    [[UIApplication sharedApplication] setStatusBarHidden:YES];

    mDisplayLinkSupported = NO;
    mLastFrameTime = 1;
    mDisplayLink = nil;
    mTimer = nil;

    // A system version of 3.1 or greater is required to use CADisplayLink. The NSTimer
    // class is used as fallback when it isn't available.
#if USE_CADISPLAYLINK
    NSString *reqSysVer = @"3.1";
    NSString *currSysVer = [[UIDevice currentDevice] systemVersion];
    if ([currSysVer compare:reqSysVer options:NSNumericSearch] != NSOrderedAscending)
        mDisplayLinkSupported = YES;
#endif

    [self go];
}

- (void)renderOneFrame:(id)sender
{
    [sb.mGestureView becomeFirstResponder];

    if (mDisplayLinkSupported)
    {
        // NSTimerInterval is a simple typedef for double
        NSTimeInterval currentFrameTime = -[mDate timeIntervalSinceNow];
        NSTimeInterval differenceInSeconds = currentFrameTime - mLastFrameTime;
        mLastFrameTime = currentFrameTime;

        Root::getSingleton().renderOneFrame((Real)differenceInSeconds);
    }
    else
    {
        Root::getSingleton().renderOneFrame((Real)[mTimer timeInterval]);
    }
}

- (void)applicationWillTerminate:(UIApplication *)application {
    sb.closeApp();
}

- (void)dealloc {
    if (mDisplayLinkSupported)
    {
        [mDate release];
        mDate = nil;

        [mDisplayLink invalidate];
        mDisplayLink = nil;
    }
    else
    {
        [mTimer invalidate];
        mTimer = nil;
    }

    [super dealloc];
}

@end
#   endif

#endif
<|endoftext|>


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

#include "net/third_party/quiche/src/quic/core/congestion_control/bbr2_misc.h"

#include "net/third_party/quiche/src/quic/core/congestion_control/bandwidth_sampler.h"
#include "net/third_party/quiche/src/quic/core/quic_bandwidth.h"
#include "net/third_party/quiche/src/quic/core/quic_time.h"
#include "net/third_party/quiche/src/quic/core/quic_types.h"
#include "net/third_party/quiche/src/quic/platform/api/quic_logging.h"

namespace quic {

RoundTripCounter::RoundTripCounter() : round_trip_count_(0) {}

void RoundTripCounter::OnPacketSent(QuicPacketNumber packet_number) {
  DCHECK(!last_sent_packet_.IsInitialized() ||
         last_sent_packet_ < packet_number);
  last_sent_packet_ = packet_number;
}

bool RoundTripCounter::OnPacketsAcked(QuicPacketNumber last_acked_packet) {
  if (!end_of_round_trip_.IsInitialized() ||
      last_acked_packet > end_of_round_trip_) {
    round_trip_count_++;
    end_of_round_trip_ = last_sent_packet_;
    return true;
  }
  return false;
}

void RoundTripCounter::RestartRound() {
  end_of_round_trip_ = last_sent_packet_;
}

MinRttFilter::MinRttFilter(QuicTime::Delta initial_min_rtt,
                           QuicTime initial_min_rtt_timestamp)
    : min_rtt_(initial_min_rtt),
      min_rtt_timestamp_(initial_min_rtt_timestamp) {}

void MinRttFilter::Update(QuicTime::Delta sample_rtt, QuicTime now) {
  if (sample_rtt < min_rtt_ || min_rtt_timestamp_ == QuicTime::Zero()) {
    min_rtt_ = sample_rtt;
    min_rtt_timestamp_ = now;
  }
}

void MinRttFilter::ForceUpdate(QuicTime::Delta sample_rtt, QuicTime now) {
  min_rtt_ = sample_rtt;
  min_rtt_timestamp_ = now;
}

Bbr2NetworkModel::Bbr2NetworkModel(const Bbr2Params* params,
                                   QuicTime::Delta initial_rtt,
                                   QuicTime initial_rtt_timestamp,
                                   float cwnd_gain,
                                   float pacing_gain,
                                   const BandwidthSampler* old_sampler)
    : params_(params),
      bandwidth_sampler_([](QuicRoundTripCount max_height_tracker_window_length,
                            const BandwidthSampler* old_sampler) {
        if (old_sampler != nullptr) {
          return BandwidthSampler(*old_sampler);
        }
        return BandwidthSampler(/*unacked_packet_map=*/nullptr,
                                max_height_tracker_window_length);
      }(params->initial_max_ack_height_filter_window, old_sampler)),
      min_rtt_filter_(initial_rtt, initial_rtt_timestamp),
      cwnd_gain_(cwnd_gain),
      pacing_gain_(pacing_gain) {}

void Bbr2NetworkModel::OnPacketSent(QuicTime sent_time,
                                    QuicByteCount bytes_in_flight,
                                    QuicPacketNumber packet_number,
                                    QuicByteCount bytes,
                                    HasRetransmittableData is_retransmittable) {
  round_trip_counter_.OnPacketSent(packet_number);

  bandwidth_sampler_.OnPacketSent(sent_time, packet_number, bytes,
                                  bytes_in_flight, is_retransmittable);
}

void Bbr2NetworkModel::OnCongestionEventStart(
    QuicTime event_time,
    const AckedPacketVector& acked_packets,
    const LostPacketVector& lost_packets,
    Bbr2CongestionEvent* congestion_event) {
  const QuicByteCount prior_bytes_acked = total_bytes_acked();
  const QuicByteCount prior_bytes_lost = total_bytes_lost();

  congestion_event->event_time = event_time;
  congestion_event->end_of_round_trip =
      acked_packets.empty() ? false
                            : round_trip_counter_.OnPacketsAcked(
                                  acked_packets.rbegin()->packet_number);

  BandwidthSamplerInterface::CongestionEventSample sample =
      bandwidth_sampler_.OnCongestionEvent(event_time, acked_packets,
                                           lost_packets, MaxBandwidth(),
                                           bandwidth_lo(), RoundTripCount());

  if (sample.last_packet_send_state.is_valid) {
    congestion_event->last_packet_send_state = sample.last_packet_send_state;
    congestion_event->last_sample_is_app_limited =
        sample.last_packet_send_state.is_app_limited;
  }

  // Avoid updating |max_bandwidth_filter_| if a) this is a loss-only event, or
  // b) all packets in |acked_packets| did not generate valid samples. (e.g. ack
  // of ack-only packets). In both cases, total_bytes_acked() will not change.
  if (prior_bytes_acked != total_bytes_acked()) {
    QUIC_LOG_IF(WARNING, sample.sample_max_bandwidth.IsZero())
        << total_bytes_acked() - prior_bytes_acked << " bytes from "
        << acked_packets.size()
        << " packets have been acked, but sample_max_bandwidth is zero.";
    if (!sample.sample_is_app_limited ||
        sample.sample_max_bandwidth > MaxBandwidth()) {
      congestion_event->sample_max_bandwidth = sample.sample_max_bandwidth;
      max_bandwidth_filter_.Update(congestion_event->sample_max_bandwidth);
    }
  }

  if (!sample.sample_rtt.IsInfinite()) {
    congestion_event->sample_min_rtt = sample.sample_rtt;
    min_rtt_filter_.Update(congestion_event->sample_min_rtt, event_time);
  }

  congestion_event->bytes_acked = total_bytes_acked() - prior_bytes_acked;
  congestion_event->bytes_lost = total_bytes_lost() - prior_bytes_lost;

  if (congestion_event->prior_bytes_in_flight >=
      congestion_event->bytes_acked + congestion_event->bytes_lost) {
    congestion_event->bytes_in_flight =
        congestion_event->prior_bytes_in_flight -
        congestion_event->bytes_acked - congestion_event->bytes_lost;
  } else {
    QUIC_LOG_FIRST_N(ERROR, 1)
        << "prior_bytes_in_flight:" << congestion_event->prior_bytes_in_flight
        << " is smaller than the sum of bytes_acked:"
        << congestion_event->bytes_acked
        << " and bytes_lost:" << congestion_event->bytes_lost;
    congestion_event->bytes_in_flight = 0;
  }

  if (congestion_event->bytes_lost > 0) {
    bytes_lost_in_round_ += congestion_event->bytes_lost;
    loss_events_in_round_++;
  }

  if (congestion_event->bytes_acked > 0 &&
      congestion_event->last_packet_send_state.is_valid &&
      total_bytes_acked() >
          congestion_event->last_packet_send_state.total_bytes_acked) {
    QuicByteCount bytes_delivered =
        total_bytes_acked() -
        congestion_event->last_packet_send_state.total_bytes_acked;
    max_bytes_delivered_in_round_ =
        std::max(max_bytes_delivered_in_round_, bytes_delivered);
  }

  // |bandwidth_latest_| and |inflight_latest_| only increased within a round.
  if (sample.sample_max_bandwidth > bandwidth_latest_) {
    bandwidth_latest_ = sample.sample_max_bandwidth;
  }

  if (sample.sample_max_inflight > inflight_latest_) {
    inflight_latest_ = sample.sample_max_inflight;
  }

  if (!congestion_event->end_of_round_trip) {
    return;
  }

  // Per round-trip updates.
  AdaptLowerBounds(*congestion_event);

  if (!sample.sample_max_bandwidth.IsZero()) {
    bandwidth_latest_ = sample.sample_max_bandwidth;
  }

  if (sample.sample_max_inflight > 0) {
    inflight_latest_ = sample.sample_max_inflight;
  }
}

void Bbr2NetworkModel::AdaptLowerBounds(
    const Bbr2CongestionEvent& congestion_event) {
  if (!congestion_event.end_of_round_trip ||
      congestion_event.is_probing_for_bandwidth) {
    return;
  }

  if (bytes_lost_in_round_ > 0) {
    if (bandwidth_lo_.IsInfinite()) {
      bandwidth_lo_ = MaxBandwidth();
    }
    bandwidth_lo_ =
        std::max(bandwidth_latest_, bandwidth_lo_ * (1.0 - Params().beta));
    QUIC_DVLOG(3) << "bandwidth_lo_ updated to " << bandwidth_lo_
                  << ", bandwidth_latest_ is " << bandwidth_latest_;

    if (Params().ignore_inflight_lo) {
      return;
    }
    if (inflight_lo_ == inflight_lo_default()) {
      inflight_lo_ = congestion_event.prior_cwnd;
    }
    inflight_lo_ = std::max<QuicByteCount>(
        inflight_latest_, inflight_lo_ * (1.0 - Params().beta));
  }
}

void Bbr2NetworkModel::OnCongestionEventFinish(
    QuicPacketNumber least_unacked_packet,
    const Bbr2CongestionEvent& congestion_event) {
  if (congestion_event.end_of_round_trip) {
    bytes_lost_in_round_ = 0;
    loss_events_in_round_ = 0;
  }

  bandwidth_sampler_.RemoveObsoletePackets(least_unacked_packet);
}

void Bbr2NetworkModel::UpdateNetworkParameters(QuicTime::Delta rtt) {
  if (!rtt.IsZero()) {
    min_rtt_filter_.Update(rtt, MinRttTimestamp());
  }
}

bool Bbr2NetworkModel::MaybeExpireMinRtt(
    const Bbr2CongestionEvent& congestion_event) {
  if (congestion_event.event_time <
      (MinRttTimestamp() + Params().probe_rtt_period)) {
    return false;
  }
  if (congestion_event.sample_min_rtt.IsInfinite()) {
    return false;
  }
  QUIC_DVLOG(3) << "Replacing expired min rtt of " << min_rtt_filter_.Get()
                << " by " << congestion_event.sample_min_rtt << "  @ "
                << congestion_event.event_time;
  min_rtt_filter_.ForceUpdate(congestion_event.sample_min_rtt,
                              congestion_event.event_time);
  return true;
}

bool Bbr2NetworkModel::IsCongestionWindowLimited(
    const Bbr2CongestionEvent& congestion_event) const {
  QuicByteCount prior_bytes_in_flight = congestion_event.bytes_in_flight +
                                        congestion_event.bytes_acked +
                                        congestion_event.bytes_lost;
  return prior_bytes_in_flight >= congestion_event.prior_cwnd;
}

bool Bbr2NetworkModel::IsInflightTooHigh(
    const Bbr2CongestionEvent& congestion_event,
    int64_t max_loss_events) const {
  const SendTimeState& send_state = congestion_event.last_packet_send_state;
  if (!send_state.is_valid) {
    // Not enough information.
    return false;
  }

  if (loss_events_in_round() < max_loss_events) {
    return false;
  }

  const QuicByteCount inflight_at_send = BytesInFlight(send_state);
  // TODO(wub): Consider total_bytes_lost() - send_state.total_bytes_lost, which
  // is the total bytes lost when the largest numbered packet was inflight.
  // bytes_lost_in_round_, OTOH, is the total bytes lost in the "current" round.
  const QuicByteCount bytes_lost_in_round = bytes_lost_in_round_;

  QUIC_DVLOG(3) << "IsInflightTooHigh: loss_events_in_round:"
                << loss_events_in_round()

                << " bytes_lost_in_round:" << bytes_lost_in_round
                << ", lost_in_round_threshold:"
                << inflight_at_send * Params().loss_threshold;

  if (inflight_at_send > 0 && bytes_lost_in_round > 0) {
    QuicByteCount lost_in_round_threshold =
        inflight_at_send * Params().loss_threshold;
    if (bytes_lost_in_round > lost_in_round_threshold) {
      return true;
    }
  }

  return false;
}

void Bbr2NetworkModel::RestartRound() {
  bytes_lost_in_round_ = 0;
  loss_events_in_round_ = 0;
  max_bytes_delivered_in_round_ = 0;
  round_trip_counter_.RestartRound();
}

void Bbr2NetworkModel::cap_inflight_lo(QuicByteCount cap) {
  if (Params().ignore_inflight_lo) {
    return;
  }
  if (inflight_lo_ != inflight_lo_default() && inflight_lo_ > cap) {
    inflight_lo_ = cap;
  }
}

QuicByteCount Bbr2NetworkModel::inflight_hi_with_headroom() const {
  QuicByteCount headroom = inflight_hi_ * Params().inflight_hi_headroom;

  return inflight_hi_ > headroom ? inflight_hi_ - headroom : 0;
}

}  // namespace quic
<commit_msg>Move the call to AdaptLowerBounds so it's called on every congestion event.  It already exits early if it's not the end of the round, so this is not a functional change.  In preparation for cr/305164640<commit_after>// Copyright 2019 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "net/third_party/quiche/src/quic/core/congestion_control/bbr2_misc.h"

#include "net/third_party/quiche/src/quic/core/congestion_control/bandwidth_sampler.h"
#include "net/third_party/quiche/src/quic/core/quic_bandwidth.h"
#include "net/third_party/quiche/src/quic/core/quic_time.h"
#include "net/third_party/quiche/src/quic/core/quic_types.h"
#include "net/third_party/quiche/src/quic/platform/api/quic_logging.h"

namespace quic {

RoundTripCounter::RoundTripCounter() : round_trip_count_(0) {}

void RoundTripCounter::OnPacketSent(QuicPacketNumber packet_number) {
  DCHECK(!last_sent_packet_.IsInitialized() ||
         last_sent_packet_ < packet_number);
  last_sent_packet_ = packet_number;
}

bool RoundTripCounter::OnPacketsAcked(QuicPacketNumber last_acked_packet) {
  if (!end_of_round_trip_.IsInitialized() ||
      last_acked_packet > end_of_round_trip_) {
    round_trip_count_++;
    end_of_round_trip_ = last_sent_packet_;
    return true;
  }
  return false;
}

void RoundTripCounter::RestartRound() {
  end_of_round_trip_ = last_sent_packet_;
}

MinRttFilter::MinRttFilter(QuicTime::Delta initial_min_rtt,
                           QuicTime initial_min_rtt_timestamp)
    : min_rtt_(initial_min_rtt),
      min_rtt_timestamp_(initial_min_rtt_timestamp) {}

void MinRttFilter::Update(QuicTime::Delta sample_rtt, QuicTime now) {
  if (sample_rtt < min_rtt_ || min_rtt_timestamp_ == QuicTime::Zero()) {
    min_rtt_ = sample_rtt;
    min_rtt_timestamp_ = now;
  }
}

void MinRttFilter::ForceUpdate(QuicTime::Delta sample_rtt, QuicTime now) {
  min_rtt_ = sample_rtt;
  min_rtt_timestamp_ = now;
}

Bbr2NetworkModel::Bbr2NetworkModel(const Bbr2Params* params,
                                   QuicTime::Delta initial_rtt,
                                   QuicTime initial_rtt_timestamp,
                                   float cwnd_gain,
                                   float pacing_gain,
                                   const BandwidthSampler* old_sampler)
    : params_(params),
      bandwidth_sampler_([](QuicRoundTripCount max_height_tracker_window_length,
                            const BandwidthSampler* old_sampler) {
        if (old_sampler != nullptr) {
          return BandwidthSampler(*old_sampler);
        }
        return BandwidthSampler(/*unacked_packet_map=*/nullptr,
                                max_height_tracker_window_length);
      }(params->initial_max_ack_height_filter_window, old_sampler)),
      min_rtt_filter_(initial_rtt, initial_rtt_timestamp),
      cwnd_gain_(cwnd_gain),
      pacing_gain_(pacing_gain) {}

void Bbr2NetworkModel::OnPacketSent(QuicTime sent_time,
                                    QuicByteCount bytes_in_flight,
                                    QuicPacketNumber packet_number,
                                    QuicByteCount bytes,
                                    HasRetransmittableData is_retransmittable) {
  round_trip_counter_.OnPacketSent(packet_number);

  bandwidth_sampler_.OnPacketSent(sent_time, packet_number, bytes,
                                  bytes_in_flight, is_retransmittable);
}

void Bbr2NetworkModel::OnCongestionEventStart(
    QuicTime event_time,
    const AckedPacketVector& acked_packets,
    const LostPacketVector& lost_packets,
    Bbr2CongestionEvent* congestion_event) {
  const QuicByteCount prior_bytes_acked = total_bytes_acked();
  const QuicByteCount prior_bytes_lost = total_bytes_lost();

  congestion_event->event_time = event_time;
  congestion_event->end_of_round_trip =
      acked_packets.empty() ? false
                            : round_trip_counter_.OnPacketsAcked(
                                  acked_packets.rbegin()->packet_number);

  BandwidthSamplerInterface::CongestionEventSample sample =
      bandwidth_sampler_.OnCongestionEvent(event_time, acked_packets,
                                           lost_packets, MaxBandwidth(),
                                           bandwidth_lo(), RoundTripCount());

  if (sample.last_packet_send_state.is_valid) {
    congestion_event->last_packet_send_state = sample.last_packet_send_state;
    congestion_event->last_sample_is_app_limited =
        sample.last_packet_send_state.is_app_limited;
  }

  // Avoid updating |max_bandwidth_filter_| if a) this is a loss-only event, or
  // b) all packets in |acked_packets| did not generate valid samples. (e.g. ack
  // of ack-only packets). In both cases, total_bytes_acked() will not change.
  if (prior_bytes_acked != total_bytes_acked()) {
    QUIC_LOG_IF(WARNING, sample.sample_max_bandwidth.IsZero())
        << total_bytes_acked() - prior_bytes_acked << " bytes from "
        << acked_packets.size()
        << " packets have been acked, but sample_max_bandwidth is zero.";
    if (!sample.sample_is_app_limited ||
        sample.sample_max_bandwidth > MaxBandwidth()) {
      congestion_event->sample_max_bandwidth = sample.sample_max_bandwidth;
      max_bandwidth_filter_.Update(congestion_event->sample_max_bandwidth);
    }
  }

  if (!sample.sample_rtt.IsInfinite()) {
    congestion_event->sample_min_rtt = sample.sample_rtt;
    min_rtt_filter_.Update(congestion_event->sample_min_rtt, event_time);
  }

  congestion_event->bytes_acked = total_bytes_acked() - prior_bytes_acked;
  congestion_event->bytes_lost = total_bytes_lost() - prior_bytes_lost;

  if (congestion_event->prior_bytes_in_flight >=
      congestion_event->bytes_acked + congestion_event->bytes_lost) {
    congestion_event->bytes_in_flight =
        congestion_event->prior_bytes_in_flight -
        congestion_event->bytes_acked - congestion_event->bytes_lost;
  } else {
    QUIC_LOG_FIRST_N(ERROR, 1)
        << "prior_bytes_in_flight:" << congestion_event->prior_bytes_in_flight
        << " is smaller than the sum of bytes_acked:"
        << congestion_event->bytes_acked
        << " and bytes_lost:" << congestion_event->bytes_lost;
    congestion_event->bytes_in_flight = 0;
  }

  if (congestion_event->bytes_lost > 0) {
    bytes_lost_in_round_ += congestion_event->bytes_lost;
    loss_events_in_round_++;
  }

  if (congestion_event->bytes_acked > 0 &&
      congestion_event->last_packet_send_state.is_valid &&
      total_bytes_acked() >
          congestion_event->last_packet_send_state.total_bytes_acked) {
    QuicByteCount bytes_delivered =
        total_bytes_acked() -
        congestion_event->last_packet_send_state.total_bytes_acked;
    max_bytes_delivered_in_round_ =
        std::max(max_bytes_delivered_in_round_, bytes_delivered);
  }

  // |bandwidth_latest_| and |inflight_latest_| only increased within a round.
  if (sample.sample_max_bandwidth > bandwidth_latest_) {
    bandwidth_latest_ = sample.sample_max_bandwidth;
  }

  if (sample.sample_max_inflight > inflight_latest_) {
    inflight_latest_ = sample.sample_max_inflight;
  }

  AdaptLowerBounds(*congestion_event);

  if (!congestion_event->end_of_round_trip) {
    return;
  }

  if (!sample.sample_max_bandwidth.IsZero()) {
    bandwidth_latest_ = sample.sample_max_bandwidth;
  }

  if (sample.sample_max_inflight > 0) {
    inflight_latest_ = sample.sample_max_inflight;
  }
}

void Bbr2NetworkModel::AdaptLowerBounds(
    const Bbr2CongestionEvent& congestion_event) {
  if (!congestion_event.end_of_round_trip ||
      congestion_event.is_probing_for_bandwidth) {
    return;
  }

  if (bytes_lost_in_round_ > 0) {
    if (bandwidth_lo_.IsInfinite()) {
      bandwidth_lo_ = MaxBandwidth();
    }
    bandwidth_lo_ =
        std::max(bandwidth_latest_, bandwidth_lo_ * (1.0 - Params().beta));
    QUIC_DVLOG(3) << "bandwidth_lo_ updated to " << bandwidth_lo_
                  << ", bandwidth_latest_ is " << bandwidth_latest_;

    if (Params().ignore_inflight_lo) {
      return;
    }
    if (inflight_lo_ == inflight_lo_default()) {
      inflight_lo_ = congestion_event.prior_cwnd;
    }
    inflight_lo_ = std::max<QuicByteCount>(
        inflight_latest_, inflight_lo_ * (1.0 - Params().beta));
  }
}

void Bbr2NetworkModel::OnCongestionEventFinish(
    QuicPacketNumber least_unacked_packet,
    const Bbr2CongestionEvent& congestion_event) {
  if (congestion_event.end_of_round_trip) {
    bytes_lost_in_round_ = 0;
    loss_events_in_round_ = 0;
  }

  bandwidth_sampler_.RemoveObsoletePackets(least_unacked_packet);
}

void Bbr2NetworkModel::UpdateNetworkParameters(QuicTime::Delta rtt) {
  if (!rtt.IsZero()) {
    min_rtt_filter_.Update(rtt, MinRttTimestamp());
  }
}

bool Bbr2NetworkModel::MaybeExpireMinRtt(
    const Bbr2CongestionEvent& congestion_event) {
  if (congestion_event.event_time <
      (MinRttTimestamp() + Params().probe_rtt_period)) {
    return false;
  }
  if (congestion_event.sample_min_rtt.IsInfinite()) {
    return false;
  }
  QUIC_DVLOG(3) << "Replacing expired min rtt of " << min_rtt_filter_.Get()
                << " by " << congestion_event.sample_min_rtt << "  @ "
                << congestion_event.event_time;
  min_rtt_filter_.ForceUpdate(congestion_event.sample_min_rtt,
                              congestion_event.event_time);
  return true;
}

bool Bbr2NetworkModel::IsCongestionWindowLimited(
    const Bbr2CongestionEvent& congestion_event) const {
  QuicByteCount prior_bytes_in_flight = congestion_event.bytes_in_flight +
                                        congestion_event.bytes_acked +
                                        congestion_event.bytes_lost;
  return prior_bytes_in_flight >= congestion_event.prior_cwnd;
}

bool Bbr2NetworkModel::IsInflightTooHigh(
    const Bbr2CongestionEvent& congestion_event,
    int64_t max_loss_events) const {
  const SendTimeState& send_state = congestion_event.last_packet_send_state;
  if (!send_state.is_valid) {
    // Not enough information.
    return false;
  }

  if (loss_events_in_round() < max_loss_events) {
    return false;
  }

  const QuicByteCount inflight_at_send = BytesInFlight(send_state);
  // TODO(wub): Consider total_bytes_lost() - send_state.total_bytes_lost, which
  // is the total bytes lost when the largest numbered packet was inflight.
  // bytes_lost_in_round_, OTOH, is the total bytes lost in the "current" round.
  const QuicByteCount bytes_lost_in_round = bytes_lost_in_round_;

  QUIC_DVLOG(3) << "IsInflightTooHigh: loss_events_in_round:"
                << loss_events_in_round()

                << " bytes_lost_in_round:" << bytes_lost_in_round
                << ", lost_in_round_threshold:"
                << inflight_at_send * Params().loss_threshold;

  if (inflight_at_send > 0 && bytes_lost_in_round > 0) {
    QuicByteCount lost_in_round_threshold =
        inflight_at_send * Params().loss_threshold;
    if (bytes_lost_in_round > lost_in_round_threshold) {
      return true;
    }
  }

  return false;
}

void Bbr2NetworkModel::RestartRound() {
  bytes_lost_in_round_ = 0;
  loss_events_in_round_ = 0;
  max_bytes_delivered_in_round_ = 0;
  round_trip_counter_.RestartRound();
}

void Bbr2NetworkModel::cap_inflight_lo(QuicByteCount cap) {
  if (Params().ignore_inflight_lo) {
    return;
  }
  if (inflight_lo_ != inflight_lo_default() && inflight_lo_ > cap) {
    inflight_lo_ = cap;
  }
}

QuicByteCount Bbr2NetworkModel::inflight_hi_with_headroom() const {
  QuicByteCount headroom = inflight_hi_ * Params().inflight_hi_headroom;

  return inflight_hi_ > headroom ? inflight_hi_ - headroom : 0;
}

}  // namespace quic
<|endoftext|>


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

This file is part of the QtMediaHub project on http://www.gitorious.org.

Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).*
All rights reserved.

Contact:  Nokia Corporation (qt-info@nokia.com)**

You may use this file under the terms of the BSD license as follows:

"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 Nokia Corporation and its Subsidiary(-ies) nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."

****************************************************************************/

#include <QApplication>
#ifdef GL
#include <QGLFormat>
#endif
#ifdef QT_SINGLE_APPLICATION
#include "qtsingleapplication.h"
#endif

#include "backend.h"
#include "qmh-config.h"

int main(int argc, char** argv)
{
    QApplication::setGraphicsSystem("raster");

#ifdef GL
    //Purely for experimentation
    QGLFormat format;
    //should suffice
    format.setDepth(false);
//    plan b: russian roulette
//    format.setStencil(false);

#ifdef Q_OS_MAC
    format.setSampleBuffers(true);
#else
    format.setSampleBuffers(false);
#endif //Q_OS_MAC

//    //FIXME: Should be configurable, but Config
//    blocked by instantiation of QApplication
//    //vsync
    format.setSwapInterval(1);
//    //no vsync
//    format.setSwapInterval(0);
//    format.setDoubleBuffer(false);
//    format.setAlpha(false);
//    format.setDirectRendering(false);

    QGLFormat::setDefaultFormat(format);

#ifdef GLGS
    //Only legitimate use is in fullscreen QGraphicsView derived classes!
    //If you use this in conjunction with our traditional QWidget style functionality
    //You are in for a rough ride
    if (Config::isEnabled("use-gl", true))
        QApplication::setGraphicsSystem("opengl");
#endif //GLGS
#endif //GL

#ifdef QT_SINGLE_APPLICATION
    QtSingleApplication app(argc, argv);
#else
    QApplication app(argc, argv);
#endif //QT_SINGLE_APPLICATION

    app.setApplicationName("qtmediahub");
    app.setOrganizationName("Nokia");
    app.setOrganizationDomain("nokia.com");

#ifdef QT_SINGLE_APPLICATION
    if (!Config::isEnabled("multi-instance", false) && app.isRunning()) {
        qWarning() << app.applicationName() << "is already running, aborting";
        return false;
    }
#endif //QT_SINGLE_APPLICATION
    Config::init(argc, argv);

    Backend::instance();

    return app.exec();
}
<commit_msg>Fix freeing of backend instance<commit_after>/****************************************************************************

This file is part of the QtMediaHub project on http://www.gitorious.org.

Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).*
All rights reserved.

Contact:  Nokia Corporation (qt-info@nokia.com)**

You may use this file under the terms of the BSD license as follows:

"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 Nokia Corporation and its Subsidiary(-ies) nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."

****************************************************************************/

#include <QApplication>
#ifdef GL
#include <QGLFormat>
#endif
#ifdef QT_SINGLE_APPLICATION
#include "qtsingleapplication.h"
#endif

#include "backend.h"
#include "qmh-config.h"

int main(int argc, char** argv)
{
    QApplication::setGraphicsSystem("raster");

#ifdef GL
    //Purely for experimentation
    QGLFormat format;
    //should suffice
    format.setDepth(false);
//    plan b: russian roulette
//    format.setStencil(false);

#ifdef Q_OS_MAC
    format.setSampleBuffers(true);
#else
    format.setSampleBuffers(false);
#endif //Q_OS_MAC

//    //FIXME: Should be configurable, but Config
//    blocked by instantiation of QApplication
//    //vsync
    format.setSwapInterval(1);
//    //no vsync
//    format.setSwapInterval(0);
//    format.setDoubleBuffer(false);
//    format.setAlpha(false);
//    format.setDirectRendering(false);

    QGLFormat::setDefaultFormat(format);

#ifdef GLGS
    //Only legitimate use is in fullscreen QGraphicsView derived classes!
    //If you use this in conjunction with our traditional QWidget style functionality
    //You are in for a rough ride
    if (Config::isEnabled("use-gl", true))
        QApplication::setGraphicsSystem("opengl");
#endif //GLGS
#endif //GL

#ifdef QT_SINGLE_APPLICATION
    QtSingleApplication app(argc, argv);
#else
    QApplication app(argc, argv);
#endif //QT_SINGLE_APPLICATION

    app.setApplicationName("qtmediahub");
    app.setOrganizationName("Nokia");
    app.setOrganizationDomain("nokia.com");

#ifdef QT_SINGLE_APPLICATION
    if (!Config::isEnabled("multi-instance", false) && app.isRunning()) {
        qWarning() << app.applicationName() << "is already running, aborting";
        return false;
    }
#endif //QT_SINGLE_APPLICATION
    Config::init(argc, argv);

    Backend::instance();

    int ret = app.exec();

    delete Backend::instance();

    return ret;
}
<|endoftext|>