<commit_before>#include "SemanticModel.h"

#include <algorithm>

#include "SyntaxTree.h"

namespace slang {

SemanticModel::SemanticModel() {
    specialTypes[(int)SpecialType::ShortInt] = alloc.emplace<IntegralTypeSymbol>(16, true, false);
    specialTypes[(int)SpecialType::Int] = alloc.emplace<IntegralTypeSymbol>(32, true, false);
    specialTypes[(int)SpecialType::LongInt] = alloc.emplace<IntegralTypeSymbol>(64, true, false);
    specialTypes[(int)SpecialType::Byte] = alloc.emplace<IntegralTypeSymbol>(8, true, false);
    specialTypes[(int)SpecialType::Bit] = alloc.emplace<IntegralTypeSymbol>(1, false, false);
    specialTypes[(int)SpecialType::Logic] = alloc.emplace<IntegralTypeSymbol>(1, false, true);
    specialTypes[(int)SpecialType::Reg] = alloc.emplace<IntegralTypeSymbol>(1, false, true);
    specialTypes[(int)SpecialType::Integer] = alloc.emplace<IntegralTypeSymbol>(32, true, true);
    specialTypes[(int)SpecialType::Time] = alloc.emplace<IntegralTypeSymbol>(64, false, true);
    specialTypes[(int)SpecialType::Error] = alloc.emplace<ErrorTypeSymbol>();
}

SemanticModel::SemanticModel(DeclarationTable& declTable) :
    SemanticModel()
{
}

void SemanticModel::bindModuleImplicit(ModuleDeclarationSyntax* module) {
}

BoundParameterDeclaration* SemanticModel::bindParameterDecl(const ParameterDeclarationSyntax* syntax) {
    ASSERT(syntax);
    ASSERT(syntax->kind == SyntaxKind::ParameterDeclaration);

    auto declarator = syntax->declarators[0];
    auto initializer = declarator->initializer;

    auto boundInitializer = bindSelfDeterminedExpression(initializer->expr);
    return alloc.emplace<BoundParameterDeclaration>(syntax, boundInitializer);
}

BoundExpression* SemanticModel::bindExpression(const ExpressionSyntax* syntax) {
    ASSERT(syntax);
    switch (syntax->kind) {
        case SyntaxKind::NullLiteralExpression:
        case SyntaxKind::StringLiteralExpression:
        case SyntaxKind::RealLiteralExpression:
        case SyntaxKind::TimeLiteralExpression:
        case SyntaxKind::WildcardLiteralExpression:
        case SyntaxKind::OneStepLiteralExpression:
        case SyntaxKind::UnbasedUnsizedLiteralExpression:
            break;
        case SyntaxKind::IntegerLiteralExpression:
            return bindLiteral(syntax->as<LiteralExpressionSyntax>());
        case SyntaxKind::IntegerVectorExpression:
            return bindLiteral(syntax->as<IntegerVectorExpressionSyntax>());
        case SyntaxKind::ParenthesizedExpression:
            return bindExpression(syntax->as<ParenthesizedExpressionSyntax>()->expression);
        case SyntaxKind::UnaryPlusExpression:
        case SyntaxKind::UnaryMinusExpression:
        case SyntaxKind::UnaryBitwiseNotExpression:
            return bindUnaryArithmeticOperator(syntax->as<PrefixUnaryExpressionSyntax>());
        case SyntaxKind::UnaryBitwiseAndExpression:
        case SyntaxKind::UnaryBitwiseOrExpression:
        case SyntaxKind::UnaryBitwiseXorExpression:
        case SyntaxKind::UnaryBitwiseNandExpression:
        case SyntaxKind::UnaryBitwiseNorExpression:
        case SyntaxKind::UnaryBitwiseXnorExpression:
        case SyntaxKind::UnaryLogicalNotExpression:
            return bindUnaryReductionOperator(syntax->as<PrefixUnaryExpressionSyntax>());
        case SyntaxKind::AddExpression:
        case SyntaxKind::SubtractExpression:
        case SyntaxKind::MultiplyExpression:
        case SyntaxKind::DivideExpression:
        case SyntaxKind::ModExpression:
        case SyntaxKind::BinaryAndExpression:
        case SyntaxKind::BinaryOrExpression:
        case SyntaxKind::BinaryXorExpression:
        case SyntaxKind::BinaryXnorExpression:
            return bindArithmeticOperator(syntax->as<BinaryExpressionSyntax>());
        case SyntaxKind::EqualityExpression:
        case SyntaxKind::InequalityExpression:
        case SyntaxKind::CaseEqualityExpression:
        case SyntaxKind::CaseInequalityExpression:
        case SyntaxKind::GreaterThanEqualExpression:
        case SyntaxKind::GreaterThanExpression:
        case SyntaxKind::LessThanEqualExpression:
        case SyntaxKind::LessThanExpression:
            return bindComparisonOperator(syntax->as<BinaryExpressionSyntax>());
        case SyntaxKind::LogicalAndExpression:
        case SyntaxKind::LogicalOrExpression:
        case SyntaxKind::LogicalImplicationExpression:
        case SyntaxKind::LogicalEquivalenceExpression:
            return bindRelationalOperator(syntax->as<BinaryExpressionSyntax>());
        case SyntaxKind::LogicalShiftLeftExpression:
        case SyntaxKind::LogicalShiftRightExpression:
        case SyntaxKind::ArithmeticShiftLeftExpression:
        case SyntaxKind::ArithmeticShiftRightExpression:
        case SyntaxKind::PowerExpression:
            return bindShiftOrPowerOperator(syntax->as<BinaryExpressionSyntax>());
    }
    return nullptr;
}

BoundExpression* SemanticModel::bindSelfDeterminedExpression(const ExpressionSyntax* syntax) {
    BoundExpression* expr = bindExpression(syntax);
	propagateAndFold(expr, expr->type);
    return expr;
}

BoundExpression* SemanticModel::bindLiteral(const LiteralExpressionSyntax* syntax) {
    switch (syntax->kind) {
        case SyntaxKind::IntegerLiteralExpression: {
            return alloc.emplace<BoundLiteralExpression>(syntax, getSpecialType(SpecialType::Int), false);
        }
        default:
            return nullptr;
    }
}

BoundExpression* SemanticModel::bindLiteral(const IntegerVectorExpressionSyntax* syntax) {
    return alloc.emplace<BoundLiteralExpression>(syntax, getSpecialType(SpecialType::Int), false);
}

BoundExpression* SemanticModel::bindUnaryArithmeticOperator(const PrefixUnaryExpressionSyntax* syntax) {
    BoundExpression* operand = bindExpression(syntax->operand);
    if (operand->bad)
        return alloc.emplace<BoundUnaryExpression>(syntax, getErrorType(), operand, true);

    return alloc.emplace<BoundUnaryExpression>(syntax, operand->type, operand, false);
}

BoundExpression* SemanticModel::bindUnaryReductionOperator(const PrefixUnaryExpressionSyntax* syntax) {
    // result type is always a single bit
    BoundExpression* operand = bindSelfDeterminedExpression(syntax->operand);
    return alloc.emplace<BoundUnaryExpression>(syntax, getSpecialType(SpecialType::Logic), operand, operand->bad);
}

BoundExpression* SemanticModel::bindArithmeticOperator(const BinaryExpressionSyntax* syntax) {
    BoundExpression* lhs = bindExpression(syntax->left);
    BoundExpression* rhs = bindExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    const IntegralTypeSymbol& l = lhs->type->integral();
    const IntegralTypeSymbol& r = rhs->type->integral();
    int width = std::max(l.width, r.width);
    bool isSigned = l.isSigned && r.isSigned;
    const TypeSymbol* type = getIntegralType(width, isSigned);

    return alloc.emplace<BoundBinaryExpression>(syntax, type, lhs, rhs, false);
}

BoundExpression* SemanticModel::bindComparisonOperator(const BinaryExpressionSyntax* syntax) {
    BoundExpression* lhs = bindExpression(syntax->left);
    BoundExpression* rhs = bindExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    // result type is always a single bit
    return alloc.emplace<BoundBinaryExpression>(syntax, getSpecialType(SpecialType::Logic), lhs, rhs, false);
}

BoundExpression* SemanticModel::bindRelationalOperator(const BinaryExpressionSyntax* syntax) {
    BoundExpression* lhs = bindSelfDeterminedExpression(syntax->left);
    BoundExpression* rhs = bindSelfDeterminedExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    // result type is always a single bit
    return alloc.emplace<BoundBinaryExpression>(syntax, getSpecialType(SpecialType::Logic), lhs, rhs, false);
}

BoundExpression* SemanticModel::bindShiftOrPowerOperator(const BinaryExpressionSyntax* syntax) {
    // The shift and power operators are handled together here because in both cases the second
    // operand is evaluated in a self determined context.
    BoundExpression* lhs = bindExpression(syntax->left);
    BoundExpression* rhs = bindSelfDeterminedExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    const IntegralTypeSymbol& l = lhs->type->integral();
    const IntegralTypeSymbol& r = rhs->type->integral();
    int width = l.width;
    bool isSigned = l.isSigned && r.isSigned;
    const TypeSymbol* type = getIntegralType(width, isSigned);

    return alloc.emplace<BoundBinaryExpression>(syntax, type, lhs, rhs, false);
}

const TypeSymbol* SemanticModel::getIntegralType(int width, bool isSigned) {
	std::unordered_map<int, const TypeSymbol*>& cache = integralTypeCache[true][isSigned]; // always use the 4-state cache

	auto it = cache.find(width);
	if (it != cache.end())
		return it->second;

	it = cache.emplace_hint(it, width, alloc.emplace<IntegralTypeSymbol>(width, isSigned, true));
	return it->second;
}

void SemanticModel::propagateAndFold(BoundExpression* expression, const TypeSymbol* type) {
    ASSERT(expression);
	if (expression->bad)
		return;

	switch (expression->syntax->kind) {
		case SyntaxKind::IntegerLiteralExpression:
		case SyntaxKind::IntegerVectorExpression:
			return propagateAndFoldLiteral((BoundLiteralExpression*)expression, type);
		case SyntaxKind::UnaryPlusExpression:
		case SyntaxKind::UnaryMinusExpression:
		case SyntaxKind::UnaryBitwiseNotExpression:
			return propagateAndFoldUnaryArithmeticOperator((BoundUnaryExpression*)expression, type);
		case SyntaxKind::UnaryBitwiseAndExpression:
		case SyntaxKind::UnaryBitwiseOrExpression:
		case SyntaxKind::UnaryBitwiseXorExpression:
		case SyntaxKind::UnaryBitwiseNandExpression:
		case SyntaxKind::UnaryBitwiseNorExpression:
		case SyntaxKind::UnaryBitwiseXnorExpression:
		case SyntaxKind::UnaryLogicalNotExpression:
			return propagateAndFoldUnaryReductionOperator((BoundUnaryExpression*)expression, type);
		case SyntaxKind::AddExpression:
		case SyntaxKind::SubtractExpression:
		case SyntaxKind::MultiplyExpression:
		case SyntaxKind::DivideExpression:
		case SyntaxKind::ModExpression:
		case SyntaxKind::BinaryAndExpression:
		case SyntaxKind::BinaryOrExpression:
		case SyntaxKind::BinaryXorExpression:
		case SyntaxKind::BinaryXnorExpression:
			return propagateAndFoldArithmeticOperator((BoundBinaryExpression*)expression, type);
		case SyntaxKind::EqualityExpression:
		case SyntaxKind::InequalityExpression:
		case SyntaxKind::CaseEqualityExpression:
		case SyntaxKind::CaseInequalityExpression:
		case SyntaxKind::GreaterThanEqualExpression:
		case SyntaxKind::GreaterThanExpression:
		case SyntaxKind::LessThanEqualExpression:
		case SyntaxKind::LessThanExpression:
			return propagateAndFoldComparisonOperator((BoundBinaryExpression*)expression, type);
		case SyntaxKind::LogicalAndExpression:
		case SyntaxKind::LogicalOrExpression:
		case SyntaxKind::LogicalImplicationExpression:
		case SyntaxKind::LogicalEquivalenceExpression:
			return propagateAndFoldRelationalOperator((BoundBinaryExpression*)expression, type);
		case SyntaxKind::LogicalShiftLeftExpression:
		case SyntaxKind::LogicalShiftRightExpression:
		case SyntaxKind::ArithmeticShiftLeftExpression:
		case SyntaxKind::ArithmeticShiftRightExpression:
		case SyntaxKind::PowerExpression:
			return propagateAndFoldShiftOrPowerOperator((BoundBinaryExpression*)expression, type);
	}
}

void SemanticModel::propagateAndFoldLiteral(BoundLiteralExpression* expression, const TypeSymbol* type) {
	switch (expression->syntax->kind) {
		case SyntaxKind::IntegerLiteralExpression: {
			const SVInt& v = get<SVInt>(expression->syntax->as<LiteralExpressionSyntax>()->literal.numericValue());
			if (v.getBitWidth() < type->integral().width)
				expression->constantValue = extend(v, type->integral().width, type->integral().isSigned);
			else
				expression->constantValue = v;
		}
	}
}

void SemanticModel::propagateAndFoldUnaryArithmeticOperator(BoundUnaryExpression* expression, const TypeSymbol* type) {
}

void SemanticModel::propagateAndFoldUnaryReductionOperator(BoundUnaryExpression* expression, const TypeSymbol* type) {
}

void SemanticModel::propagateAndFoldArithmeticOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
	expression->type = type;
	propagateAndFold(expression->left, type);
	propagateAndFold(expression->right, type);

	ConstantValue cv;
	SVInt& l = get<SVInt>(expression->left->constantValue);
	SVInt& r = get<SVInt>(expression->right->constantValue);

	switch (expression->syntax->kind) {
		case SyntaxKind::AddExpression: cv = l + r; break;
		case SyntaxKind::SubtractExpression: cv = l - r; break;
		case SyntaxKind::MultiplyExpression: cv = l * r; break;
		case SyntaxKind::DivideExpression: cv = l / r; break;
		case SyntaxKind::ModExpression: cv = l % r; break;
		case SyntaxKind::BinaryAndExpression: cv = l & r; break;
		case SyntaxKind::BinaryOrExpression: cv = l | r; break;
		case SyntaxKind::BinaryXorExpression: cv = l ^ r; break;
		case SyntaxKind::BinaryXnorExpression: cv = l.xnor(r); break;
			DEFAULT_UNREACHABLE;
	}
	expression->constantValue = cv;
}

void SemanticModel::propagateAndFoldComparisonOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
}

void SemanticModel::propagateAndFoldRelationalOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
}

void SemanticModel::propagateAndFoldShiftOrPowerOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
}

}<commit_msg>More operator propagation<commit_after>#include "SemanticModel.h"

#include <algorithm>

#include "SyntaxTree.h"

namespace slang {

SemanticModel::SemanticModel() {
    specialTypes[(int)SpecialType::ShortInt] = alloc.emplace<IntegralTypeSymbol>(16, true, false);
    specialTypes[(int)SpecialType::Int] = alloc.emplace<IntegralTypeSymbol>(32, true, false);
    specialTypes[(int)SpecialType::LongInt] = alloc.emplace<IntegralTypeSymbol>(64, true, false);
    specialTypes[(int)SpecialType::Byte] = alloc.emplace<IntegralTypeSymbol>(8, true, false);
    specialTypes[(int)SpecialType::Bit] = alloc.emplace<IntegralTypeSymbol>(1, false, false);
    specialTypes[(int)SpecialType::Logic] = alloc.emplace<IntegralTypeSymbol>(1, false, true);
    specialTypes[(int)SpecialType::Reg] = alloc.emplace<IntegralTypeSymbol>(1, false, true);
    specialTypes[(int)SpecialType::Integer] = alloc.emplace<IntegralTypeSymbol>(32, true, true);
    specialTypes[(int)SpecialType::Time] = alloc.emplace<IntegralTypeSymbol>(64, false, true);
    specialTypes[(int)SpecialType::Error] = alloc.emplace<ErrorTypeSymbol>();
}

SemanticModel::SemanticModel(DeclarationTable& declTable) :
    SemanticModel()
{
}

void SemanticModel::bindModuleImplicit(ModuleDeclarationSyntax* module) {
}

BoundParameterDeclaration* SemanticModel::bindParameterDecl(const ParameterDeclarationSyntax* syntax) {
    ASSERT(syntax);
    ASSERT(syntax->kind == SyntaxKind::ParameterDeclaration);

    auto declarator = syntax->declarators[0];
    auto initializer = declarator->initializer;

    auto boundInitializer = bindSelfDeterminedExpression(initializer->expr);
    return alloc.emplace<BoundParameterDeclaration>(syntax, boundInitializer);
}

BoundExpression* SemanticModel::bindExpression(const ExpressionSyntax* syntax) {
    ASSERT(syntax);
    switch (syntax->kind) {
        case SyntaxKind::NullLiteralExpression:
        case SyntaxKind::StringLiteralExpression:
        case SyntaxKind::RealLiteralExpression:
        case SyntaxKind::TimeLiteralExpression:
        case SyntaxKind::WildcardLiteralExpression:
        case SyntaxKind::OneStepLiteralExpression:
        case SyntaxKind::UnbasedUnsizedLiteralExpression:
            break;
        case SyntaxKind::IntegerLiteralExpression:
            return bindLiteral(syntax->as<LiteralExpressionSyntax>());
        case SyntaxKind::IntegerVectorExpression:
            return bindLiteral(syntax->as<IntegerVectorExpressionSyntax>());
        case SyntaxKind::ParenthesizedExpression:
            return bindExpression(syntax->as<ParenthesizedExpressionSyntax>()->expression);
        case SyntaxKind::UnaryPlusExpression:
        case SyntaxKind::UnaryMinusExpression:
        case SyntaxKind::UnaryBitwiseNotExpression:
            return bindUnaryArithmeticOperator(syntax->as<PrefixUnaryExpressionSyntax>());
        case SyntaxKind::UnaryBitwiseAndExpression:
        case SyntaxKind::UnaryBitwiseOrExpression:
        case SyntaxKind::UnaryBitwiseXorExpression:
        case SyntaxKind::UnaryBitwiseNandExpression:
        case SyntaxKind::UnaryBitwiseNorExpression:
        case SyntaxKind::UnaryBitwiseXnorExpression:
        case SyntaxKind::UnaryLogicalNotExpression:
            return bindUnaryReductionOperator(syntax->as<PrefixUnaryExpressionSyntax>());
        case SyntaxKind::AddExpression:
        case SyntaxKind::SubtractExpression:
        case SyntaxKind::MultiplyExpression:
        case SyntaxKind::DivideExpression:
        case SyntaxKind::ModExpression:
        case SyntaxKind::BinaryAndExpression:
        case SyntaxKind::BinaryOrExpression:
        case SyntaxKind::BinaryXorExpression:
        case SyntaxKind::BinaryXnorExpression:
            return bindArithmeticOperator(syntax->as<BinaryExpressionSyntax>());
        case SyntaxKind::EqualityExpression:
        case SyntaxKind::InequalityExpression:
        case SyntaxKind::CaseEqualityExpression:
        case SyntaxKind::CaseInequalityExpression:
        case SyntaxKind::GreaterThanEqualExpression:
        case SyntaxKind::GreaterThanExpression:
        case SyntaxKind::LessThanEqualExpression:
        case SyntaxKind::LessThanExpression:
            return bindComparisonOperator(syntax->as<BinaryExpressionSyntax>());
        case SyntaxKind::LogicalAndExpression:
        case SyntaxKind::LogicalOrExpression:
        case SyntaxKind::LogicalImplicationExpression:
        case SyntaxKind::LogicalEquivalenceExpression:
            return bindRelationalOperator(syntax->as<BinaryExpressionSyntax>());
        case SyntaxKind::LogicalShiftLeftExpression:
        case SyntaxKind::LogicalShiftRightExpression:
        case SyntaxKind::ArithmeticShiftLeftExpression:
        case SyntaxKind::ArithmeticShiftRightExpression:
        case SyntaxKind::PowerExpression:
            return bindShiftOrPowerOperator(syntax->as<BinaryExpressionSyntax>());
    }
    return nullptr;
}

BoundExpression* SemanticModel::bindSelfDeterminedExpression(const ExpressionSyntax* syntax) {
    BoundExpression* expr = bindExpression(syntax);
	propagateAndFold(expr, expr->type);
    return expr;
}

BoundExpression* SemanticModel::bindLiteral(const LiteralExpressionSyntax* syntax) {
    switch (syntax->kind) {
        case SyntaxKind::IntegerLiteralExpression: {
            return alloc.emplace<BoundLiteralExpression>(syntax, getSpecialType(SpecialType::Int), false);
        }
        default:
            return nullptr;
    }
}

BoundExpression* SemanticModel::bindLiteral(const IntegerVectorExpressionSyntax* syntax) {
    return alloc.emplace<BoundLiteralExpression>(syntax, getSpecialType(SpecialType::Int), false);
}

BoundExpression* SemanticModel::bindUnaryArithmeticOperator(const PrefixUnaryExpressionSyntax* syntax) {
    BoundExpression* operand = bindExpression(syntax->operand);
    if (operand->bad)
        return alloc.emplace<BoundUnaryExpression>(syntax, getErrorType(), operand, true);

    return alloc.emplace<BoundUnaryExpression>(syntax, operand->type, operand, false);
}

BoundExpression* SemanticModel::bindUnaryReductionOperator(const PrefixUnaryExpressionSyntax* syntax) {
    // result type is always a single bit
    BoundExpression* operand = bindSelfDeterminedExpression(syntax->operand);
    return alloc.emplace<BoundUnaryExpression>(syntax, getSpecialType(SpecialType::Logic), operand, operand->bad);
}

BoundExpression* SemanticModel::bindArithmeticOperator(const BinaryExpressionSyntax* syntax) {
    BoundExpression* lhs = bindExpression(syntax->left);
    BoundExpression* rhs = bindExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    const IntegralTypeSymbol& l = lhs->type->integral();
    const IntegralTypeSymbol& r = rhs->type->integral();
    int width = std::max(l.width, r.width);
    bool isSigned = l.isSigned && r.isSigned;
    const TypeSymbol* type = getIntegralType(width, isSigned);

    return alloc.emplace<BoundBinaryExpression>(syntax, type, lhs, rhs, false);
}

BoundExpression* SemanticModel::bindComparisonOperator(const BinaryExpressionSyntax* syntax) {
    BoundExpression* lhs = bindExpression(syntax->left);
    BoundExpression* rhs = bindExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    // result type is always a single bit
    return alloc.emplace<BoundBinaryExpression>(syntax, getSpecialType(SpecialType::Logic), lhs, rhs, false);
}

BoundExpression* SemanticModel::bindRelationalOperator(const BinaryExpressionSyntax* syntax) {
    BoundExpression* lhs = bindSelfDeterminedExpression(syntax->left);
    BoundExpression* rhs = bindSelfDeterminedExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    // result type is always a single bit
    return alloc.emplace<BoundBinaryExpression>(syntax, getSpecialType(SpecialType::Logic), lhs, rhs, false);
}

BoundExpression* SemanticModel::bindShiftOrPowerOperator(const BinaryExpressionSyntax* syntax) {
    // The shift and power operators are handled together here because in both cases the second
    // operand is evaluated in a self determined context.
    BoundExpression* lhs = bindExpression(syntax->left);
    BoundExpression* rhs = bindSelfDeterminedExpression(syntax->right);
    if (lhs->bad || rhs->bad)
        return alloc.emplace<BoundBinaryExpression>(syntax, getErrorType(), lhs, rhs, true);

    const IntegralTypeSymbol& l = lhs->type->integral();
    const IntegralTypeSymbol& r = rhs->type->integral();
    int width = l.width;
    bool isSigned = l.isSigned && r.isSigned;
    const TypeSymbol* type = getIntegralType(width, isSigned);

    return alloc.emplace<BoundBinaryExpression>(syntax, type, lhs, rhs, false);
}

const TypeSymbol* SemanticModel::getIntegralType(int width, bool isSigned) {
	std::unordered_map<int, const TypeSymbol*>& cache = integralTypeCache[true][isSigned]; // always use the 4-state cache

	auto it = cache.find(width);
	if (it != cache.end())
		return it->second;

	it = cache.emplace_hint(it, width, alloc.emplace<IntegralTypeSymbol>(width, isSigned, true));
	return it->second;
}

void SemanticModel::propagateAndFold(BoundExpression* expression, const TypeSymbol* type) {
    ASSERT(expression);
	if (expression->bad)
		return;

	switch (expression->syntax->kind) {
		case SyntaxKind::IntegerLiteralExpression:
		case SyntaxKind::IntegerVectorExpression:
			return propagateAndFoldLiteral((BoundLiteralExpression*)expression, type);
		case SyntaxKind::UnaryPlusExpression:
		case SyntaxKind::UnaryMinusExpression:
		case SyntaxKind::UnaryBitwiseNotExpression:
			return propagateAndFoldUnaryArithmeticOperator((BoundUnaryExpression*)expression, type);
		case SyntaxKind::UnaryBitwiseAndExpression:
		case SyntaxKind::UnaryBitwiseOrExpression:
		case SyntaxKind::UnaryBitwiseXorExpression:
		case SyntaxKind::UnaryBitwiseNandExpression:
		case SyntaxKind::UnaryBitwiseNorExpression:
		case SyntaxKind::UnaryBitwiseXnorExpression:
		case SyntaxKind::UnaryLogicalNotExpression:
			return propagateAndFoldUnaryReductionOperator((BoundUnaryExpression*)expression, type);
		case SyntaxKind::AddExpression:
		case SyntaxKind::SubtractExpression:
		case SyntaxKind::MultiplyExpression:
		case SyntaxKind::DivideExpression:
		case SyntaxKind::ModExpression:
		case SyntaxKind::BinaryAndExpression:
		case SyntaxKind::BinaryOrExpression:
		case SyntaxKind::BinaryXorExpression:
		case SyntaxKind::BinaryXnorExpression:
			return propagateAndFoldArithmeticOperator((BoundBinaryExpression*)expression, type);
		case SyntaxKind::EqualityExpression:
		case SyntaxKind::InequalityExpression:
		case SyntaxKind::CaseEqualityExpression:
		case SyntaxKind::CaseInequalityExpression:
		case SyntaxKind::GreaterThanEqualExpression:
		case SyntaxKind::GreaterThanExpression:
		case SyntaxKind::LessThanEqualExpression:
		case SyntaxKind::LessThanExpression:
			return propagateAndFoldComparisonOperator((BoundBinaryExpression*)expression, type);
		case SyntaxKind::LogicalAndExpression:
		case SyntaxKind::LogicalOrExpression:
		case SyntaxKind::LogicalImplicationExpression:
		case SyntaxKind::LogicalEquivalenceExpression:
			return propagateAndFoldRelationalOperator((BoundBinaryExpression*)expression, type);
		case SyntaxKind::LogicalShiftLeftExpression:
		case SyntaxKind::LogicalShiftRightExpression:
		case SyntaxKind::ArithmeticShiftLeftExpression:
		case SyntaxKind::ArithmeticShiftRightExpression:
		case SyntaxKind::PowerExpression:
			return propagateAndFoldShiftOrPowerOperator((BoundBinaryExpression*)expression, type);
	}
}

void SemanticModel::propagateAndFoldLiteral(BoundLiteralExpression* expression, const TypeSymbol* type) {
	switch (expression->syntax->kind) {
		case SyntaxKind::IntegerLiteralExpression: {
			const SVInt& v = get<SVInt>(expression->syntax->as<LiteralExpressionSyntax>()->literal.numericValue());
			if (v.getBitWidth() < type->integral().width)
				expression->constantValue = extend(v, type->integral().width, type->integral().isSigned);
			else
				expression->constantValue = v;
		}
	}
}

void SemanticModel::propagateAndFoldUnaryArithmeticOperator(BoundUnaryExpression* expression, const TypeSymbol* type) {
	expression->type = type;
	propagateAndFold(expression->operand, type);

	ConstantValue cv;
	SVInt& v = get<SVInt>(expression->operand->constantValue);

	switch (expression->syntax->kind) {
		case SyntaxKind::UnaryPlusExpression: cv = v; break;
		case SyntaxKind::UnaryMinusExpression: cv = -v; break;
		case SyntaxKind::UnaryBitwiseNotExpression: cv = ~v; break;
			DEFAULT_UNREACHABLE;
	}
	expression->constantValue = cv;
}

void SemanticModel::propagateAndFoldUnaryReductionOperator(BoundUnaryExpression* expression, const TypeSymbol* type) {
	// operands are self-determined and result type is always 1 bit
	ConstantValue cv;
	SVInt& v = get<SVInt>(expression->operand->constantValue);

	switch (expression->syntax->kind) {
		case SyntaxKind::UnaryBitwiseAndExpression: cv = SVInt(v.reductionAnd()); break;
		case SyntaxKind::UnaryBitwiseOrExpression: cv = SVInt(v.reductionOr()); break;
		case SyntaxKind::UnaryBitwiseXorExpression: cv = SVInt(v.reductionXor()); break;
		case SyntaxKind::UnaryBitwiseNandExpression: cv = SVInt(!v.reductionAnd()); break;
		case SyntaxKind::UnaryBitwiseNorExpression: cv = SVInt(!v.reductionOr()); break;
		case SyntaxKind::UnaryBitwiseXnorExpression: cv = SVInt(!v.reductionXor()); break;
		case SyntaxKind::UnaryLogicalNotExpression: cv = SVInt(!v); break;
			DEFAULT_UNREACHABLE;
	}
	expression->constantValue = cv;
}

void SemanticModel::propagateAndFoldArithmeticOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
	expression->type = type;
	propagateAndFold(expression->left, type);
	propagateAndFold(expression->right, type);

	ConstantValue cv;
	SVInt& l = get<SVInt>(expression->left->constantValue);
	SVInt& r = get<SVInt>(expression->right->constantValue);

	switch (expression->syntax->kind) {
		case SyntaxKind::AddExpression: cv = l + r; break;
		case SyntaxKind::SubtractExpression: cv = l - r; break;
		case SyntaxKind::MultiplyExpression: cv = l * r; break;
		case SyntaxKind::DivideExpression: cv = l / r; break;
		case SyntaxKind::ModExpression: cv = l % r; break;
		case SyntaxKind::BinaryAndExpression: cv = l & r; break;
		case SyntaxKind::BinaryOrExpression: cv = l | r; break;
		case SyntaxKind::BinaryXorExpression: cv = l ^ r; break;
		case SyntaxKind::BinaryXnorExpression: cv = l.xnor(r); break;
			DEFAULT_UNREACHABLE;
	}
	expression->constantValue = cv;
}

void SemanticModel::propagateAndFoldComparisonOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
}

void SemanticModel::propagateAndFoldRelationalOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
}

void SemanticModel::propagateAndFoldShiftOrPowerOperator(BoundBinaryExpression* expression, const TypeSymbol* type) {
}

}<|endoftext|>


<commit_before>#include <stdio.h>
#include <string>
#include "zmq.hpp"
#include "canna_core.h"
#include "canna_random.h"

int main(int argc, char** argv)
{
    if (argc < 2) {
        printf("usage: peering me {you} ...\n");
        return 0;
    }

    char *self = argv[1];
    printf("I: preparing broker at %s ... \n", self);
    CaRandom random;
    random.SetSeed(canna_gettime());

    zmq::context_t context(1);

    zmq::socket_t statebe(context, ZMQ_PUB);
    char statebe_ipc[64];
    memset(statebe_ipc, 0, sizeof(statebe_ipc));
    sprintf(statebe_ipc, "ipc://%s-state.ipc", self);
    statebe.bind(statebe_ipc);

    zmq::socket_t statefe(context, ZMQ_SUB);
    const char *filter = "";
    statefe.setsockopt(ZMQ_SUBSCRIBE, filter, strlen(filter));
    for (int index = 2; index < argc; index++) {
        char *peer = argv[index];
        char statefe_ipc[64];
        memset(statefe_ipc, 0, sizeof(statefe_ipc));
        sprintf(statebe_ipc, "ipc://%s-state.ipc", peer);
        printf("I: connecting to state backend at '%s'\n", statefe_ipc);
        statefe.connect(statefe_ipc);
    }

    while (true) {
        zmq::pollitem_t items[] = {(void *)statefe, 0, ZMQ_POLLIN, 0};
        zmq::poll(items, 1, 1000);

        if (items[0].revents & ZMQ_POLLIN) {
            std::string peer_name = canna_recv(statefe);
            std::string available = canna_recv(statefe);
            printf("%s - %s work free \n", peer_name.c_str(), available.c_str());
        } else {
            canna_send(statebe, self);
            canna_send(statebe, "ping");
        }
    }

    return 0;
}
<commit_msg>bug fixed<commit_after>#include <stdio.h>
#include <string>
#include "zmq.hpp"
#include "canna_core.h"
#include "canna_random.h"

int main(int argc, char** argv)
{
    if (argc < 2) {
        printf("usage: peering me {you} ...\n");
        return 0;
    }

    char *self = argv[1];
    printf("I: preparing broker at %s ... \n", self);
    CaRandom random;
    random.SetSeed(canna_gettime());

    zmq::context_t context(1);

    zmq::socket_t statebe(context, ZMQ_PUB);
    char statebe_ipc[64];
    memset(statebe_ipc, 0, sizeof(statebe_ipc));
    sprintf(statebe_ipc, "ipc://%s-state.ipc", self);
    printf("I: connecting to state backend at '%s'\n", statebe_ipc);
    statebe.bind(statebe_ipc);

    zmq::socket_t statefe(context, ZMQ_SUB);
    const char *filter = "";
    statefe.setsockopt(ZMQ_SUBSCRIBE, filter, strlen(filter));
    for (int index = 2; index < argc; index++) {
        char *peer = argv[index];
        char statefe_ipc[64];
        memset(statefe_ipc, 0, sizeof(statefe_ipc));
        sprintf(statefe_ipc, "ipc://%s-state.ipc", peer);
        printf("I: connecting to state backend at '%s'\n", statefe_ipc);
        statefe.connect(statefe_ipc);
    }

    while (true) {
        zmq::pollitem_t items[] = {(void *)statefe, 0, ZMQ_POLLIN, 0};
        zmq::poll(items, 1, 1000);

        if (items[0].revents & ZMQ_POLLIN) {
            std::string peer_name = canna_recv(statefe);
            std::string available = canna_recv(statefe);
            printf("%s - %s work free \n", peer_name.c_str(), available.c_str());
        } else {
            canna_send(statebe, self);
            canna_send(statebe, "ping");
        }
    }

    return 0;
}
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  $RCSfile: accessiblecontexthelper.cxx,v $
 *
 *  $Revision: 1.13 $
 *
 *  last change: $Author: vg $ $Date: 2003-04-24 17:27:02 $
 *
 *  The Contents of this file are made available subject to the terms of
 *  either of the following licenses
 *
 *         - GNU Lesser General Public License Version 2.1
 *         - Sun Industry Standards Source License Version 1.1
 *
 *  Sun Microsystems Inc., October, 2000
 *
 *  GNU Lesser General Public License Version 2.1
 *  =============================================
 *  Copyright 2000 by Sun Microsystems, Inc.
 *  901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *  This library is free software; you can redistribute it and/or
 *  modify it under the terms of the GNU Lesser General Public
 *  License version 2.1, as published by the Free Software Foundation.
 *
 *  This library is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *  Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public
 *  License along with this library; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *  MA  02111-1307  USA
 *
 *
 *  Sun Industry Standards Source License Version 1.1
 *  =================================================
 *  The contents of this file are subject to the Sun Industry Standards
 *  Source License Version 1.1 (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.openoffice.org/license.html.
 *
 *  Software provided under this License is provided on an "AS IS" basis,
 *  WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING,
 *  WITHOUT LIMITATION, WARRANTIES THAT THE SOFTWARE IS FREE OF DEFECTS,
 *  MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE, OR NON-INFRINGING.
 *  See the License for the specific provisions governing your rights and
 *  obligations concerning the Software.
 *
 *  The Initial Developer of the Original Code is: Sun Microsystems, Inc..
 *
 *  Copyright: 2000 by Sun Microsystems, Inc.
 *
 *  All Rights Reserved.
 *
 *  Contributor(s): _______________________________________
 *
 *
 ************************************************************************/

#ifndef COMPHELPER_ACCESSIBLE_CONTEXT_HELPER_HXX
#include <comphelper/accessiblecontexthelper.hxx>
#endif
#ifndef INCLUDED_COMPHELPER_ACCESSIBLEEVENTBUFFER_HXX
#include <comphelper/accessibleeventbuffer.hxx>
#endif
#ifndef _OSL_DIAGNOSE_H_
#include <osl/diagnose.h>
#endif
#ifndef _CPPUHELPER_WEAKREF_HXX_
#include <cppuhelper/weakref.hxx>
#endif

#ifndef _COM_SUN_STAR_ACCESSIBILITY_ACCESSIBLEEVENTID_HPP_
#include <com/sun/star/accessibility/AccessibleEventId.hpp>
#endif
#ifndef _COM_SUN_STAR_ACCESSIBILITY_ACCESSIBLESTATETYPE_HPP_
#include <com/sun/star/accessibility/AccessibleStateType.hpp>
#endif

#ifndef COMPHELPER_ACCESSIBLE_EVENT_NOTIFIER
#include <comphelper/accessibleeventnotifier.hxx>
#endif

//.........................................................................
namespace comphelper
{
//.........................................................................

    using namespace ::com::sun::star::uno;
    using namespace ::com::sun::star::lang;
    using namespace ::com::sun::star::accessibility;

    //=====================================================================
    //= OContextHelper_Impl
    //=====================================================================
    /** implementation class for OAccessibleContextHelper. No own thread safety!
    */
    class OContextHelper_Impl
    {
    private:
        OAccessibleContextHelper*           m_pAntiImpl;        // the owning instance
        IMutex*                             m_pExternalLock;    // the optional additional external lock

        ::cppu::OInterfaceContainerHelper*  m_pEventListeners;
        WeakReference< XAccessible >        m_aCreator;         // the XAccessible which created our XAccessibleContext

        AccessibleEventNotifier::TClientId  m_nClientId;

    public:
        inline  Reference< XAccessible >    getCreator( ) const                 { return m_aCreator; }
        inline  void                        setCreator( const Reference< XAccessible >& _rAcc );

        inline  IMutex*                     getExternalLock( )                  { return m_pExternalLock; }
        inline  void                        setExternalLock( IMutex* _pLock )   { m_pExternalLock = _pLock; }

        inline  AccessibleEventNotifier::TClientId
                                            getClientId() const                 { return m_nClientId; }
        inline  void                        setClientId( const AccessibleEventNotifier::TClientId _nId )
                                                                                { m_nClientId = _nId; }

    public:
        OContextHelper_Impl( OAccessibleContextHelper* _pAntiImpl )
            :m_pAntiImpl( _pAntiImpl )
            ,m_pExternalLock( NULL )
            ,m_pEventListeners( NULL )
            ,m_nClientId( 0 )
        {
        }
    };

    //---------------------------------------------------------------------
    inline  void OContextHelper_Impl::setCreator( const Reference< XAccessible >& _rAcc )
    {
        m_aCreator = _rAcc;
    }

    //=====================================================================
    //= OAccessibleContextHelper
    //=====================================================================
    //---------------------------------------------------------------------
    OAccessibleContextHelper::OAccessibleContextHelper( )
        :OAccessibleContextHelper_Base( GetMutex() )
        ,m_pImpl( NULL )
    {
        m_pImpl = new OContextHelper_Impl( this );
    }

    //---------------------------------------------------------------------
    OAccessibleContextHelper::OAccessibleContextHelper( IMutex* _pExternalLock )
        :OAccessibleContextHelper_Base( GetMutex() )
        ,m_pImpl( NULL )
    {
        m_pImpl = new OContextHelper_Impl( this );
        m_pImpl->setExternalLock( _pExternalLock );
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::forgetExternalLock()
    {
        m_pImpl->setExternalLock( NULL );
    }

    //---------------------------------------------------------------------
    OAccessibleContextHelper::~OAccessibleContextHelper( )
    {
        forgetExternalLock();
            // this ensures that the lock, which may be already destroyed as part of the derivee,
            // is not used anymore

        ensureDisposed();

        delete m_pImpl;
        m_pImpl = NULL;
    }

    //---------------------------------------------------------------------
    IMutex* OAccessibleContextHelper::getExternalLock( )
    {
        return m_pImpl->getExternalLock();
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::disposing()
    {
        ::osl::ClearableMutexGuard aGuard( GetMutex() );

        if ( m_pImpl->getClientId( ) )
        {
            AccessibleEventNotifier::revokeClientNotifyDisposing( m_pImpl->getClientId( ), *this );
            m_pImpl->setClientId( 0 );
        }
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::addEventListener( const Reference< XAccessibleEventListener >& _rxListener ) throw (RuntimeException)
    {
        OMutexGuard aGuard( getExternalLock() );
            // don't use the OContextEntryGuard - it will throw an exception if we're not alive
            // anymore, while the most recent specification for XComponent states that we should
            // silently ignore the call in such a situation
        if ( !isAlive() )
        {
            if ( _rxListener.is() )
                _rxListener->disposing( EventObject( *this ) );
            return;
        }

        if ( _rxListener.is() )
        {
            if ( !m_pImpl->getClientId( ) )
                m_pImpl->setClientId( AccessibleEventNotifier::registerClient( ) );

            AccessibleEventNotifier::addEventListener( m_pImpl->getClientId( ), _rxListener );
        }
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::removeEventListener( const Reference< XAccessibleEventListener >& _rxListener ) throw (RuntimeException)
    {
        OMutexGuard aGuard( getExternalLock() );
            // don't use the OContextEntryGuard - it will throw an exception if we're not alive
            // anymore, while the most recent specification for XComponent states that we should
            // silently ignore the call in such a situation
        if ( !isAlive() )
            return;

        if ( _rxListener.is() )
        {
            sal_Int32 nListenerCount = AccessibleEventNotifier::removeEventListener( m_pImpl->getClientId( ), _rxListener );
            if ( !nListenerCount )
            {
                // no listeners anymore
                // -> revoke ourself. This may lead to the notifier thread dying (if we were the last client),
                // and at least to us not firing any events anymore, in case somebody calls
                // NotifyAccessibleEvent, again
                AccessibleEventNotifier::revokeClient( m_pImpl->getClientId( ) );
                m_pImpl->setClientId( 0 );
            }
        }
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::NotifyAccessibleEvent( const sal_Int16 _nEventId,
        const Any& _rOldValue, const Any& _rNewValue )
    {
        if ( !m_pImpl->getClientId( ) )
            // if we don't have a client id for the notifier, then we don't have listeners, then
            // we don't need to notify anything
            return;

        // build an event object
        AccessibleEventObject aEvent;
        aEvent.Source = *this;
        aEvent.EventId = _nEventId;
        aEvent.OldValue = _rOldValue;
        aEvent.NewValue = _rNewValue;

        // let the notifier handle this event
        AccessibleEventNotifier::addEvent( m_pImpl->getClientId( ), aEvent );
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::BufferAccessibleEvent( const sal_Int16 _nEventId,
        const Any& _rOldValue, const Any& _rNewValue,
        AccessibleEventBuffer & _rBuffer )
    {
        // TODO: this whole method (as well as the class AccessibleEventBuffer) should be removed
        // The reasons why they have been introduces id that we needed to collect a set of events
        // before notifying them alltogether (after releasing our mutex). With the other
        // NotifyAccessibleEvent being asynchronous now, this should not be necessary anymore
        // - clients could use the other version now.

        // copy our current listeners
        Sequence< Reference< XInterface > > aListeners;
        if ( m_pImpl->getClientId( ) )
            aListeners = AccessibleEventNotifier::getEventListeners( m_pImpl->getClientId( ) );

        if ( aListeners.getLength() )
        {
            AccessibleEventObject aEvent;
            aEvent.Source = *this;
            OSL_ENSURE( aEvent.Source.is(), "OAccessibleContextHelper::BufferAccessibleEvent: invalid creator!" );
            aEvent.EventId = _nEventId;
            aEvent.OldValue = _rOldValue;
            aEvent.NewValue = _rNewValue;

            _rBuffer.addEvent( aEvent, aListeners );
        }
    }

    //---------------------------------------------------------------------
    sal_Bool OAccessibleContextHelper::isAlive() const
    {
        return !GetBroadcastHelper().bDisposed && !GetBroadcastHelper().bInDispose;
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::ensureAlive() const SAL_THROW( ( DisposedException ) )
    {
        if( !isAlive() )
            throw DisposedException();
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::ensureDisposed( )
    {
        if ( !GetBroadcastHelper().bDisposed )
        {
            OSL_ENSURE( 0 == m_refCount, "OAccessibleContextHelper::ensureDisposed: this method _has_ to be called from without your dtor only!" );
            acquire();
            dispose();
        }
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::lateInit( const Reference< XAccessible >& _rxAccessible )
    {
        m_pImpl->setCreator( _rxAccessible );
    }

    //---------------------------------------------------------------------
    Reference< XAccessible > OAccessibleContextHelper::getAccessibleCreator( ) const
    {
        return m_pImpl->getCreator();
    }

    //---------------------------------------------------------------------
    sal_Int32 SAL_CALL OAccessibleContextHelper::getAccessibleIndexInParent(  ) throw (RuntimeException)
    {
        OExternalLockGuard aGuard( this );

        // -1 for child not found/no parent (according to specification)
        sal_Int32 nRet = -1;

        try
        {

            Reference< XAccessibleContext > xParentContext( implGetParentContext() );

            //  iterate over parent's children and search for this object
            if ( xParentContext.is() )
            {
                // our own XAccessible for comparing with the children of our parent
                Reference< XAccessible > xCreator( m_pImpl->getCreator() );

                OSL_ENSURE( xCreator.is(), "OAccessibleContextHelper::getAccessibleIndexInParent: invalid creator!" );
                    // two ideas why this could be NULL:
                    // * nobody called our late ctor (init), so we never had a creator at all -> bad
                    // * the creator is already dead. In this case, we should have been disposed, and
                    //   never survived the above OContextEntryGuard.
                    // in all other situations the creator should be non-NULL

                if ( xCreator.is() )
                {
                    sal_Int32 nChildCount = xParentContext->getAccessibleChildCount();
                    for ( sal_Int32 nChild = 0; ( nChild < nChildCount ) && ( -1 == nRet ); ++nChild )
                    {
                        Reference< XAccessible > xChild( xParentContext->getAccessibleChild( nChild ) );
                        if ( xChild.get() == xCreator.get() )
                            nRet = nChild;
                    }
                }
            }
        }
        catch( const Exception& )
        {
            OSL_ENSURE( sal_False, "OAccessibleContextHelper::getAccessibleIndexInParent: caught an exception!" );
        }

        return nRet;
    }

    //---------------------------------------------------------------------
    Locale SAL_CALL OAccessibleContextHelper::getLocale(  ) throw (IllegalAccessibleComponentStateException, RuntimeException)
    {
        // simply ask the parent
        Reference< XAccessible > xParent = getAccessibleParent();
        Reference< XAccessibleContext > xParentContext;
        if ( xParent.is() )
            xParentContext = xParent->getAccessibleContext();

        if ( !xParentContext.is() )
            throw IllegalAccessibleComponentStateException( ::rtl::OUString(), *this );

        return xParentContext->getLocale();
    }

    //---------------------------------------------------------------------
    Reference< XAccessibleContext > OAccessibleContextHelper::implGetParentContext() SAL_THROW( ( RuntimeException ) )
    {
        Reference< XAccessible > xParent = getAccessibleParent();
        Reference< XAccessibleContext > xParentContext;
        if ( xParent.is() )
            xParentContext = xParent->getAccessibleContext();
        return xParentContext;
    }

//.........................................................................
}   // namespace comphelper
//.........................................................................

<commit_msg>INTEGRATION: CWS ooo19126 (1.13.264); FILE MERGED 2005/09/05 15:23:57 rt 1.13.264.1: #i54170# Change license header: remove SISSL<commit_after>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: accessiblecontexthelper.cxx,v $
 *
 *  $Revision: 1.14 $
 *
 *  last change: $Author: rt $ $Date: 2005-09-08 02:46:36 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    This library is free software; you can redistribute it and/or
 *    modify it under the terms of the GNU Lesser General Public
 *    License version 2.1, as published by the Free Software Foundation.
 *
 *    This library is distributed in the hope that it will be useful,
 *    but WITHOUT ANY WARRANTY; without even the implied warranty of
 *    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 *    Lesser General Public License for more details.
 *
 *    You should have received a copy of the GNU Lesser General Public
 *    License along with this library; if not, write to the Free Software
 *    Foundation, Inc., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

#ifndef COMPHELPER_ACCESSIBLE_CONTEXT_HELPER_HXX
#include <comphelper/accessiblecontexthelper.hxx>
#endif
#ifndef INCLUDED_COMPHELPER_ACCESSIBLEEVENTBUFFER_HXX
#include <comphelper/accessibleeventbuffer.hxx>
#endif
#ifndef _OSL_DIAGNOSE_H_
#include <osl/diagnose.h>
#endif
#ifndef _CPPUHELPER_WEAKREF_HXX_
#include <cppuhelper/weakref.hxx>
#endif

#ifndef _COM_SUN_STAR_ACCESSIBILITY_ACCESSIBLEEVENTID_HPP_
#include <com/sun/star/accessibility/AccessibleEventId.hpp>
#endif
#ifndef _COM_SUN_STAR_ACCESSIBILITY_ACCESSIBLESTATETYPE_HPP_
#include <com/sun/star/accessibility/AccessibleStateType.hpp>
#endif

#ifndef COMPHELPER_ACCESSIBLE_EVENT_NOTIFIER
#include <comphelper/accessibleeventnotifier.hxx>
#endif

//.........................................................................
namespace comphelper
{
//.........................................................................

    using namespace ::com::sun::star::uno;
    using namespace ::com::sun::star::lang;
    using namespace ::com::sun::star::accessibility;

    //=====================================================================
    //= OContextHelper_Impl
    //=====================================================================
    /** implementation class for OAccessibleContextHelper. No own thread safety!
    */
    class OContextHelper_Impl
    {
    private:
        OAccessibleContextHelper*           m_pAntiImpl;        // the owning instance
        IMutex*                             m_pExternalLock;    // the optional additional external lock

        ::cppu::OInterfaceContainerHelper*  m_pEventListeners;
        WeakReference< XAccessible >        m_aCreator;         // the XAccessible which created our XAccessibleContext

        AccessibleEventNotifier::TClientId  m_nClientId;

    public:
        inline  Reference< XAccessible >    getCreator( ) const                 { return m_aCreator; }
        inline  void                        setCreator( const Reference< XAccessible >& _rAcc );

        inline  IMutex*                     getExternalLock( )                  { return m_pExternalLock; }
        inline  void                        setExternalLock( IMutex* _pLock )   { m_pExternalLock = _pLock; }

        inline  AccessibleEventNotifier::TClientId
                                            getClientId() const                 { return m_nClientId; }
        inline  void                        setClientId( const AccessibleEventNotifier::TClientId _nId )
                                                                                { m_nClientId = _nId; }

    public:
        OContextHelper_Impl( OAccessibleContextHelper* _pAntiImpl )
            :m_pAntiImpl( _pAntiImpl )
            ,m_pExternalLock( NULL )
            ,m_pEventListeners( NULL )
            ,m_nClientId( 0 )
        {
        }
    };

    //---------------------------------------------------------------------
    inline  void OContextHelper_Impl::setCreator( const Reference< XAccessible >& _rAcc )
    {
        m_aCreator = _rAcc;
    }

    //=====================================================================
    //= OAccessibleContextHelper
    //=====================================================================
    //---------------------------------------------------------------------
    OAccessibleContextHelper::OAccessibleContextHelper( )
        :OAccessibleContextHelper_Base( GetMutex() )
        ,m_pImpl( NULL )
    {
        m_pImpl = new OContextHelper_Impl( this );
    }

    //---------------------------------------------------------------------
    OAccessibleContextHelper::OAccessibleContextHelper( IMutex* _pExternalLock )
        :OAccessibleContextHelper_Base( GetMutex() )
        ,m_pImpl( NULL )
    {
        m_pImpl = new OContextHelper_Impl( this );
        m_pImpl->setExternalLock( _pExternalLock );
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::forgetExternalLock()
    {
        m_pImpl->setExternalLock( NULL );
    }

    //---------------------------------------------------------------------
    OAccessibleContextHelper::~OAccessibleContextHelper( )
    {
        forgetExternalLock();
            // this ensures that the lock, which may be already destroyed as part of the derivee,
            // is not used anymore

        ensureDisposed();

        delete m_pImpl;
        m_pImpl = NULL;
    }

    //---------------------------------------------------------------------
    IMutex* OAccessibleContextHelper::getExternalLock( )
    {
        return m_pImpl->getExternalLock();
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::disposing()
    {
        ::osl::ClearableMutexGuard aGuard( GetMutex() );

        if ( m_pImpl->getClientId( ) )
        {
            AccessibleEventNotifier::revokeClientNotifyDisposing( m_pImpl->getClientId( ), *this );
            m_pImpl->setClientId( 0 );
        }
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::addEventListener( const Reference< XAccessibleEventListener >& _rxListener ) throw (RuntimeException)
    {
        OMutexGuard aGuard( getExternalLock() );
            // don't use the OContextEntryGuard - it will throw an exception if we're not alive
            // anymore, while the most recent specification for XComponent states that we should
            // silently ignore the call in such a situation
        if ( !isAlive() )
        {
            if ( _rxListener.is() )
                _rxListener->disposing( EventObject( *this ) );
            return;
        }

        if ( _rxListener.is() )
        {
            if ( !m_pImpl->getClientId( ) )
                m_pImpl->setClientId( AccessibleEventNotifier::registerClient( ) );

            AccessibleEventNotifier::addEventListener( m_pImpl->getClientId( ), _rxListener );
        }
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::removeEventListener( const Reference< XAccessibleEventListener >& _rxListener ) throw (RuntimeException)
    {
        OMutexGuard aGuard( getExternalLock() );
            // don't use the OContextEntryGuard - it will throw an exception if we're not alive
            // anymore, while the most recent specification for XComponent states that we should
            // silently ignore the call in such a situation
        if ( !isAlive() )
            return;

        if ( _rxListener.is() )
        {
            sal_Int32 nListenerCount = AccessibleEventNotifier::removeEventListener( m_pImpl->getClientId( ), _rxListener );
            if ( !nListenerCount )
            {
                // no listeners anymore
                // -> revoke ourself. This may lead to the notifier thread dying (if we were the last client),
                // and at least to us not firing any events anymore, in case somebody calls
                // NotifyAccessibleEvent, again
                AccessibleEventNotifier::revokeClient( m_pImpl->getClientId( ) );
                m_pImpl->setClientId( 0 );
            }
        }
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::NotifyAccessibleEvent( const sal_Int16 _nEventId,
        const Any& _rOldValue, const Any& _rNewValue )
    {
        if ( !m_pImpl->getClientId( ) )
            // if we don't have a client id for the notifier, then we don't have listeners, then
            // we don't need to notify anything
            return;

        // build an event object
        AccessibleEventObject aEvent;
        aEvent.Source = *this;
        aEvent.EventId = _nEventId;
        aEvent.OldValue = _rOldValue;
        aEvent.NewValue = _rNewValue;

        // let the notifier handle this event
        AccessibleEventNotifier::addEvent( m_pImpl->getClientId( ), aEvent );
    }

    //---------------------------------------------------------------------
    void SAL_CALL OAccessibleContextHelper::BufferAccessibleEvent( const sal_Int16 _nEventId,
        const Any& _rOldValue, const Any& _rNewValue,
        AccessibleEventBuffer & _rBuffer )
    {
        // TODO: this whole method (as well as the class AccessibleEventBuffer) should be removed
        // The reasons why they have been introduces id that we needed to collect a set of events
        // before notifying them alltogether (after releasing our mutex). With the other
        // NotifyAccessibleEvent being asynchronous now, this should not be necessary anymore
        // - clients could use the other version now.

        // copy our current listeners
        Sequence< Reference< XInterface > > aListeners;
        if ( m_pImpl->getClientId( ) )
            aListeners = AccessibleEventNotifier::getEventListeners( m_pImpl->getClientId( ) );

        if ( aListeners.getLength() )
        {
            AccessibleEventObject aEvent;
            aEvent.Source = *this;
            OSL_ENSURE( aEvent.Source.is(), "OAccessibleContextHelper::BufferAccessibleEvent: invalid creator!" );
            aEvent.EventId = _nEventId;
            aEvent.OldValue = _rOldValue;
            aEvent.NewValue = _rNewValue;

            _rBuffer.addEvent( aEvent, aListeners );
        }
    }

    //---------------------------------------------------------------------
    sal_Bool OAccessibleContextHelper::isAlive() const
    {
        return !GetBroadcastHelper().bDisposed && !GetBroadcastHelper().bInDispose;
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::ensureAlive() const SAL_THROW( ( DisposedException ) )
    {
        if( !isAlive() )
            throw DisposedException();
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::ensureDisposed( )
    {
        if ( !GetBroadcastHelper().bDisposed )
        {
            OSL_ENSURE( 0 == m_refCount, "OAccessibleContextHelper::ensureDisposed: this method _has_ to be called from without your dtor only!" );
            acquire();
            dispose();
        }
    }

    //---------------------------------------------------------------------
    void OAccessibleContextHelper::lateInit( const Reference< XAccessible >& _rxAccessible )
    {
        m_pImpl->setCreator( _rxAccessible );
    }

    //---------------------------------------------------------------------
    Reference< XAccessible > OAccessibleContextHelper::getAccessibleCreator( ) const
    {
        return m_pImpl->getCreator();
    }

    //---------------------------------------------------------------------
    sal_Int32 SAL_CALL OAccessibleContextHelper::getAccessibleIndexInParent(  ) throw (RuntimeException)
    {
        OExternalLockGuard aGuard( this );

        // -1 for child not found/no parent (according to specification)
        sal_Int32 nRet = -1;

        try
        {

            Reference< XAccessibleContext > xParentContext( implGetParentContext() );

            //  iterate over parent's children and search for this object
            if ( xParentContext.is() )
            {
                // our own XAccessible for comparing with the children of our parent
                Reference< XAccessible > xCreator( m_pImpl->getCreator() );

                OSL_ENSURE( xCreator.is(), "OAccessibleContextHelper::getAccessibleIndexInParent: invalid creator!" );
                    // two ideas why this could be NULL:
                    // * nobody called our late ctor (init), so we never had a creator at all -> bad
                    // * the creator is already dead. In this case, we should have been disposed, and
                    //   never survived the above OContextEntryGuard.
                    // in all other situations the creator should be non-NULL

                if ( xCreator.is() )
                {
                    sal_Int32 nChildCount = xParentContext->getAccessibleChildCount();
                    for ( sal_Int32 nChild = 0; ( nChild < nChildCount ) && ( -1 == nRet ); ++nChild )
                    {
                        Reference< XAccessible > xChild( xParentContext->getAccessibleChild( nChild ) );
                        if ( xChild.get() == xCreator.get() )
                            nRet = nChild;
                    }
                }
            }
        }
        catch( const Exception& )
        {
            OSL_ENSURE( sal_False, "OAccessibleContextHelper::getAccessibleIndexInParent: caught an exception!" );
        }

        return nRet;
    }

    //---------------------------------------------------------------------
    Locale SAL_CALL OAccessibleContextHelper::getLocale(  ) throw (IllegalAccessibleComponentStateException, RuntimeException)
    {
        // simply ask the parent
        Reference< XAccessible > xParent = getAccessibleParent();
        Reference< XAccessibleContext > xParentContext;
        if ( xParent.is() )
            xParentContext = xParent->getAccessibleContext();

        if ( !xParentContext.is() )
            throw IllegalAccessibleComponentStateException( ::rtl::OUString(), *this );

        return xParentContext->getLocale();
    }

    //---------------------------------------------------------------------
    Reference< XAccessibleContext > OAccessibleContextHelper::implGetParentContext() SAL_THROW( ( RuntimeException ) )
    {
        Reference< XAccessible > xParent = getAccessibleParent();
        Reference< XAccessibleContext > xParentContext;
        if ( xParent.is() )
            xParentContext = xParent->getAccessibleContext();
        return xParentContext;
    }

//.........................................................................
}   // namespace comphelper
//.........................................................................

<|endoftext|>


<commit_before>//
//  GameModel.cpp
//  CatchiOS
//
//  Created by John Barbero Unenge on 10/7/12.
//  Copyright (c) 2012 John Barbero Unenge. All rights reserved.
//

#include "GameModel.hpp"
#include "../EventHandling/EventBus.hpp"
#include "../Helper/Logger.hpp"
#include "Physics/PBody.hpp"

GameModel::GameModel()
{
    m_physicsManager = new PhysicsManager();
	m_gameMap = new GameMap();

    m_player = new Player();
    m_chainsaw = 0;

}
GameModel::~GameModel()
{

}

void GameModel::update(float dt)
{
    if (m_chainsaw != 0){
        if (m_chainsaw->targetReached()){
            m_chainsaw->setTarget(m_player->getPosition());
        }
        m_chainsaw->update(dt);
    }
    m_physicsManager->update(dt);
    m_player->update();
//    m_gameMap->update();
}
Vector2d* GameModel::getCenterPoint()
{
    return new Vector2d(m_player->getPosition().x, m_player->getPosition().y);
}

void GameModel::playerJump()
{
    m_player->jump();
}
void GameModel::playerThrowAt(int x, int y)
{
    b2Vec2 target = b2Vec2(x,y);
    m_chainsaw = new Chainsaw(b2Vec2(0.3, 0.3 ), m_player->getPosition(), target, false, true, PB_PLATFORM_1);
    Log(LOG_INFO, "GameModel", generateCString("Player threw his chainsaw at: %i,%i", x, y));
}<commit_msg>More accurate target for chainsaw<commit_after>//
//  GameModel.cpp
//  CatchiOS
//
//  Created by John Barbero Unenge on 10/7/12.
//  Copyright (c) 2012 John Barbero Unenge. All rights reserved.
//

#include "GameModel.hpp"
#include "../EventHandling/EventBus.hpp"
#include "../Helper/Logger.hpp"
#include "Physics/PBody.hpp"
#include "../Helper/Constants.hpp"

GameModel::GameModel()
{
    m_physicsManager = new PhysicsManager();
	m_gameMap = new GameMap();

    m_player = new Player();
    m_chainsaw = 0;

}
GameModel::~GameModel()
{

}

void GameModel::update(float dt)
{
    if (m_chainsaw != 0){
        if (m_chainsaw->targetReached()){
            m_chainsaw->setTarget(m_player->getPosition());
            Log(LOG_INFO, "Chainsaw", "The Chainsaw has reached its target!!  ****");
        }
        m_chainsaw->update(dt);
    }
    m_physicsManager->update(dt);
    m_player->update();
//    m_gameMap->update();
}
Vector2d* GameModel::getCenterPoint()
{
    return new Vector2d(m_player->getPosition().x, m_player->getPosition().y);
}

void GameModel::playerJump()
{
    m_player->jump();
}
void GameModel::playerThrowAt(int x, int y)
{
    double convertedX = x * Constants::getGameWidth();
    double convertedY = y * Constants::getGameHeight();

    b2Vec2 target = b2Vec2( convertedX + m_player->getPosition().x, convertedY + m_player->getPosition().y);
    b2Vec2 spawn = b2Vec2(m_player->getPosition().x + 3, m_player->getPosition().y + 3);
    m_chainsaw = new Chainsaw(b2Vec2(1.0, 1.0 ),spawn , target, false, true, PB_PLAYER);
    Log(LOG_INFO, "GameModel", generateCString("Player threw his chainsaw at: %i,%i", x, y));
}<|endoftext|>


<commit_before>#include <iostream>
using namespace std;

int numOfGoals;
int numOfSkills;
int numOfAwards;
int numOfJobs;
int numOfDegrees;
string age;
string phoneNumber;
string schoolName;
string majorr;
string concentration;
string minorr;
string gradDate;
string communityInvolvement;
string name;
string address;
string email;
string credentials;
bool majorBool;
bool minorBool;
bool gradDateBool;
bool degree;

int main() {
    /*
    cout << "Hello, Welcome to Resume Builder!" << endl;
    cout << "Input your name:" << endl;
    getline (cin, name);
    cout << "How old are you?" << endl;
    getline (cin, age);
    cout << "What is your Address?" << endl;
    getline (cin, address);
    cout << "What is your Phone Number?" << endl;
    getline (cin, phoneNumber);
    cout << "What is your email?" << endl;
    getline (cin, email);
    cout << "What is the name of your School?" << endl;
    getline (cin, schoolName);
    cout << "What is your Major? If you don't have one, type: 'none'" << endl;
    getline (cin, majorr);
    if (majorr == "none") {
        majorBool = false;
    }else {
        majorBool = true;
    }
    cout << "What is your Minor? If you don't have one, type 'none'" << endl;
    getline (cin, minorr);
    if (minorr == "none") {
        minorBool = false;
    } else {
        minorBool = true;
    }
    cout << "What is your graduation date? If you are still enrolled or something, type: 'none'" << endl;
    getline (cin, gradDate);
    if (gradDate == "none") {
        gradDateBool = false;
    } else {
        gradDateBool = true;
    }
    */
    cout << "How many degrees do you have? if none type 0 (zero)." << endl;
    cin >> numOfDegrees;
    if (numOfDegrees <= 0) {
        degree = false;
    } else {
        degree = true;
    }
    if (degree == 1) {
        string* degrees = new string[numOfDegrees];
        for (int i = 0; i < numOfDegrees; i++) {

        cout << "Degree " << i << ": " << endl;
        getline (cin, degrees[i]);

        }
    }
    cout << "it worked." << endl;
    while (numOfJobs > 4 || numOfJobs < 1) {
        cout << "How many jobs do you want to show (up to 4)?" << endl;
        cin >> numOfJobs;
        if (numOfJobs >4 || numOfJobs < 1) {
            cout << "Invalid Input." << endl;
        } else {
            cout << "valid input" << endl; //this output is filler
        }
    }

    return 0;
}

string jobs (string string) {
    //the return is filler for now
    return string;
}
<commit_msg>Update ResumeBuilder.cpp<commit_after>#include <iostream>
using namespace std;

int numOfGoals;
int numOfSkills;
int numOfAwards;
int numOfJobs;
int numOfDegrees;
string age;
string phoneNumber;
string schoolName;
string majorr;
string concentration;
string minorr;
string gradDate;
string communityInvolvement;
string name;
string address;
string email;
string credentials;
bool majorBool;
bool minorBool;
bool gradDateBool;
bool degree;

int main() {
    /*
    cout << "Hello, Welcome to Resume Builder!" << endl;
    cout << "Input your name:" << endl;
    getline (cin, name);
    cout << "How old are you?" << endl;
    getline (cin, age);
    cout << "What is your Address?" << endl;
    getline (cin, address);
    cout << "What is your Phone Number?" << endl;
    getline (cin, phoneNumber);
    cout << "What is your email?" << endl;
    getline (cin, email);
    cout << "What is the name of your School?" << endl;
    getline (cin, schoolName);
    cout << "What is your Major? If you don't have one, type: 'none'" << endl;
    getline (cin, majorr);
    if (majorr == "none") {
        majorBool = false;
    }else {
        majorBool = true;
    }
    cout << "What is your Minor? If you don't have one, type 'none'" << endl;
    getline (cin, minorr);
    if (minorr == "none") {
        minorBool = false;
    } else {
        minorBool = true;
    }
    cout << "What is your graduation date? If you are still enrolled or something, type: 'none'" << endl;
    getline (cin, gradDate);
    if (gradDate == "none") {
        gradDateBool = false;
    } else {
        gradDateBool = true;
    }
    */
    cout << "How many degrees do you have? if none type 0 (zero)." << endl;
    cin >> numOfDegrees;
    if (numOfDegrees <= 0) {
        degree = false;
    } else {
        degree = true;
    }
    if (degree == 1) {
        string* degrees = new string[numOfDegrees];
        for (int i = 0; i < numOfDegrees; i++) {

        cout << "Degree " << i + 1 << ": " << endl;
        cin >> degrees[i];

        }
    }
    cout << "it worked." << endl;
    while (numOfJobs > 4 || numOfJobs < 1) {
        cout << "How many jobs do you want to show (up to 4)?" << endl;
        cin >> numOfJobs;
        if (numOfJobs >4 || numOfJobs < 1) {
            cout << "Invalid Input." << endl;
        } else {
            cout << "valid input" << endl; //this output is filler
        }
    }

    return 0;
}

string jobs (string string) {
    //the return is filler for now
    return string;
}
<|endoftext|>


<commit_before>

// This file contains definition of C++ new/delete operators

#include <stddef.h>
#include <malloc.h>
#include "stdexcept.h"

__attribute__((weak))
void * operator new(size_t size) {
    void * mem = malloc(size);
    if(mem == NULL) {
        throw std::bad_alloc();
    }

    return mem;
}

__attribute__((weak))
void operator delete(void * ptr) {
    free(ptr);
}

__attribute__((weak))
void * operator new[](size_t size) {
    return ::operator new(size);
}

__attribute__((weak))
void operator delete[](void * ptr) {
    ::operator delete(ptr);
}

<commit_msg>set_new_handler was implemented<commit_after>

// This file contains definition of C++ new/delete operators

#include <stddef.h>
#include <malloc.h>
#include "stdexcept.h"

namespace std {
    void terminate();
}

typedef void (*new_handler)();
static new_handler new_handl = &std::terminate;

namespace std {
    new_handler set_new_handler(new_handler handl) {
        new_handler old = new_handl;
        new_handl = handl;
        return old;
    }
}

__attribute__((weak))
void * operator new(size_t size) {

    void * mem = malloc(size);
    while(mem == NULL) {
        new_handl();
        mem = malloc(size);
    }

    return mem;
}

__attribute__((weak))
void operator delete(void * ptr) {
    free(ptr);
}

__attribute__((weak))
void * operator new[](size_t size) {
    return ::operator new(size);
}

__attribute__((weak))
void operator delete[](void * ptr) {
    ::operator delete(ptr);
}

<|endoftext|>


<commit_before>/**
 * memory.cc - Contains stub definition of C++ new/delete operators.
 *
 * These definitions are intended to be used for testing and are weak symbols
 * to allow them to be replaced by definitions from a STL implementation.
 * These versions simply wrap malloc() and free(), they do not provide a
 * C++-specific allocator.
 */

#include <stddef.h>
#include <stdlib.h>
#include "stdexcept.h"

namespace std
{
	struct nothrow_t {};
}

/// The type of the function called when allocation fails.
typedef void (*new_handler)();
/**
 * The function to call when allocation fails.  By default, there is no
 * handler and a bad allocation exception is thrown if an allocation fails.
 */
static new_handler new_handl;

namespace std
{
	/**
	 * Sets a function to be called when there is a failure in new.
	 */
	__attribute__((weak))
	new_handler set_new_handler(new_handler handler)
	{
		return __sync_lock_test_and_set(&new_handl, handler);
	}
}

__attribute__((weak))
void* operator new(size_t size)
{
	void * mem = malloc(size);
	while (0 == mem)
	{
		if (0 != new_handl)
		{
			new_handl();
		}
		else
		{
			throw std::bad_alloc();
		}
		mem = malloc(size);
	}

	return mem;
}

__attribute__((weak))
void* operator new(size_t size, const std::nothrow_t &) throw()
{
	void *mem = malloc(size);
	while (0 == mem)
	{
		if (0 != new_handl)
		{
			try
			{
				new_handl();
			}
			catch (...)
			{
				// nothrow operator new should return NULL in case of
				// std::bad_alloc exception in new handler
				return NULL;
			}
		}
		else
		{
			return NULL;
		}
		mem = malloc(size);
	}

	return mem;
}

__attribute__((weak))
void operator delete(void * ptr)
{
	free(ptr);
}

__attribute__((weak))
void * operator new[](size_t size)
{
	return ::operator new(size);
}

__attribute__((weak))
void operator delete[](void * ptr)
{
	::operator delete(ptr);
}

<commit_msg>Fixed a warning.<commit_after>/**
 * memory.cc - Contains stub definition of C++ new/delete operators.
 *
 * These definitions are intended to be used for testing and are weak symbols
 * to allow them to be replaced by definitions from a STL implementation.
 * These versions simply wrap malloc() and free(), they do not provide a
 * C++-specific allocator.
 */

#include <stddef.h>
#include <stdlib.h>
#include "stdexcept.h"

namespace std
{
	struct nothrow_t {};
}

/// The type of the function called when allocation fails.
typedef void (*new_handler)();
/**
 * The function to call when allocation fails.  By default, there is no
 * handler and a bad allocation exception is thrown if an allocation fails.
 */
static new_handler new_handl;

namespace std
{
	/**
	 * Sets a function to be called when there is a failure in new.
	 */
	__attribute__((weak))
	new_handler set_new_handler(new_handler handler)
	{
		return __sync_lock_test_and_set(&new_handl, handler);
	}
}

__attribute__((weak))
void* operator new(size_t size)
{
	void * mem = malloc(size);
	while (0 == mem)
	{
		if (0 != new_handl)
		{
			new_handl();
		}
		else
		{
			throw std::bad_alloc();
		}
		mem = malloc(size);
	}

	return mem;
}

__attribute__((weak))
void* operator new(size_t size, const std::nothrow_t &) throw()
{
	void *mem = malloc(size);
	while (0 == mem)
	{
		if (0 != new_handl)
		{
			try
			{
				new_handl();
			}
			catch (...)
			{
				// nothrow operator new should return NULL in case of
				// std::bad_alloc exception in new handler
				return NULL;
			}
		}
		else
		{
			return NULL;
		}
		mem = malloc(size);
	}

	return mem;
}

__attribute__((weak))
void operator delete(void * ptr)
{
	free(ptr);
}

__attribute__((weak))
void * operator new[](size_t size)
{
	return ::operator new(size);
}

__attribute__((weak))
void operator delete[](void * ptr) throw()
{
	::operator delete(ptr);
}

<|endoftext|>


<commit_before>
#pragma once

#include "./a.hpp"

void b(float);

void N::nf(X x) {
	(void)x;
}

void sf(N::S&);

namespace N {
	S nsf();
}
<commit_msg>test/b.hpp: added [[noreturn]] to N::nsf().¹<commit_after>
#pragma once

#include "./a.hpp"

void b(float);

void N::nf(X x) {
	(void)x;
}

void sf(N::S&);

namespace N {
	[[noreturn]]
	S nsf();
}
<|endoftext|>


<commit_before>//
// Created by Miguel Rentes on 30/01/2017.
//

#include "STL.h"

void printKMax(int arr[], int n, int k) {
    deque<int> mydeque;
    int index = 0, iteration = 0, value = 0, greatest = 0;
    // pushing all the values on each k-elements to the front of the deque
    for (int i = 0; i < n; i++) {
        if (iteration == n-k+1)
            break;
        if (index < k) {
            mydeque.push_front(arr[i]);
            if (index == k - 1) {
                index = 0;
                iteration++;
                i = iteration-1;
            } else index++;
        }
    }
    index = 0;
    iteration = 0;
    // calculating the max value on each group of k-elements
    // and placing the max value on the back of the deque
    // and then print these values as they are the greatest found
    // ... to be continued
    for (int i= 0; i < n; i++) {
        if (iteration == n-k+1)
            break;
        if (index < k) {
            value = mydeque.front();
            mydeque.pop_front();
            if (value > greatest) {
                greatest = value;
            }
            if (index == k - 1) {
                mydeque.push_back(greatest);
                index = 0;
                greatest = 0;
                iteration++;
                i = iteration-1;
            } else index++;
        }
    }
    while(mydeque.size() > 0) {
        printf("%d ", mydeque.back());
        mydeque.pop_back();
    }
    printf("\n");
}

int main(void) {
    int t;
    cin >> t;
    while (t > 0) {
        int n, k;
        cin >> n >> k;
        int i;
        int arr[n];
        for (i = 0; i < n; i++)
            cin >> arr[i];
        printKMax(arr, n, k);
        t--;
    }
    return EXIT_SUCCESS;
}<commit_msg>Starts solution for the Deque-STL challenge.<commit_after>//
// Created by Miguel Rentes on 30/01/2017.
//

#include "STL.h"

void printKMax(int arr[], int n, int k) {
    deque<int> mydeque;
    int greatest = 0, value = 0, index = 0, iteration = 0;
    /*
     * pushing all the greatest values on each k-elements to the front of the deque
     */
    for (int i = 0; i < n; i++) {
        if (index < k) {
            value = arr[i];
            if (value > greatest)
                greatest = value;
            if (index == k - 1) {
                mydeque.push_front(greatest);
                greatest = 0;
                index = 0;
                iteration++;
                i = iteration-1;
            } else {
                index++;
            }
        }
    }
    /*
     * pop-ing the greatest values from the back of the deque
     */
    while(mydeque.size() > 0) {
        printf("%d ", mydeque.back());
        mydeque.pop_back();
    }
    printf("\n");
}

int main(void) {
    int t;
    cin >> t;
    while (t > 0) {
        int n, k;
        cin >> n >> k;
        int i;
        int arr[n];
        for (i = 0; i < n; i++)
            cin >> arr[i];
        printKMax(arr, n, k);
        t--;
    }
    return EXIT_SUCCESS;
}<|endoftext|>


<commit_before>//
//  CSwing.cpp
//  SwingGame
//
//  Created by Tim Brier on 31/10/2014.
//  Copyright (c) 2014 tbrier. All rights reserved.
//

// =============================================================================
// Include Files
// -----------------------------------------------------------------------------
#include "CSwing.hpp"
#include "CSwingGame.hpp"

// =============================================================================
// CSwing constructor/destructor
// -----------------------------------------------------------------------------
CSwing::CSwing(CPhysicsBody *theBob) :  mBob(theBob),
                                        mAttached(false)
{

}

CSwing::~CSwing()
{
    // Unregister this x-able
    if (mAttached)
    {
        CSwingGame::UnregisterRenderable(this);
        CSwingGame::UnregisterUpdateable(this);
    }
}

// =============================================================================
// CSwing::AttemptToAttach
// Find the first point between the bob and the aim point to attach to
// -----------------------------------------------------------------------------
void CSwing::AttemptToAttach(CVector2f theAimPoint)
{
    // Attach the swing if we can find a valid anchor point
    CVector2f anchorPoint;
    if (IsThereAValidAnchor(theAimPoint, &anchorPoint))
    {
        // Make sure we detach from any existing swing
        Detach();

        // Now attach
        mAttached = true;

        mOrigin = anchorPoint;
        mLength = GetDistanceToBob();

        // Register ourselves now we're active
        CSwingGame::RegisterRenderable(this);
        CSwingGame::RegisterUpdateable(this);
    }
}

// =============================================================================
// CSwing::Detach
// -----------------------------------------------------------------------------
void CSwing::Detach()
{
    if (mAttached)
    {
        mAttached = false;
        CSwingGame::UnregisterUpdateable(this);
        CSwingGame::UnregisterRenderable(this);
    }
}

// =============================================================================
// CSwing::AttenuateGravity
// Alter the affect of gravity based on the swings angle
// -----------------------------------------------------------------------------
CVector2f CSwing::AttenuateGravity(CVector2f gravity)
{
    // If we're not attached then don't affect gravity
    if (!mAttached)
    {
        return gravity;
    }

    // Throw away any component of the gravity that isn't perpendicular to the
    // swing
    return gravity.GetComponentInDirection(GetPerpendicularDirection());
}

// =============================================================================
// CSwing::Draw
// -----------------------------------------------------------------------------
void CSwing::Draw(CWindow *theWindow)
{
    theWindow->DrawLine(mBob->GetPosition(), mOrigin);
}

// =============================================================================
// CSwing::Update
// -----------------------------------------------------------------------------
void CSwing::Update(CTime elapsedTime)
{
    // Throw away any velocity of the bob that isn't perpendicular to the
    // swing
    CVector2f v = mBob->GetVelocity();
    CVector2f newV = v.GetComponentInDirection(GetPerpendicularDirection());
    mBob->SetVelocity(newV);

    // Make sure the bob isn't further away from the origin than the length of
    // the swing
    CVector2f bobToOrigin = mOrigin - mBob->GetPosition();
    float distance = bobToOrigin.GetMagnitude();
    if (distance > mLength)
    {
        // Move by the difference between the distance and length
        float moveDistance = distance - mLength;
        bobToOrigin.Normalise();
        bobToOrigin *= moveDistance;
        mBob->GetShape()->move(bobToOrigin);
    }
}

// =============================================================================
// CSwing::GetDistanceToBob
// -----------------------------------------------------------------------------
float CSwing::GetDistanceToBob()
{
    CVector2f bobPosition = mBob->GetPosition();
    CVector2f bobToOrigin = mOrigin - bobPosition;
    return bobToOrigin.GetMagnitude();
}

// =============================================================================
// CSwing::IsThereAValidAnchor
// -----------------------------------------------------------------------------
bool CSwing::IsThereAValidAnchor(CVector2f theAimPoint, CVector2f *anchor)
{
    // For now just say the aim point is valid
    *anchor = theAimPoint;
    return true;
}

// =============================================================================
// CSwing::GetPerpendicularDirection
// -----------------------------------------------------------------------------
CVector2f CSwing::GetPerpendicularDirection()
{
    CVector2f originToBob = mBob->GetPosition() - mOrigin;
    originToBob.Normalise();

    CVector2f perpendicularDirection;
    perpendicularDirection.x = originToBob.y;
    perpendicularDirection.y = -originToBob.x;

    return perpendicularDirection;
}<commit_msg>Instead of throwing away velocity that isn't perpendicular to the swing every update just change the current velocities direction. Now velocity isn't dampened, but it does increase while swinging. This can be fixed by applying a damping I choose<commit_after>//
//  CSwing.cpp
//  SwingGame
//
//  Created by Tim Brier on 31/10/2014.
//  Copyright (c) 2014 tbrier. All rights reserved.
//

// =============================================================================
// Include Files
// -----------------------------------------------------------------------------
#include "CSwing.hpp"
#include "CSwingGame.hpp"

// =============================================================================
// CSwing constructor/destructor
// -----------------------------------------------------------------------------
CSwing::CSwing(CPhysicsBody *theBob) :  mBob(theBob),
                                        mAttached(false)
{

}

CSwing::~CSwing()
{
    // Unregister this x-able
    if (mAttached)
    {
        CSwingGame::UnregisterRenderable(this);
        CSwingGame::UnregisterUpdateable(this);
    }
}

// =============================================================================
// CSwing::AttemptToAttach
// Find the first point between the bob and the aim point to attach to
// -----------------------------------------------------------------------------
void CSwing::AttemptToAttach(CVector2f theAimPoint)
{
    // Attach the swing if we can find a valid anchor point
    CVector2f anchorPoint;
    if (IsThereAValidAnchor(theAimPoint, &anchorPoint))
    {
        // Make sure we detach from any existing swing
        Detach();

        // Now attach
        mAttached = true;

        mOrigin = anchorPoint;
        mLength = GetDistanceToBob();

        // Throw away any velocity that isn't perpendicular to the swing
        CVector2f v = mBob->GetVelocity();
        CVector2f newV = v.GetComponentInDirection(GetPerpendicularDirection());
        mBob->SetVelocity(newV);

        // Register ourselves now we're active
        CSwingGame::RegisterRenderable(this);
        CSwingGame::RegisterUpdateable(this);
    }
}

// =============================================================================
// CSwing::Detach
// -----------------------------------------------------------------------------
void CSwing::Detach()
{
    if (mAttached)
    {
        mAttached = false;
        CSwingGame::UnregisterUpdateable(this);
        CSwingGame::UnregisterRenderable(this);
    }
}

// =============================================================================
// CSwing::AttenuateGravity
// Alter the affect of gravity based on the swings angle
// -----------------------------------------------------------------------------
CVector2f CSwing::AttenuateGravity(CVector2f gravity)
{
    // If we're not attached then don't affect gravity
    if (!mAttached)
    {
        return gravity;
    }

    // Throw away any component of the gravity that isn't perpendicular to the
    // swing
    return gravity.GetComponentInDirection(GetPerpendicularDirection());
}

// =============================================================================
// CSwing::Draw
// -----------------------------------------------------------------------------
void CSwing::Draw(CWindow *theWindow)
{
    theWindow->DrawLine(mBob->GetPosition(), mOrigin);
}

// =============================================================================
// CSwing::Update
// -----------------------------------------------------------------------------
void CSwing::Update(CTime elapsedTime)
{
    // Adjust the velocity so it is perpendicular to the swing
    CVector2f v = mBob->GetVelocity();
    CVector2f newV = v.GetComponentInDirection(GetPerpendicularDirection());
    newV.Normalise();
    newV *= v.GetMagnitude();
    mBob->SetVelocity(newV);

    // Make sure the bob isn't further away from the origin than the length of
    // the swing
    CVector2f bobToOrigin = mOrigin - mBob->GetPosition();
    float distance = bobToOrigin.GetMagnitude();
    if (distance > mLength)
    {
        // Move by the difference between the distance and length
        float moveDistance = distance - mLength;
        bobToOrigin.Normalise();
        bobToOrigin *= moveDistance;
        mBob->GetShape()->move(bobToOrigin);
    }
}

// =============================================================================
// CSwing::GetDistanceToBob
// -----------------------------------------------------------------------------
float CSwing::GetDistanceToBob()
{
    CVector2f bobPosition = mBob->GetPosition();
    CVector2f bobToOrigin = mOrigin - bobPosition;
    return bobToOrigin.GetMagnitude();
}

// =============================================================================
// CSwing::IsThereAValidAnchor
// -----------------------------------------------------------------------------
bool CSwing::IsThereAValidAnchor(CVector2f theAimPoint, CVector2f *anchor)
{
    // For now just say the aim point is valid
    *anchor = theAimPoint;
    return true;
}

// =============================================================================
// CSwing::GetPerpendicularDirection
// -----------------------------------------------------------------------------
CVector2f CSwing::GetPerpendicularDirection()
{
    CVector2f originToBob = mBob->GetPosition() - mOrigin;
    originToBob.Normalise();

    CVector2f perpendicularDirection;
    perpendicularDirection.x = originToBob.y;
    perpendicularDirection.y = -originToBob.x;

    return perpendicularDirection;
}<|endoftext|>


<commit_before>/*
 *  Fit.cpp
 *
 *  Copyright (c) 2017 Tobias Wood.
 *
 *  This Source Code Form is subject to the terms of the Mozilla Public
 *  License, v. 2.0. If a copy of the MPL was not distributed with this
 *  file, you can obtain one at http://mozilla.org/MPL/2.0/.
 *
 */

#include "QI/Fit.h"

#include <iostream>
#include <iomanip>
#include <algorithm>

namespace QI {

double standard_dev(const Eigen::ArrayXd &x) {
    return sqrt((x - x.mean()).square().sum() / (x.rows() - 1));
}

double mad_sigma(Eigen::ArrayXd &r, Eigen::ArrayXd &sr, const int p) {
    sr = r.abs();
    std::sort(sr.data(), sr.data() + sr.size());
    const size_t index = (sr.size() + p) / 2;
    return sr[index] / 0.6745;
}

Eigen::VectorXd LeastSquares(const Eigen::MatrixXd &X, const Eigen::VectorXd &y) {
    // Solve Xb = Y via least squares via QR decomposition
    Eigen::ColPivHouseholderQR<Eigen::MatrixXd> QR(X);
    Eigen::VectorXd b = QR.solve(y);
    return b;
}

Eigen::VectorXd RobustLeastSquares(const Eigen::MatrixXd &X, const Eigen::VectorXd &y) {
    // With thanks to gsl_multifit_robust & Matlab
    const double sig_y = standard_dev(y);
    const double sig_lower = (sig_y == 0) ? 1.0 : 1e-6 * sig_y;

    // Solve Xb = Y via least squares via QR decomposition, keep the decomposition around
    Eigen::ColPivHouseholderQR<Eigen::MatrixXd> QR(X);
    Eigen::VectorXd b = QR.solve(y);
    // Calculate leverage and correction factor from the 'thinQ' matrix
    Eigen::MatrixXd Q(X.rows(), X.cols()); Q.setIdentity();
    Q = QR.householderQ() * Q;
    Eigen::ArrayXd h = Q.array().square().rowwise().sum(); //(Q * Q.transpose()).diagonal();
    Eigen::ArrayXd corr_fac = (1.0 - h).sqrt();

    // For Huber at the moment
    const double tune = 1.345;
    int iter = 0;
    bool converged = false;

    // Allocate some workspace for loop
    Eigen::ArrayXd resid(y.rows()), sorted_resid(y.rows()), r(y.rows()), w(y.rows()), wy(y.rows());
    Eigen::VectorXd b_prev(b.rows());
    Eigen::MatrixXd wX(X.rows(), X.cols());
    while (!converged && (++iter < 10)) {
        resid = (y - X*b); // Calculate residuals
        const double sig = mad_sigma(resid, sorted_resid, X.cols()); // Get Median Absolute Deviation
        r = resid / (tune * std::max(sig, sig_lower) * corr_fac); // Adjust residuals
        std::cerr << "Iteration: " << iter << " total resid: " << resid.square().sum() << " adjusted resid: " << r.square().sum() << std::endl;
        w = 1 / r.abs().max(1); // Huber weights
        b_prev = b; // Save weights
        wX = w.matrix().asDiagonal() * X;
        wy = w * y.array();
        b = LeastSquares(wX, wy); // Weighted solve
        if (((b - b_prev).array().abs() < sqrt(std::numeric_limits<double>::epsilon())).all()) {
            converged = true;
        }
    }

    return b;
}

} // End namespace QI<commit_msg>ENH: Memory optimisations<commit_after>/*
 *  Fit.cpp
 *
 *  Copyright (c) 2017 Tobias Wood.
 *
 *  This Source Code Form is subject to the terms of the Mozilla Public
 *  License, v. 2.0. If a copy of the MPL was not distributed with this
 *  file, you can obtain one at http://mozilla.org/MPL/2.0/.
 *
 */

#include "QI/Fit.h"

#include <iostream>
#include <iomanip>
#include <algorithm>

namespace QI {

double standard_dev(const Eigen::ArrayXd &x) {
    return sqrt((x - x.mean()).square().sum() / (x.rows() - 1));
}

double mad_sigma(Eigen::ArrayXd &r, Eigen::ArrayXd &sr, const int p) {
    sr = r.abs();
    std::sort(sr.data(), sr.data() + sr.size());
    const size_t index = (sr.size() + p) / 2;
    return sr[index] / 0.6745;
}

Eigen::VectorXd LeastSquares(const Eigen::MatrixXd &X, const Eigen::VectorXd &y) {
    // Solve Xb = Y via least squares via QR decomposition
    Eigen::ColPivHouseholderQR<Eigen::MatrixXd> QR(X);
    Eigen::VectorXd b = QR.solve(y);
    return b;
}

Eigen::VectorXd RobustLeastSquares(const Eigen::MatrixXd &X, const Eigen::VectorXd &y) {
    // With thanks to gsl_multifit_robust & Matlab
    const double sig_y = standard_dev(y);
    const double sig_lower = (sig_y == 0) ? 1.0 : 1e-6 * sig_y;

    // Solve Xb = Y via least squares via QR decomposition, keep the decomposition around
    Eigen::ColPivHouseholderQR<Eigen::MatrixXd> QR(X.rows(), X.cols());
    QR.compute(X);
    Eigen::VectorXd b = QR.solve(y);
    Eigen::ArrayXd corr_fac;
    {   // Calculate leverage and correction factor from the 'thinQ' matrix in here to de-alloc memory when done
        Eigen::MatrixXd Q(X.rows(), X.cols()); Q.setIdentity();
        Q = QR.householderQ() * Q;
        // The below expression with Q is equal to (Q * Q.transpose()).diagonal() = h
        corr_fac = (1.0 - Q.array().square().rowwise().sum()).sqrt();
    }

    // Allocate some workspace for loop
    Eigen::ArrayXd r(y.rows()), sr(y.rows()), w(y.rows());
    Eigen::VectorXd b_prev(b.rows());
    Eigen::MatrixXd wX(X.rows(), X.cols());

    const double tune = 1.345; // For Huber only
    int iter = 0;
    bool converged = false;
    while (!converged && (++iter < 20)) {
        r = (y - X*b); // Calculate residuals
        const double sig = mad_sigma(r, sr, X.cols()); // Get Median Absolute Deviation
        r /= (tune * std::max(sig, sig_lower) * corr_fac); // Adjust residuals
        w = 1 / r.abs().max(1); // Huber weights
        b_prev = b; // Save co-efficients
        wX = w.matrix().asDiagonal() * X;
        QR.compute(wX);
        w *= y.array(); // Re-use w array for weighted-y
        b = QR.solve(w.matrix()); // Weighted solve
        if (((b - b_prev).array().abs() < sqrt(std::numeric_limits<double>::epsilon())).all()) {
            converged = true;
        }
    }

    return b;
}

} // End namespace QI<|endoftext|>