<commit_before>/*****************************************************************************
   Copyright 2004 Steve M�nard

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

       http://www.apache.org/licenses/LICENSE-2.0

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

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

#include <jpype_python.h>
PyObject* JPypeModule::startup(PyObject* obj, PyObject* args)
{
	TRACE_IN("startup");
	try {
		PyObject* vmOpt;
		PyObject* vmPath;
		char ignoreUnrecognized = true;

		JPyArg::parseTuple(args, "OO!b|", &vmPath, &PyTuple_Type, &vmOpt, &ignoreUnrecognized);

		if (! (JPyString::check(vmPath)))
		{
			RAISE(JPypeException, "First paramter must be a string or unicode");
		}

		string cVmPath = JPyString::asString(vmPath);

		StringVector args;

		for (int i = 0; i < JPyObject::length(vmOpt); i++)
		{
			PyObject* obj = JPySequence::getItem(vmOpt, i);

			if (JPyString::check(obj))
			{
				// TODO support unicode
				string v = JPyString::asString(obj);

				args.push_back(v);
			}
			else if (JPySequence::check(obj))
			{
				//String name = arg[0];
				//Callable value = arg[1];

				// TODO complete this for the hooks ....
			}
			else {
				RAISE(JPypeException, "VM Arguments must be string or tuple");
			}
		}

		JPEnv::loadJVM(cVmPath, ignoreUnrecognized, args);

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH

	return NULL;
	TRACE_OUT;
}

PyObject* JPypeModule::attach(PyObject* obj, PyObject* args)
{
	TRACE_IN("attach");
	try {
		PyObject* vmPath;

		JPyArg::parseTuple(args, "O", &vmPath);

		if (! (JPyString::check(vmPath)))
		{
			RAISE(JPypeException, "First paramter must be a string or unicode");
		}

		string cVmPath = JPyString::asString(vmPath);
		JPEnv::attachJVM(cVmPath);

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH

	return NULL;
	TRACE_OUT;
}

PyObject* JPypeModule::dumpJVMStats(PyObject* obj)
{
 	cerr << "JVM activity report     :" << endl;
	//cerr << "\tmethod calls         : " << methodCalls << endl;
	//cerr << "\tstatic method calls  : " << staticMethodCalls << endl;
	//cerr << "\tconstructor calls    : " << constructorCalls << endl;
	//cerr << "\tproxy callbacks      : " << JProxy::getCallbackCount() << endl;
	//cerr << "\tfield gets           : " << fieldGets << endl;
	//cerr << "\tfield sets           : " << fieldSets << endl;
	cerr << "\tclasses loaded       : " << JPTypeManager::getLoadedClasses() << endl;

	Py_INCREF(Py_None);
	return Py_None;
}

PyObject* JPypeModule::shutdown(PyObject* obj)
{
	TRACE_IN("shutdown");
	try {
		dumpJVMStats(obj);

		JPEnv::getJava()->checkInitialized();

		JPTypeManager::shutdown();

		if (JPEnv::getJava()->DestroyJavaVM() )
		{
			RAISE(JPypeException, "Unable to destroy JVM");
		}

		JPEnv::getJava()->shutdown();
		cerr << "JVM has been shutdown" << endl;

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
	TRACE_OUT;
}

PyObject* JPypeModule::synchronized(PyObject* obj, PyObject* args)
{
	JPCleaner cleaner;
	TRACE_IN("synchronized");
	try {
		PyObject* o;

		JPyArg::parseTuple(args, "O!", &PyCapsule_Type, &o);
		string desc = (char*)JPyCObject::getDesc(o);

		jobject obj;
		if (desc == "JPObject")
		{
			JPObject* jpo = (JPObject*)JPyCObject::asVoidPtr(o);
			obj = jpo->getObject();
			cleaner.addLocal(obj);
		}
		else if (desc == "JPClass")
		{
			JPClass* jpo = (JPClass*)JPyCObject::asVoidPtr(o);
			obj = jpo->getClass();
			cleaner.addLocal(obj);
		}
		else if (desc == "JPArray")
		{
			JPArray* jpo = (JPArray*)JPyCObject::asVoidPtr(o);
			obj = jpo->getObject();
			cleaner.addLocal(obj);
		}
		else if (desc == "JPArrayClass")
		{
			JPArrayClass* jpo = (JPArrayClass*)JPyCObject::asVoidPtr(o);
			obj = jpo->getClass();
			cleaner.addLocal(obj);
		}
		else if (hostEnv->isWrapper(o) && hostEnv->getWrapperTypeName(o).isObjectType())
		{
			obj = hostEnv->getWrapperValue(o).l;
			cleaner.addLocal(obj);
		}
		// TODO proxy
		else
		{
			RAISE(JPypeException, "method only accepts object values.");
		}

		PyJPMonitor* c = PyJPMonitor::alloc(new JPMonitor(obj));

		return (PyObject*)c;
	}
	PY_STANDARD_CATCH;

	PyErr_Clear();

	Py_INCREF(Py_None);
	return Py_None;

	TRACE_OUT;
}

PyObject* JPypeModule::isStarted(PyObject* obj)
{
	if (JPEnv::isInitialized())
	{
		return JPyBoolean::getTrue();
	}
	return JPyBoolean::getFalse();
}

PyObject* JPypeModule::attachThread(PyObject* obj)
{
	try {
		JPEnv::attachCurrentThread();
		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::detachThread(PyObject* obj)
{
	try {
		JPEnv::getJava()->DetachCurrentThread();
		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::isThreadAttached(PyObject* obj)
{
	try {
		if (JPEnv::isThreadAttached())
	{
		return JPyBoolean::getTrue();
	}
	return JPyBoolean::getFalse();
	}
	PY_STANDARD_CATCH;

	return NULL;

}

PyObject* JPypeModule::raiseJava(PyObject* , PyObject* args)
{
	try
	{
		//PyObject* arg;
		//JPyArg::parseTuple(args, "O", &arg);
		//JPObject* obj;
		//JPCleaner cleaner;
		//
		//if (JPyCObject::check(arg) && string((char*)JPyCObject::getDesc(arg)) == "JPObject")
		//{
		//	obj = (JPObject*)JPyCObject::asVoidPtr(arg);
		//}
		//else
		//{
		//	JPyErr::setString(PyExc_TypeError, "You can only throw a subclass of java.lang.Throwable");
		//	return NULL;
		//}
		//
		//// check if claz is an instance of Throwable
		//JPClass* claz = obj->getClass();
		//jclass jc = claz->getClass();
		//cleaner.add(jc);
		//if (! JPJni::isThrowable(jc))
		//{
		//	JPyErr::setString(PyExc_TypeError, "You can only throw a subclass of java.lang.Throwable");
		//	return NULL;
		//}
		//
		//jobject jobj = obj->getObject();
		//cleaner.add(jobj);
		//JPEnv::getJava()->Throw((jthrowable)jobj);

		//PyJavaException::errorOccurred();
	}
	PY_STANDARD_CATCH;
	return NULL;
}

PyObject* JPypeModule::attachThreadAsDaemon(PyObject* obj)
{
	try {
		JPEnv::attachCurrentThreadAsDaemon();

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::startReferenceQueue(PyObject* obj, PyObject* args)
{
	try {
		int i;
		JPyArg::parseTuple(args, "i", &i);

		JPJni::startJPypeReferenceQueue(i == 1);

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::stopReferenceQueue(PyObject* obj)
{
	try {
		JPJni::stopJPypeReferenceQueue();

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::setConvertStringObjects(PyObject* obj, PyObject* args)
{
	try {
		PyObject* flag;
		JPyArg::parseTuple(args, "O", &flag);

		if (JPyBoolean::isTrue(flag))
		{
			JPEnv::getJava()->setConvertStringObjects(true);
		}
		else
		{
			JPEnv::getJava()->setConvertStringObjects(false);
		}

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}
<commit_msg>[jvm-shutdown] disable jvm activity report<commit_after>/*****************************************************************************
   Copyright 2004 Steve M�nard

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

       http://www.apache.org/licenses/LICENSE-2.0

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

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

#include <jpype_python.h>
PyObject* JPypeModule::startup(PyObject* obj, PyObject* args)
{
	TRACE_IN("startup");
	try {
		PyObject* vmOpt;
		PyObject* vmPath;
		char ignoreUnrecognized = true;

		JPyArg::parseTuple(args, "OO!b|", &vmPath, &PyTuple_Type, &vmOpt, &ignoreUnrecognized);

		if (! (JPyString::check(vmPath)))
		{
			RAISE(JPypeException, "First paramter must be a string or unicode");
		}

		string cVmPath = JPyString::asString(vmPath);

		StringVector args;

		for (int i = 0; i < JPyObject::length(vmOpt); i++)
		{
			PyObject* obj = JPySequence::getItem(vmOpt, i);

			if (JPyString::check(obj))
			{
				// TODO support unicode
				string v = JPyString::asString(obj);

				args.push_back(v);
			}
			else if (JPySequence::check(obj))
			{
				//String name = arg[0];
				//Callable value = arg[1];

				// TODO complete this for the hooks ....
			}
			else {
				RAISE(JPypeException, "VM Arguments must be string or tuple");
			}
		}

		JPEnv::loadJVM(cVmPath, ignoreUnrecognized, args);

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH

	return NULL;
	TRACE_OUT;
}

PyObject* JPypeModule::attach(PyObject* obj, PyObject* args)
{
	TRACE_IN("attach");
	try {
		PyObject* vmPath;

		JPyArg::parseTuple(args, "O", &vmPath);

		if (! (JPyString::check(vmPath)))
		{
			RAISE(JPypeException, "First paramter must be a string or unicode");
		}

		string cVmPath = JPyString::asString(vmPath);
		JPEnv::attachJVM(cVmPath);

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH

	return NULL;
	TRACE_OUT;
}

PyObject* JPypeModule::dumpJVMStats(PyObject* obj)
{
 	cerr << "JVM activity report     :" << endl;
	//cerr << "\tmethod calls         : " << methodCalls << endl;
	//cerr << "\tstatic method calls  : " << staticMethodCalls << endl;
	//cerr << "\tconstructor calls    : " << constructorCalls << endl;
	//cerr << "\tproxy callbacks      : " << JProxy::getCallbackCount() << endl;
	//cerr << "\tfield gets           : " << fieldGets << endl;
	//cerr << "\tfield sets           : " << fieldSets << endl;
	cerr << "\tclasses loaded       : " << JPTypeManager::getLoadedClasses() << endl;

	Py_INCREF(Py_None);
	return Py_None;
}

PyObject* JPypeModule::shutdown(PyObject* obj)
{
	TRACE_IN("shutdown");
	try {
		//dumpJVMStats(obj);

		JPEnv::getJava()->checkInitialized();

		JPTypeManager::shutdown();

		if (JPEnv::getJava()->DestroyJavaVM() )
		{
			RAISE(JPypeException, "Unable to destroy JVM");
		}

		JPEnv::getJava()->shutdown();
		cerr << "JVM has been shutdown" << endl;

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
	TRACE_OUT;
}

PyObject* JPypeModule::synchronized(PyObject* obj, PyObject* args)
{
	JPCleaner cleaner;
	TRACE_IN("synchronized");
	try {
		PyObject* o;

		JPyArg::parseTuple(args, "O!", &PyCapsule_Type, &o);
		string desc = (char*)JPyCObject::getDesc(o);

		jobject obj;
		if (desc == "JPObject")
		{
			JPObject* jpo = (JPObject*)JPyCObject::asVoidPtr(o);
			obj = jpo->getObject();
			cleaner.addLocal(obj);
		}
		else if (desc == "JPClass")
		{
			JPClass* jpo = (JPClass*)JPyCObject::asVoidPtr(o);
			obj = jpo->getClass();
			cleaner.addLocal(obj);
		}
		else if (desc == "JPArray")
		{
			JPArray* jpo = (JPArray*)JPyCObject::asVoidPtr(o);
			obj = jpo->getObject();
			cleaner.addLocal(obj);
		}
		else if (desc == "JPArrayClass")
		{
			JPArrayClass* jpo = (JPArrayClass*)JPyCObject::asVoidPtr(o);
			obj = jpo->getClass();
			cleaner.addLocal(obj);
		}
		else if (hostEnv->isWrapper(o) && hostEnv->getWrapperTypeName(o).isObjectType())
		{
			obj = hostEnv->getWrapperValue(o).l;
			cleaner.addLocal(obj);
		}
		// TODO proxy
		else
		{
			RAISE(JPypeException, "method only accepts object values.");
		}

		PyJPMonitor* c = PyJPMonitor::alloc(new JPMonitor(obj));

		return (PyObject*)c;
	}
	PY_STANDARD_CATCH;

	PyErr_Clear();

	Py_INCREF(Py_None);
	return Py_None;

	TRACE_OUT;
}

PyObject* JPypeModule::isStarted(PyObject* obj)
{
	if (JPEnv::isInitialized())
	{
		return JPyBoolean::getTrue();
	}
	return JPyBoolean::getFalse();
}

PyObject* JPypeModule::attachThread(PyObject* obj)
{
	try {
		JPEnv::attachCurrentThread();
		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::detachThread(PyObject* obj)
{
	try {
		JPEnv::getJava()->DetachCurrentThread();
		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::isThreadAttached(PyObject* obj)
{
	try {
		if (JPEnv::isThreadAttached())
	{
		return JPyBoolean::getTrue();
	}
	return JPyBoolean::getFalse();
	}
	PY_STANDARD_CATCH;

	return NULL;

}

PyObject* JPypeModule::raiseJava(PyObject* , PyObject* args)
{
	try
	{
		//PyObject* arg;
		//JPyArg::parseTuple(args, "O", &arg);
		//JPObject* obj;
		//JPCleaner cleaner;
		//
		//if (JPyCObject::check(arg) && string((char*)JPyCObject::getDesc(arg)) == "JPObject")
		//{
		//	obj = (JPObject*)JPyCObject::asVoidPtr(arg);
		//}
		//else
		//{
		//	JPyErr::setString(PyExc_TypeError, "You can only throw a subclass of java.lang.Throwable");
		//	return NULL;
		//}
		//
		//// check if claz is an instance of Throwable
		//JPClass* claz = obj->getClass();
		//jclass jc = claz->getClass();
		//cleaner.add(jc);
		//if (! JPJni::isThrowable(jc))
		//{
		//	JPyErr::setString(PyExc_TypeError, "You can only throw a subclass of java.lang.Throwable");
		//	return NULL;
		//}
		//
		//jobject jobj = obj->getObject();
		//cleaner.add(jobj);
		//JPEnv::getJava()->Throw((jthrowable)jobj);

		//PyJavaException::errorOccurred();
	}
	PY_STANDARD_CATCH;
	return NULL;
}

PyObject* JPypeModule::attachThreadAsDaemon(PyObject* obj)
{
	try {
		JPEnv::attachCurrentThreadAsDaemon();

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::startReferenceQueue(PyObject* obj, PyObject* args)
{
	try {
		int i;
		JPyArg::parseTuple(args, "i", &i);

		JPJni::startJPypeReferenceQueue(i == 1);

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::stopReferenceQueue(PyObject* obj)
{
	try {
		JPJni::stopJPypeReferenceQueue();

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}

PyObject* JPypeModule::setConvertStringObjects(PyObject* obj, PyObject* args)
{
	try {
		PyObject* flag;
		JPyArg::parseTuple(args, "O", &flag);

		if (JPyBoolean::isTrue(flag))
		{
			JPEnv::getJava()->setConvertStringObjects(true);
		}
		else
		{
			JPEnv::getJava()->setConvertStringObjects(false);
		}

		Py_INCREF(Py_None);
		return Py_None;
	}
	PY_STANDARD_CATCH;

	return NULL;
}
<|endoftext|>


<commit_before>/****************************************************************************
**
** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/
**
** This file is part of the QtQml module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** GNU Lesser General Public License Usage
** This file may be used under the terms of the GNU Lesser General Public
** License version 2.1 as published by the Free Software Foundation and
** appearing in the file LICENSE.LGPL included in the packaging of this
** file. Please review the following information to ensure the GNU Lesser
** General Public License version 2.1 requirements will be met:
** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU General
** Public License version 3.0 as published by the Free Software Foundation
** and appearing in the file LICENSE.GPL included in the packaging of this
** file. Please review the following information to ensure the GNU General
** Public License version 3.0 requirements will be met:
** http://www.gnu.org/copyleft/gpl.html.
**
** Other Usage
** Alternatively, this file may be used in accordance with the terms and
** conditions contained in a signed written agreement between you and Nokia.
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/

#include "highlight.h"

#include <QtGui/QPainter>

namespace QmlJSDebugger {
namespace QtQuick2 {

Highlight::Highlight(QQuickItem *item, QQuickItem *parent)
    : QQuickPaintedItem(parent)
{
    setItem(item);
}

void Highlight::setItem(QQuickItem *item)
{
    if (m_item)
        m_item.data()->disconnect(this);

    if (item) {
        connect(item, SIGNAL(xChanged()), SLOT(adjust()));
        connect(item, SIGNAL(yChanged()), SLOT(adjust()));
        connect(item, SIGNAL(widthChanged()), SLOT(adjust()));
        connect(item, SIGNAL(heightChanged()), SLOT(adjust()));
        connect(item, SIGNAL(rotationChanged()), SLOT(adjust()));
        connect(item, SIGNAL(transformOriginChanged(TransformOrigin)),
                SLOT(adjust()));
    }

    m_item = item;
    adjust();
}

void Highlight::adjust()
{
    const QQuickItem *item = m_item.data();
    setSize(QSizeF(item->width(), item->height()));
    setPos(parentItem()->mapFromItem(item->parentItem(), item->pos()));
    setRotation(item->rotation());
    setTransformOrigin(item->transformOrigin());
}

void HoverHighlight::paint(QPainter *painter)
{
    painter->setPen(QColor(108, 141, 221));
    painter->drawRect(QRect(0, 0, width() - 1, height() - 1));
}

void SelectionHighlight::paint(QPainter *painter)
{
    painter->setPen(QPen(QColor(0, 22, 159)));
    painter->drawRect(QRect(1, 1, width() - 3, height() - 3));
    painter->setPen(QColor(158, 199, 255));
    painter->drawRect(QRect(0, 0, width() - 1, height() - 1));
}

} // namespace QtQuick2
} // namespace QmlJSDebugger
<commit_msg>Debugger: Inspect tool - changes made to highlight on selection<commit_after>/****************************************************************************
**
** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/
**
** This file is part of the QtQml module of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** GNU Lesser General Public License Usage
** This file may be used under the terms of the GNU Lesser General Public
** License version 2.1 as published by the Free Software Foundation and
** appearing in the file LICENSE.LGPL included in the packaging of this
** file. Please review the following information to ensure the GNU Lesser
** General Public License version 2.1 requirements will be met:
** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU General
** Public License version 3.0 as published by the Free Software Foundation
** and appearing in the file LICENSE.GPL included in the packaging of this
** file. Please review the following information to ensure the GNU General
** Public License version 3.0 requirements will be met:
** http://www.gnu.org/copyleft/gpl.html.
**
** Other Usage
** Alternatively, this file may be used in accordance with the terms and
** conditions contained in a signed written agreement between you and Nokia.
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/

#include "highlight.h"

#include <QtGui/QPainter>

namespace QmlJSDebugger {
namespace QtQuick2 {

Highlight::Highlight(QQuickItem *item, QQuickItem *parent)
    : QQuickPaintedItem(parent)
{
    setItem(item);
}

void Highlight::setItem(QQuickItem *item)
{
    if (m_item)
        m_item.data()->disconnect(this);

    if (item) {
        connect(item, SIGNAL(xChanged()), SLOT(adjust()));
        connect(item, SIGNAL(yChanged()), SLOT(adjust()));
        connect(item, SIGNAL(widthChanged()), SLOT(adjust()));
        connect(item, SIGNAL(heightChanged()), SLOT(adjust()));
        connect(item, SIGNAL(rotationChanged()), SLOT(adjust()));
        connect(item, SIGNAL(transformOriginChanged(TransformOrigin)),
                SLOT(adjust()));
    }

    m_item = item;
    adjust();
}

void Highlight::adjust()
{
    const QQuickItem *item = m_item.data();
    setSize(QSizeF(item->width(), item->height()));
    setPos(parentItem()->mapFromItem(item->parentItem(), item->pos()));
    setRotation(item->rotation());
    setTransformOrigin(item->transformOrigin());
}

void HoverHighlight::paint(QPainter *painter)
{
    painter->setPen(QColor(108, 141, 221));
    painter->drawRect(QRect(0, 0, width() - 1, height() - 1));
}

void SelectionHighlight::paint(QPainter *painter)
{
    if (height() >= 10 && width() >= 10) {
        QColor colorHighlight = Qt::green;

        painter->fillRect(QRectF(0, 0, width(), 5), colorHighlight);
        painter->fillRect(QRectF(0, height()-5, width(), 5), colorHighlight);
        painter->fillRect(QRectF(0, 5, 5, height() - 10), colorHighlight);
        painter->fillRect(QRectF(width()-5, 5, 5, height() - 10), colorHighlight);
    }
    painter->setPen(QPen(QColor(0, 22, 159)));
    painter->drawRect(QRect(1, 1, width() - 3, height() - 3));
    painter->setPen(QColor(158, 199, 255));
    painter->drawRect(QRect(0, 0, width() - 1, height() - 1));
}

} // namespace QtQuick2
} // namespace QmlJSDebugger
<|endoftext|>


<commit_before>//==============================================================================
// Heun solver class
//==============================================================================

#include "heunsolver.h"

//==============================================================================

namespace OpenCOR {
namespace HeunSolver {

//==============================================================================

HeunSolver::HeunSolver() :
    mStep(DefaultStep),
    mK(0),
    mYk(0)
{
}

//==============================================================================

HeunSolver::~HeunSolver()
{
    // Delete some internal objects

    delete[] mK;
    delete[] mYk;
}

//==============================================================================

void HeunSolver::initialize(const double &pVoiStart, const int &pStatesCount,
                            double *pConstants, double *pStates, double *pRates,
                            double *pAlgebraic,
                            ComputeRatesFunction pComputeRates)
{
    // Initialise the ODE solver itself

    OpenCOR::CoreSolver::CoreOdeSolver::initialize(pVoiStart, pStatesCount,
                                                   pConstants, pStates, pRates,
                                                   pAlgebraic, pComputeRates);

    // Retrieve the solver's properties

    if (mProperties.contains(StepProperty)) {
        mStep = mProperties.value(StepProperty).toDouble();

        if (!mStep)
            emit error(QObject::tr("the 'step' property value cannot be equal to zero"));
    } else {
        emit error(QObject::tr("the 'step' property value could not be retrieved"));
    }

    // (Re-)create our various arrays

    delete[] mK;
    delete[] mYk;

    mK  = new double[pStatesCount];
    mYk = new double[pStatesCount];
}

//==============================================================================

void HeunSolver::solve(double &pVoi, const double &pVoiEnd) const
{
    // k = h * f(t_n, Y_n)
    // Y_n+1 = Y_n + h / 2 * (f(t_n, Y_n) + f(t_n + h, Y_n + k))

    double voiStart = pVoi;

    int stepNumber = 0;
    double realStep = mStep;
    double realHalfStep = 0.5*realStep;

    while (pVoi != pVoiEnd) {
        // Check that the time step is correct

        if (pVoi+realStep > pVoiEnd) {
            realStep = pVoiEnd-pVoi;
            realHalfStep = 0.5*realStep;
        }

        // Compute f(t_n, Y_n)

        mComputeRates(pVoi, mConstants, mRates, mStates, mAlgebraic);

        // Compute k and Yk

        for (int i = 0; i < mStatesCount; ++i) {
            mK[i]  = mRates[i];
            mYk[i] = mStates[i]+realStep*mK[i];
        }

        // Compute f(t_n + h, Y_n + k)

        mComputeRates(pVoi+realStep, mConstants, mRates, mYk, mAlgebraic);

        // Compute Y_n+1

        for (int i = 0; i < mStatesCount; ++i)
            mStates[i] += realHalfStep*(mK[i]+mRates[i]);

        // Advance through time

        if (realStep != mStep)
            pVoi = pVoiEnd;
        else
            pVoi = voiStart+(++stepNumber)*mStep;
    }
}

//==============================================================================

}   // namespace HeunSolver
}   // namespace OpenCOR

//==============================================================================
// End of file
//==============================================================================
<commit_msg>Some minor cleaning up.<commit_after>//==============================================================================
// Heun solver class
//==============================================================================

#include "heunsolver.h"

//==============================================================================

namespace OpenCOR {
namespace HeunSolver {

//==============================================================================

HeunSolver::HeunSolver() :
    mStep(DefaultStep),
    mK(0),
    mYk(0)
{
}

//==============================================================================

HeunSolver::~HeunSolver()
{
    // Delete some internal objects

    delete[] mK;
    delete[] mYk;
}

//==============================================================================

void HeunSolver::initialize(const double &pVoiStart, const int &pStatesCount,
                            double *pConstants, double *pStates, double *pRates,
                            double *pAlgebraic,
                            ComputeRatesFunction pComputeRates)
{
    // Initialise the ODE solver itself

    OpenCOR::CoreSolver::CoreOdeSolver::initialize(pVoiStart, pStatesCount,
                                                   pConstants, pStates, pRates,
                                                   pAlgebraic, pComputeRates);

    // Retrieve the solver's properties

    if (mProperties.contains(StepProperty)) {
        mStep = mProperties.value(StepProperty).toDouble();

        if (!mStep)
            emit error(QObject::tr("the 'step' property value cannot be equal to zero"));
    } else {
        emit error(QObject::tr("the 'step' property value could not be retrieved"));
    }

    // (Re-)create our various arrays

    delete[] mK;
    delete[] mYk;

    mK  = new double[pStatesCount];
    mYk = new double[pStatesCount];
}

//==============================================================================

void HeunSolver::solve(double &pVoi, const double &pVoiEnd) const
{
    // k = h * f(t_n, Y_n)
    // Y_n+1 = Y_n + h / 2 * ( f(t_n, Y_n) + f(t_n + h, Y_n + k) )

    double voiStart = pVoi;

    int stepNumber = 0;
    double realStep = mStep;
    double realHalfStep = 0.5*realStep;

    while (pVoi != pVoiEnd) {
        // Check that the time step is correct

        if (pVoi+realStep > pVoiEnd) {
            realStep = pVoiEnd-pVoi;
            realHalfStep = 0.5*realStep;
        }

        // Compute f(t_n, Y_n)

        mComputeRates(pVoi, mConstants, mRates, mStates, mAlgebraic);

        // Compute k and Yk

        for (int i = 0; i < mStatesCount; ++i) {
            mK[i]  = mRates[i];
            mYk[i] = mStates[i]+realStep*mK[i];
        }

        // Compute f(t_n + h, Y_n + k)

        mComputeRates(pVoi+realStep, mConstants, mRates, mYk, mAlgebraic);

        // Compute Y_n+1

        for (int i = 0; i < mStatesCount; ++i)
            mStates[i] += realHalfStep*(mK[i]+mRates[i]);

        // Advance through time

        if (realStep != mStep)
            pVoi = pVoiEnd;
        else
            pVoi = voiStart+(++stepNumber)*mStep;
    }
}

//==============================================================================

}   // namespace HeunSolver
}   // namespace OpenCOR

//==============================================================================
// End of file
//==============================================================================
<|endoftext|>


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

#include "net/base/ssl_config_service.h"

#if defined(OS_WIN)
#include "net/base/ssl_config_service_win.h"
#elif defined(OS_MACOSX)
#include "net/base/ssl_config_service_mac.h"
#else
#include "net/base/ssl_config_service_defaults.h"
#endif

namespace net {

// static
SSLConfigService* SSLConfigService::CreateSystemSSLConfigService() {
#if defined(OS_WIN)
  return new SSLConfigServiceWin;
#elif defined(OS_MACOSX)
  return new SSLConfigServiceMac;
#else
  return new SSLConfigServiceDefaults;
#endif
}

// static
bool SSLConfigService::IsKnownStrictTLSServer(const std::string& hostname) {
  // If you wish to add an entry to this list, please contact agl AT chromium
  // DOT org.
  //
  // If this list starts growing, it'll need to be something more efficient
  // than a linear list.
  static const char kStrictServers[][20] = {
      "www.google.com",
      "mail.google.com",
      "www.gmail.com",
      "docs.google.com",
      "clients1.google.com",

      // Removed until we update the XMPP servers with the renegotiation
      // extension.
      // "gmail.com",
  };

  for (size_t i = 0; i < arraysize(kStrictServers); i++) {
    if (strcmp(hostname.c_str(), kStrictServers[i]) == 0)
      return true;
  }

  return false;
}

}  // namespace net
<commit_msg>Add sunshinepress.org to the list of renegotiation extension required hosts.<commit_after>// Copyright (c) 2009 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "net/base/ssl_config_service.h"

#if defined(OS_WIN)
#include "net/base/ssl_config_service_win.h"
#elif defined(OS_MACOSX)
#include "net/base/ssl_config_service_mac.h"
#else
#include "net/base/ssl_config_service_defaults.h"
#endif

namespace net {

// static
SSLConfigService* SSLConfigService::CreateSystemSSLConfigService() {
#if defined(OS_WIN)
  return new SSLConfigServiceWin;
#elif defined(OS_MACOSX)
  return new SSLConfigServiceMac;
#else
  return new SSLConfigServiceDefaults;
#endif
}

// static
bool SSLConfigService::IsKnownStrictTLSServer(const std::string& hostname) {
  // If you wish to add an entry to this list, please contact agl AT chromium
  // DOT org.
  //
  // If this list starts growing, it'll need to be something more efficient
  // than a linear list.
  static const char kStrictServers[][22] = {
      "www.google.com",
      "mail.google.com",
      "www.gmail.com",
      "docs.google.com",
      "clients1.google.com",
      "sunshinepress.org",
      "www.sunshinepress.org",

      // Removed until we update the XMPP servers with the renegotiation
      // extension.
      // "gmail.com",
  };

  for (size_t i = 0; i < arraysize(kStrictServers); i++) {
    // Note that the hostname is normalised to lower-case by this point.
    if (strcmp(hostname.c_str(), kStrictServers[i]) == 0)
      return true;
  }

  return false;
}

}  // namespace net
<|endoftext|>


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

#include "net/http/http_network_layer.h"

#include "base/field_trial.h"
#include "base/logging.h"
#include "base/string_util.h"
#include "net/http/http_network_session.h"
#include "net/http/http_network_transaction.h"
#include "net/socket/client_socket_factory.h"
#include "net/spdy/spdy_framer.h"
#include "net/spdy/spdy_network_transaction.h"
#include "net/spdy/spdy_session.h"
#include "net/spdy/spdy_session_pool.h"

namespace net {

//-----------------------------------------------------------------------------

// static
HttpTransactionFactory* HttpNetworkLayer::CreateFactory(
    HostResolver* host_resolver,
    ProxyService* proxy_service,
    SSLConfigService* ssl_config_service,
    HttpAuthHandlerFactory* http_auth_handler_factory,
    HttpNetworkDelegate* network_delegate,
    NetLog* net_log) {
  DCHECK(proxy_service);

  return new HttpNetworkLayer(ClientSocketFactory::GetDefaultFactory(),
                              host_resolver, proxy_service, ssl_config_service,
                              http_auth_handler_factory,
                              network_delegate,
                              net_log);
}

// static
HttpTransactionFactory* HttpNetworkLayer::CreateFactory(
    HttpNetworkSession* session) {
  DCHECK(session);

  return new HttpNetworkLayer(session);
}

//-----------------------------------------------------------------------------
HttpNetworkLayer::HttpNetworkLayer(
    ClientSocketFactory* socket_factory,
    HostResolver* host_resolver,
    ProxyService* proxy_service,
    SSLConfigService* ssl_config_service,
    HttpAuthHandlerFactory* http_auth_handler_factory,
    HttpNetworkDelegate* network_delegate,
    NetLog* net_log)
    : socket_factory_(socket_factory),
      host_resolver_(host_resolver),
      proxy_service_(proxy_service),
      ssl_config_service_(ssl_config_service),
      session_(NULL),
      spdy_session_pool_(NULL),
      http_auth_handler_factory_(http_auth_handler_factory),
      network_delegate_(network_delegate),
      net_log_(net_log),
      suspended_(false) {
  DCHECK(proxy_service_);
  DCHECK(ssl_config_service_.get());
}

HttpNetworkLayer::HttpNetworkLayer(HttpNetworkSession* session)
    : socket_factory_(ClientSocketFactory::GetDefaultFactory()),
      ssl_config_service_(NULL),
      session_(session),
      spdy_session_pool_(session->spdy_session_pool()),
      http_auth_handler_factory_(NULL),
      network_delegate_(NULL),
      net_log_(NULL),
      suspended_(false) {
  DCHECK(session_.get());
}

HttpNetworkLayer::~HttpNetworkLayer() {
}

int HttpNetworkLayer::CreateTransaction(scoped_ptr<HttpTransaction>* trans) {
  if (suspended_)
    return ERR_NETWORK_IO_SUSPENDED;

  trans->reset(new HttpNetworkTransaction(GetSession()));
  return OK;
}

HttpCache* HttpNetworkLayer::GetCache() {
  return NULL;
}

void HttpNetworkLayer::Suspend(bool suspend) {
  suspended_ = suspend;

  if (suspend && session_)
    session_->tcp_socket_pool()->CloseIdleSockets();
}

HttpNetworkSession* HttpNetworkLayer::GetSession() {
  if (!session_) {
    DCHECK(proxy_service_);
    SpdySessionPool* spdy_pool = new SpdySessionPool();
    session_ = new HttpNetworkSession(host_resolver_, proxy_service_,
        socket_factory_, ssl_config_service_, spdy_pool,
        http_auth_handler_factory_, network_delegate_, net_log_);
    // These were just temps for lazy-initializing HttpNetworkSession.
    host_resolver_ = NULL;
    proxy_service_ = NULL;
    socket_factory_ = NULL;
    http_auth_handler_factory_ = NULL;
    net_log_ = NULL;
    network_delegate_ = NULL;
  }
  return session_;
}

// static
void HttpNetworkLayer::EnableSpdy(const std::string& mode) {
  static const char kSSL[] = "ssl";
  static const char kDisableSSL[] = "no-ssl";
  static const char kDisableCompression[] = "no-compress";
  static const char kDisableAltProtocols[] = "no-alt-protocols";
  static const char kEnableVersionOne[] = "v1";

  // If flow-control is enabled, received WINDOW_UPDATE and SETTINGS
  // messages are processed and outstanding window size is actually obeyed
  // when sending data frames, and WINDOW_UPDATE messages are generated
  // when data is consumed.
  static const char kEnableFlowControl[] = "flow-control";

  // We want an A/B experiment between SPDY enabled and SPDY disabled,
  // but only for pages where SPDY *could have been* negotiated.  To do
  // this, we use NPN, but prevent it from negotiating SPDY.  If the
  // server negotiates HTTP, rather than SPDY, today that will only happen
  // on servers that installed NPN (and could have done SPDY).  But this is
  // a bit of a hack, as this correlation between NPN and SPDY is not
  // really guaranteed.
  static const char kEnableNPN[] = "npn";
  static const char kEnableNpnHttpOnly[] = "npn-http";

  // Except for the first element, the order is irrelevant.  First element
  // specifies the fallback in case nothing matches
  // (SSLClientSocket::kNextProtoNoOverlap).  Otherwise, the SSL library
  // will choose the first overlapping protocol in the server's list, since
  // it presumedly has a better understanding of which protocol we should
  // use, therefore the rest of the ordering here is not important.
  static const char kNpnProtosFull[] = "\x08http/1.1\x06spdy/2";
  // This is a temporary hack to pretend we support version 1.
  static const char kNpnProtosFullV1[] = "\x08http/1.1\x06spdy/1\x06spdy/2";
  // No spdy specified.
  static const char kNpnProtosHttpOnly[] = "\x08http/1.1\x07http1.1";

  std::vector<std::string> spdy_options;
  SplitString(mode, ',', &spdy_options);

  bool use_alt_protocols = true;

  for (std::vector<std::string>::iterator it = spdy_options.begin();
       it != spdy_options.end(); ++it) {
    const std::string& option = *it;
    if (option == kDisableSSL) {
      SpdySession::SetSSLMode(false);  // Disable SSL
      HttpNetworkTransaction::SetUseSSLOverSpdyWithoutNPN(false);
      HttpNetworkTransaction::SetUseSpdyWithoutNPN(true);
    } else if (option == kSSL) {
      HttpNetworkTransaction::SetUseSSLOverSpdyWithoutNPN(true);
      HttpNetworkTransaction::SetUseSpdyWithoutNPN(true);
    } else if (option == kDisableCompression) {
      spdy::SpdyFramer::set_enable_compression_default(false);
    } else if (option == kEnableNPN) {
      HttpNetworkTransaction::SetUseAlternateProtocols(use_alt_protocols);
      HttpNetworkTransaction::SetNextProtos(kNpnProtosFull);
    } else if (option == kEnableNpnHttpOnly) {
      // Avoid alternate protocol in this case. Otherwise, browser will try SSL
      // and then fallback to http. This introduces extra load.
      HttpNetworkTransaction::SetUseAlternateProtocols(false);
      HttpNetworkTransaction::SetNextProtos(kNpnProtosHttpOnly);
    } else if (option == kEnableVersionOne) {
      spdy::SpdyFramer::set_protocol_version(1);
      HttpNetworkTransaction::SetNextProtos(kNpnProtosFullV1);
    } else if (option == kDisableAltProtocols) {
      use_alt_protocols = false;
      HttpNetworkTransaction::SetUseAlternateProtocols(false);
    } else if (option == kEnableFlowControl) {
      SpdySession::SetFlowControl(true);
    } else if (option.empty() && it == spdy_options.begin()) {
      continue;
    } else {
      LOG(DFATAL) << "Unrecognized spdy option: " << option;
    }
  }
}
}  // namespace net
<commit_msg>Modify the SPDY v1 hack to only advertise v1 and not v2 over NPN. There is no point in advertising a protocol that won't work.  (When in v1 mode, the protocol frames will all say v1, which, to a v2 server will likely be broken<commit_after>// Copyright (c) 2010 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "net/http/http_network_layer.h"

#include "base/field_trial.h"
#include "base/logging.h"
#include "base/string_util.h"
#include "net/http/http_network_session.h"
#include "net/http/http_network_transaction.h"
#include "net/socket/client_socket_factory.h"
#include "net/spdy/spdy_framer.h"
#include "net/spdy/spdy_network_transaction.h"
#include "net/spdy/spdy_session.h"
#include "net/spdy/spdy_session_pool.h"

namespace net {

//-----------------------------------------------------------------------------

// static
HttpTransactionFactory* HttpNetworkLayer::CreateFactory(
    HostResolver* host_resolver,
    ProxyService* proxy_service,
    SSLConfigService* ssl_config_service,
    HttpAuthHandlerFactory* http_auth_handler_factory,
    HttpNetworkDelegate* network_delegate,
    NetLog* net_log) {
  DCHECK(proxy_service);

  return new HttpNetworkLayer(ClientSocketFactory::GetDefaultFactory(),
                              host_resolver, proxy_service, ssl_config_service,
                              http_auth_handler_factory,
                              network_delegate,
                              net_log);
}

// static
HttpTransactionFactory* HttpNetworkLayer::CreateFactory(
    HttpNetworkSession* session) {
  DCHECK(session);

  return new HttpNetworkLayer(session);
}

//-----------------------------------------------------------------------------
HttpNetworkLayer::HttpNetworkLayer(
    ClientSocketFactory* socket_factory,
    HostResolver* host_resolver,
    ProxyService* proxy_service,
    SSLConfigService* ssl_config_service,
    HttpAuthHandlerFactory* http_auth_handler_factory,
    HttpNetworkDelegate* network_delegate,
    NetLog* net_log)
    : socket_factory_(socket_factory),
      host_resolver_(host_resolver),
      proxy_service_(proxy_service),
      ssl_config_service_(ssl_config_service),
      session_(NULL),
      spdy_session_pool_(NULL),
      http_auth_handler_factory_(http_auth_handler_factory),
      network_delegate_(network_delegate),
      net_log_(net_log),
      suspended_(false) {
  DCHECK(proxy_service_);
  DCHECK(ssl_config_service_.get());
}

HttpNetworkLayer::HttpNetworkLayer(HttpNetworkSession* session)
    : socket_factory_(ClientSocketFactory::GetDefaultFactory()),
      ssl_config_service_(NULL),
      session_(session),
      spdy_session_pool_(session->spdy_session_pool()),
      http_auth_handler_factory_(NULL),
      network_delegate_(NULL),
      net_log_(NULL),
      suspended_(false) {
  DCHECK(session_.get());
}

HttpNetworkLayer::~HttpNetworkLayer() {
}

int HttpNetworkLayer::CreateTransaction(scoped_ptr<HttpTransaction>* trans) {
  if (suspended_)
    return ERR_NETWORK_IO_SUSPENDED;

  trans->reset(new HttpNetworkTransaction(GetSession()));
  return OK;
}

HttpCache* HttpNetworkLayer::GetCache() {
  return NULL;
}

void HttpNetworkLayer::Suspend(bool suspend) {
  suspended_ = suspend;

  if (suspend && session_)
    session_->tcp_socket_pool()->CloseIdleSockets();
}

HttpNetworkSession* HttpNetworkLayer::GetSession() {
  if (!session_) {
    DCHECK(proxy_service_);
    SpdySessionPool* spdy_pool = new SpdySessionPool();
    session_ = new HttpNetworkSession(host_resolver_, proxy_service_,
        socket_factory_, ssl_config_service_, spdy_pool,
        http_auth_handler_factory_, network_delegate_, net_log_);
    // These were just temps for lazy-initializing HttpNetworkSession.
    host_resolver_ = NULL;
    proxy_service_ = NULL;
    socket_factory_ = NULL;
    http_auth_handler_factory_ = NULL;
    net_log_ = NULL;
    network_delegate_ = NULL;
  }
  return session_;
}

// static
void HttpNetworkLayer::EnableSpdy(const std::string& mode) {
  static const char kSSL[] = "ssl";
  static const char kDisableSSL[] = "no-ssl";
  static const char kDisableCompression[] = "no-compress";
  static const char kDisableAltProtocols[] = "no-alt-protocols";
  static const char kEnableVersionOne[] = "v1";

  // If flow-control is enabled, received WINDOW_UPDATE and SETTINGS
  // messages are processed and outstanding window size is actually obeyed
  // when sending data frames, and WINDOW_UPDATE messages are generated
  // when data is consumed.
  static const char kEnableFlowControl[] = "flow-control";

  // We want an A/B experiment between SPDY enabled and SPDY disabled,
  // but only for pages where SPDY *could have been* negotiated.  To do
  // this, we use NPN, but prevent it from negotiating SPDY.  If the
  // server negotiates HTTP, rather than SPDY, today that will only happen
  // on servers that installed NPN (and could have done SPDY).  But this is
  // a bit of a hack, as this correlation between NPN and SPDY is not
  // really guaranteed.
  static const char kEnableNPN[] = "npn";
  static const char kEnableNpnHttpOnly[] = "npn-http";

  // Except for the first element, the order is irrelevant.  First element
  // specifies the fallback in case nothing matches
  // (SSLClientSocket::kNextProtoNoOverlap).  Otherwise, the SSL library
  // will choose the first overlapping protocol in the server's list, since
  // it presumedly has a better understanding of which protocol we should
  // use, therefore the rest of the ordering here is not important.
  static const char kNpnProtosFull[] = "\x08http/1.1\x06spdy/2";
  // This is a temporary hack to pretend we support version 1.
  static const char kNpnProtosFullV1[] = "\x08http/1.1\x06spdy/1";
  // No spdy specified.
  static const char kNpnProtosHttpOnly[] = "\x08http/1.1\x07http1.1";

  std::vector<std::string> spdy_options;
  SplitString(mode, ',', &spdy_options);

  bool use_alt_protocols = true;

  for (std::vector<std::string>::iterator it = spdy_options.begin();
       it != spdy_options.end(); ++it) {
    const std::string& option = *it;
    if (option == kDisableSSL) {
      SpdySession::SetSSLMode(false);  // Disable SSL
      HttpNetworkTransaction::SetUseSSLOverSpdyWithoutNPN(false);
      HttpNetworkTransaction::SetUseSpdyWithoutNPN(true);
    } else if (option == kSSL) {
      HttpNetworkTransaction::SetUseSSLOverSpdyWithoutNPN(true);
      HttpNetworkTransaction::SetUseSpdyWithoutNPN(true);
    } else if (option == kDisableCompression) {
      spdy::SpdyFramer::set_enable_compression_default(false);
    } else if (option == kEnableNPN) {
      HttpNetworkTransaction::SetUseAlternateProtocols(use_alt_protocols);
      HttpNetworkTransaction::SetNextProtos(kNpnProtosFull);
    } else if (option == kEnableNpnHttpOnly) {
      // Avoid alternate protocol in this case. Otherwise, browser will try SSL
      // and then fallback to http. This introduces extra load.
      HttpNetworkTransaction::SetUseAlternateProtocols(false);
      HttpNetworkTransaction::SetNextProtos(kNpnProtosHttpOnly);
    } else if (option == kEnableVersionOne) {
      spdy::SpdyFramer::set_protocol_version(1);
      HttpNetworkTransaction::SetNextProtos(kNpnProtosFullV1);
    } else if (option == kDisableAltProtocols) {
      use_alt_protocols = false;
      HttpNetworkTransaction::SetUseAlternateProtocols(false);
    } else if (option == kEnableFlowControl) {
      SpdySession::SetFlowControl(true);
    } else if (option.empty() && it == spdy_options.begin()) {
      continue;
    } else {
      LOG(DFATAL) << "Unrecognized spdy option: " << option;
    }
  }
}
}  // namespace net
<|endoftext|>


<commit_before>// Debugging Settings
#define DEBUG
#define DEBUG_V1
#define DEBUG_V2
#define DEBUG_V3
//#define DEBUG_V4

#include <iostream>
#include <iomanip>
#include <memory>
#include <random>
#include <iterator>
#include <functional>
#include <ctime>

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <memory.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <sys/resource.h>
#include <math.h>

#include <bsl_memory.h>
#include <bslma_testallocator.h>
#include <bslma_newdeleteallocator.h>
#include <bsls_stopwatch.h>

#include <bdlma_sequentialpool.h>
#include <bdlma_sequentialallocator.h>
#include <bdlma_bufferedsequentialallocator.h>
#include <bdlma_multipoolallocator.h>

#include <vector>
#include <list>

#include "benchmark_common.h"

// Debugging
#include <typeinfo>
#include <assert.h>

using namespace BloombergLP;

// Global Variables

#ifdef DEBUG
int AF_RF_PRODUCT = 256;
#else
int AF_RF_PRODUCT = 2560;
#endif // DEBUG

template<typename ALLOC>
class AllocSubsystem {
public:
	ALLOC d_alloc;
	std::list<int, alloc_adaptor<int, ALLOC> > d_list;
	AllocSubsystem() : d_alloc(), d_list(&d_alloc) {}
};

class DefaultSubsystem {
public:
	std::list<int> d_list;
	DefaultSubsystem() : d_list() {}
};

// Convenience typedefs
struct subsystems {
	typedef DefaultSubsystem def;
	typedef AllocSubsystem<BloombergLP::bdlma::MultipoolAllocator> multipool;
};

template<typename VECTOR>
double access_lists(VECTOR *vec, int af, int rf) {
#ifdef DEBUG_V3
	std::cout << "Accessing Lists" << std::endl;
#endif // DEBUG_V3

	std::clock_t c_start = std::clock();

	for (size_t r = 0; r < rf; r++)	{
		for (size_t i = 0; i < vec->size(); i++) {
			for (size_t a = 0; a < af; a++) {
				for (auto it = (*vec)[i]->d_list.begin(); it != (*vec)[i]->d_list.end(); ++it) {
					(*it)++; // Increment int to cause loop to have some effect
				}
				clobber(); // TODO will this hurt caching?
			}
		}
	}
	std::clock_t c_end = std::clock();

#ifdef DEBUG_V3
	std::cout << "Finished accessing Lists" << std::endl;
#endif // DEBUG_V3
	return (c_end - c_start) * 1.0 / CLOCKS_PER_SEC;
}

template<typename SUBSYS>
double run_combination(int G, int S, int af, int sf, int rf) {
	// G  = Total system size (# subsystems * elements in subsystems). Given as power of 2 (size really = 2^G)
	// S  = Elements per subsystem. Given as power of 2 (size really = 2^S)
	// af = Access Factor - Number of iterations through a subsystem (linked list) before moving to the next
	// sf = Shuffle Factor - Number of elements popped from each list and pushed to a randomly chosen list
	//						 Note: -ve value means access occurs before shuffle
	// rf = Repeat Factor - Number of times the subsystems are iterated over

	int k = std::abs(G) - std::abs(S);
	size_t expanded_S = 1, expanded_k = 1;
	expanded_S <<= S;
	expanded_k <<= k;

#ifdef DEBUG_V3
	std::cout << "Total number of lists (k) = 2^" << k << " (aka " << expanded_k << ")" << std::endl;
	std::cout << "Total number of elements per sub system (S) = 2^" << S << " (aka " << expanded_S << ")" << std::endl;
#endif // DEBUG_V3

	std::vector<SUBSYS *> vec;

	// Create data under test
	vec.reserve(expanded_k);
	for (size_t i = 0; i < expanded_k; i++)	{
		vec.emplace_back(new SUBSYS()); // Never deallocated because we exit immediately after this function reutrns anyway

		for (size_t j = 0; j < expanded_S; j++)
		{
			vec.back()->d_list.emplace_back((int)j);
		}
	}

#ifdef DEBUG_V3
	std::cout << "Created vector with " << vec.size() << " elements" << std::endl;
#endif // DEBUG_V3

	double result = 0.0;
	if (sf < 0) {
		// Access the data
#ifdef DEBUG_V3
		std::cout << "Accessing data BEFORE shuffling" << std::endl;
#endif // DEBUG_V3
		result = access_lists(&vec, af, rf);
	}

	// Shuffle the data
#ifdef DEBUG_V3
	std::cout << "Shuffling data " << std::abs(sf) << " times" << std::endl;
#endif // DEBUG_V3

	std::default_random_engine generator(1); // Consistent seed to get the same (pseudo) random distribution each time
	std::uniform_int_distribution<size_t> position_distribution(0, vec.size() - 1);
	for (size_t i = 0; i < std::abs(sf); i++) {
		for (size_t j = 0; j < vec.size(); j++)	{
			if(j%100000 == 0)
			{
				std::cout << "j:" << j << std::endl;
			}
#ifdef DEBUG_V4
			std::cout << "Generating position" << std::endl;
#endif // DEBUG_V4
			size_t pos = position_distribution(generator);

			if (vec[j]->d_list.size() > 0) { // TODO: not quite what is in the paper
#ifdef DEBUG_V4
				std::cout << "Grabbing front element of list at " << j << std::endl;
#endif // DEBUG_V4
				int popped = vec[j]->d_list.front();

#ifdef DEBUG_V4
				std::cout << "Emplacing " << popped << " into list at " << pos << std::endl;
#endif // DEBUG_V4
				vec[pos]->d_list.emplace_back(popped);

#ifdef DEBUG_V4
				std::cout << "Popping from front of list at " << j << " with " << vec[j]->d_list.size() << " elements" << std::endl;
#endif // DEBUG_V4
				vec[j]->d_list.pop_front();
			}

#ifdef DEBUG_V4
			std::cout << "Finished iteration" << std::endl;
#endif // DEBUG_V4
		}
	}

	if (sf > 0) {
		// Access the data
#ifdef DEBUG_V3
		std::cout << "Accessing data AFTER shuffling" << std::endl;
#endif // DEBUG_V3
		result = access_lists(&vec, af, rf);
	}

#ifdef DEBUG_V3
	std::cout << "Deleting memory from vecor" << std::endl;
#endif // DEBUG_V3

	//for (size_t i = 0; i < vec.size(); i++)
	//{
	//	delete vec[i];
	//}

#ifdef DEBUG_V3
	std::cout << "Done running combination" << std::endl;
#endif // DEBUG_V3

	return result;
}

void generate_table(int G, int alloc_num) {
	int sf = 5;
	for (int S = 0; S >= 0; S--) { // S = 21
		std::cout << "S=" << S << " " << std::flush;
		for (int af = 256; af >= 1; af >>= 1) {
			int rf = AF_RF_PRODUCT / af;
#ifdef DEBUG_V3
			std::cout << "G: " << G << " S: " << S << " af: " << af << " sf: " << sf << " rf: " << rf << std::endl;
#endif
			int pid = fork();
			if (pid == 0) { // Child process
				double result = 0;
				switch (alloc_num) {
					case 0: {
						result = run_combination<typename subsystems::def>(G, S, af, sf, rf);
						break;
					}

					case 7: {
						result = run_combination<typename subsystems::multipool>(G, S, af, sf, rf);
						break;
					}
				}
				std::cout << result << " " << std::flush;
				exit(0);
			}
			else {
				int error;
				wait(&error);
				if (error) {
					std::cout << "Error code " << error << "at G: " << G << " S: " << S << " af: " << af << " sf: " << sf << " rf: " << rf << std::endl;
				}
			}
		}
		std::cout << std::endl;
	}
}

int main(int argc, char *argv[]) {
	// TODO: Notes:
	// 1) Incremented int by 1 on each iteration of af, to prevent compiler optimizing away loop (also used Chandler's
	//    optimizer-defeating functions to access the ints after each iteration -- could this be a problem with caching?)
	// 2) Couldn't follow paper exactly, because popping off subsystems iteratively (then pushing randmonly) means that on
	//    2nd (and further) iterations through the list, some subsystems will not have an element to pop.

	// For baseline, G = 10^7, af = 10

	std::cout << "Started" << std::endl;

	//size_t default_subsystem_size = sizeof(subsystems::def);
	//size_t alloc_subsystem_size = sizeof(subsystems::multipool);
	//size_t list_size = sizeof(subsystems::multipool::d_list);
	//size_t int_size = sizeof(int);
	//size_t ptr_size = sizeof(void *);

	//int G = 20;

	//std::cout << "Object Sizes" << std::endl;
	//std::cout << "Def: " << default_subsystem_size << " Alloc: " << alloc_subsystem_size << " List: " << list_size << " Int: " << int_size << " Pointer: " << ptr_size << std::endl;
	//
	//std::cout << "Total Sizes: " << std::endl;
	//std::cout << "Def: " << default_subsystem_size*(1 << G) << " Alloc: " << alloc_subsystem_size*(1 << G) << " List: " << list_size*(1 << G) << " Int: " << int_size*(1 << G) << " Pointer: " << ptr_size*(1 << G)*2 << std::endl;

	//std::cout << "Total Usage" << std::endl;
	//std::cout << default_subsystem_size*(1 << G) + int_size*(1 << G) + 2 * ptr_size*(1 << G) << std::endl;

	//struct rlimit rlim;
	//getrlimit(RLIMIT_AS, &rlim);

	//std::cout << "Limit: " << rlim.rlim_cur << std::endl;
	//
	//char * arr = new char[92274688];
	//escape(arr);
	//arr[92274687] = 0;

	//std::vector<typename subsystems::def> vec;
	//std::allocator<int> alloc;
	//vec.emplace_back(alloc);

	//std::vector<typename subsystems::multipool> vec_1;
	//BloombergLP::bdlma::MultipoolAllocator alloc_1;
	//vec_1.emplace_back(alloc_1);

	//{
	//	std::cout << "Creating allocator" << std::endl;
	//	BloombergLP::bdlma::MultipoolAllocator alloc;
	//	std::cout << "Creating Vector" << std::endl;
	//	typename vectors::multipool vector(&alloc);
	//	std::cout << "Creating List" << std::endl;
	//	vector.emplace_back(&alloc);
	//	std::cout << "Adding to list" << std::endl;
	//	vector[0].push_back(3);
	//	std::cout << "Reading from List/Vector" << std::endl;
	//	std::cout << vector[0].back() << std::endl;
	//	std::cout << "Destroying Vector/List" << std::endl;
	//}

	std::cout << "Problem Size 2^21 Without Allocators" << std::endl;
	generate_table(21, 0);

	//std::cout << "Problem Size 2^25 Without Allocators" << std::endl;
	//generate_table(25, 0);

	//std::cout << "Problem Size 2^21 With Allocators" << std::endl;
	//generate_table(21, 7);

	//std::cout << "Problem Size 2^25 With Allocators" << std::endl;
	//generate_table(25, 7);

	//run_combination<typename subsystems::multipool>(2, 1, 5, 5, 5);

	std::cout << "Done" << std::endl;
}
<commit_msg>Removed old code<commit_after>// Debugging Settings
#define DEBUG
#define DEBUG_V1
#define DEBUG_V2
#define DEBUG_V3
//#define DEBUG_V4

#include <iostream>
#include <iomanip>
#include <memory>
#include <random>
#include <iterator>
#include <functional>
#include <ctime>

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <memory.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <sys/resource.h>
#include <math.h>

#include <bsl_memory.h>
#include <bslma_testallocator.h>
#include <bslma_newdeleteallocator.h>
#include <bsls_stopwatch.h>

#include <bdlma_sequentialpool.h>
#include <bdlma_sequentialallocator.h>
#include <bdlma_bufferedsequentialallocator.h>
#include <bdlma_multipoolallocator.h>

#include <vector>
#include <list>

#include "benchmark_common.h"

// Debugging
#include <typeinfo>
#include <assert.h>

using namespace BloombergLP;

// Global Variables

#ifdef DEBUG
int AF_RF_PRODUCT = 256;
#else
int AF_RF_PRODUCT = 2560;
#endif // DEBUG

template<typename ALLOC>
class AllocSubsystem {
public:
	ALLOC d_alloc;
	std::list<int, alloc_adaptor<int, ALLOC> > d_list;
	AllocSubsystem() : d_alloc(), d_list(&d_alloc) {}
};

class DefaultSubsystem {
public:
	std::list<int> d_list;
	DefaultSubsystem() : d_list() {}
};

// Convenience typedefs
struct subsystems {
	typedef DefaultSubsystem def;
	typedef AllocSubsystem<BloombergLP::bdlma::MultipoolAllocator> multipool;
};

template<typename VECTOR>
double access_lists(VECTOR *vec, int af, int rf) {
#ifdef DEBUG_V3
	std::cout << "Accessing Lists" << std::endl;
#endif // DEBUG_V3

	std::clock_t c_start = std::clock();

	for (size_t r = 0; r < rf; r++)	{
		for (size_t i = 0; i < vec->size(); i++) {
			for (size_t a = 0; a < af; a++) {
				for (auto it = (*vec)[i]->d_list.begin(); it != (*vec)[i]->d_list.end(); ++it) {
					(*it)++; // Increment int to cause loop to have some effect
				}
				clobber(); // TODO will this hurt caching?
			}
		}
	}
	std::clock_t c_end = std::clock();

#ifdef DEBUG_V3
	std::cout << "Finished accessing Lists" << std::endl;
#endif // DEBUG_V3
	return (c_end - c_start) * 1.0 / CLOCKS_PER_SEC;
}

template<typename SUBSYS>
double run_combination(int G, int S, int af, int sf, int rf) {
	// G  = Total system size (# subsystems * elements in subsystems). Given as power of 2 (size really = 2^G)
	// S  = Elements per subsystem. Given as power of 2 (size really = 2^S)
	// af = Access Factor - Number of iterations through a subsystem (linked list) before moving to the next
	// sf = Shuffle Factor - Number of elements popped from each list and pushed to a randomly chosen list
	//						 Note: -ve value means access occurs before shuffle
	// rf = Repeat Factor - Number of times the subsystems are iterated over

	int k = std::abs(G) - std::abs(S);
	size_t expanded_S = 1, expanded_k = 1;
	expanded_S <<= S;
	expanded_k <<= k;

#ifdef DEBUG_V3
	std::cout << "Total number of lists (k) = 2^" << k << " (aka " << expanded_k << ")" << std::endl;
	std::cout << "Total number of elements per sub system (S) = 2^" << S << " (aka " << expanded_S << ")" << std::endl;
#endif // DEBUG_V3

	std::vector<SUBSYS *> vec;

	// Create data under test
	vec.reserve(expanded_k);
	for (size_t i = 0; i < expanded_k; i++)	{
		vec.emplace_back(new SUBSYS()); // Never deallocated because we exit immediately after this function reutrns anyway

		for (size_t j = 0; j < expanded_S; j++)
		{
			vec.back()->d_list.emplace_back((int)j);
		}
	}

#ifdef DEBUG_V3
	std::cout << "Created vector with " << vec.size() << " elements" << std::endl;
#endif // DEBUG_V3

	double result = 0.0;
	if (sf < 0) {
		// Access the data
#ifdef DEBUG_V3
		std::cout << "Accessing data BEFORE shuffling" << std::endl;
#endif // DEBUG_V3
		result = access_lists(&vec, af, rf);
	}

	// Shuffle the data
#ifdef DEBUG_V3
	std::cout << "Shuffling data " << std::abs(sf) << " times" << std::endl;
#endif // DEBUG_V3

	std::default_random_engine generator(1); // Consistent seed to get the same (pseudo) random distribution each time
	std::uniform_int_distribution<size_t> position_distribution(0, vec.size() - 1);
	for (size_t i = 0; i < std::abs(sf); i++) {
		for (size_t j = 0; j < vec.size(); j++)	{
			if(j%100000 == 0)
			{
				std::cout << "j:" << j << std::endl;
			}
#ifdef DEBUG_V4
			std::cout << "Generating position" << std::endl;
#endif // DEBUG_V4
			size_t pos = position_distribution(generator);

			if (vec[j]->d_list.size() > 0) { // TODO: not quite what is in the paper
#ifdef DEBUG_V4
				std::cout << "Grabbing front element of list at " << j << std::endl;
#endif // DEBUG_V4
				int popped = vec[j]->d_list.front();

#ifdef DEBUG_V4
				std::cout << "Emplacing " << popped << " into list at " << pos << std::endl;
#endif // DEBUG_V4
				vec[pos]->d_list.emplace_back(popped);

#ifdef DEBUG_V4
				std::cout << "Popping from front of list at " << j << " with " << vec[j]->d_list.size() << " elements" << std::endl;
#endif // DEBUG_V4
				vec[j]->d_list.pop_front();
			}

#ifdef DEBUG_V4
			std::cout << "Finished iteration" << std::endl;
#endif // DEBUG_V4
		}
	}

	if (sf > 0) {
		// Access the data
#ifdef DEBUG_V3
		std::cout << "Accessing data AFTER shuffling" << std::endl;
#endif // DEBUG_V3
		result = access_lists(&vec, af, rf);
	}

#ifdef DEBUG_V3
	std::cout << "Done running combination" << std::endl;
#endif // DEBUG_V3

	return result;
}

void generate_table(int G, int alloc_num) {
	int sf = 5;
	for (int S = 0; S >= 0; S--) { // S = 21
		std::cout << "S=" << S << " " << std::flush;
		for (int af = 256; af >= 1; af >>= 1) {
			int rf = AF_RF_PRODUCT / af;
#ifdef DEBUG_V3
			std::cout << "G: " << G << " S: " << S << " af: " << af << " sf: " << sf << " rf: " << rf << std::endl;
#endif
			int pid = fork();
			if (pid == 0) { // Child process
				double result = 0;
				switch (alloc_num) {
					case 0: {
						result = run_combination<typename subsystems::def>(G, S, af, sf, rf);
						break;
					}

					case 7: {
						result = run_combination<typename subsystems::multipool>(G, S, af, sf, rf);
						break;
					}
				}
				std::cout << result << " " << std::flush;
				exit(0);
			}
			else {
				int error;
				wait(&error);
				if (error) {
					std::cout << "Error code " << error << "at G: " << G << " S: " << S << " af: " << af << " sf: " << sf << " rf: " << rf << std::endl;
				}
			}
		}
		std::cout << std::endl;
	}
}

int main(int argc, char *argv[]) {
	// TODO: Notes:
	// 1) Incremented int by 1 on each iteration of af, to prevent compiler optimizing away loop (also used Chandler's
	//    optimizer-defeating functions to access the ints after each iteration -- could this be a problem with caching?)
	// 2) Couldn't follow paper exactly, because popping off subsystems iteratively (then pushing randmonly) means that on
	//    2nd (and further) iterations through the list, some subsystems will not have an element to pop.

	// For baseline, G = 10^7, af = 10

	std::cout << "Started" << std::endl;

	std::cout << "Problem Size 2^21 Without Allocators" << std::endl;
	generate_table(21, 0);

	std::cout << "Problem Size 2^25 Without Allocators" << std::endl;
	generate_table(25, 0);

	std::cout << "Problem Size 2^21 With Allocators" << std::endl;
	generate_table(21, 7);

	std::cout << "Problem Size 2^25 With Allocators" << std::endl;
	generate_table(25, 7);

	std::cout << "Done" << std::endl;
}
<|endoftext|>


<commit_before>#include <unistd.h>
#include <string>
#include <iostream>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>

#include "FatSystem.h"
#include "FatFilename.h"
#include "FatEntry.h"
#include "utils.h"

using namespace std;

/**
 * Opens the FAT resource
 */
FatSystem::FatSystem(string filename)
    : strange(0),
    totalSize(-1),
    listDeleted(false),
    contiguous(false)
{
    fd = open(filename.c_str(), O_RDONLY);
}

FatSystem::~FatSystem()
{
    close(fd);
}

/**
 * Reading some data
 */
void FatSystem::readData(int address, char *buffer, int size)
{
    if (totalSize != -1 && address+size > totalSize) {
        cout << "! Trying to read outside the disk" << endl;
    }

    lseek(fd, address, SEEK_SET);
    read(fd, buffer, size);
}

/**
 * Parses FAT header
 */
void FatSystem::parseHeader()
{
    char buffer[128];

    readData(0x0, buffer, sizeof(buffer));
    bytesPerSector = FAT_READ_SHORT(buffer, FAT_BYTES_PER_SECTOR);
    sectorsPerCluster = buffer[FAT_SECTORS_PER_CLUSTER];
    reservedSectors = FAT_READ_SHORT(buffer, FAT_RESERVED_SECTORS);
    fats = buffer[FAT_FATS];
    sectorsPerFat = FAT_READ_LONG(buffer, FAT_SECTORS_PER_FAT);
    rootDirectory = FAT_READ_LONG(buffer, FAT_ROOT_DIRECTORY);
    totalSectors = FAT_READ_LONG(buffer, FAT_TOTAL_SECTORS);
    diskLabel = string(buffer+FAT_DISK_LABEL, FAT_DISK_LABEL_SIZE);
    oemName = string(buffer+FAT_DISK_OEM, FAT_DISK_OEM_SIZE);
    fsType = string(buffer+FAT_DISK_FS, FAT_DISK_FS_SIZE);

    if (bytesPerSector != 512) {
        printf("WARNING: Bytes per sector is not 512 (%d)\n", bytesPerSector);
        strange++;
    }

    if (sectorsPerCluster > 128) {
        printf("WARNING: Sectors per cluster high (%d)\n", sectorsPerCluster);
        strange++;
    }

    if (reservedSectors != 0x20) {
        printf("WARNING: Reserved sectors !=0x20 (0x%08x)\n", reservedSectors);
        strange++;
    }

    if (fats != 2) {
        printf("WARNING: Fats number different of 2 (%d)\n", fats);
        strange++;
    }

    if (rootDirectory != 2) {
        printf("WARNING: Root directory is not 2 (%d)\n", rootDirectory);
        strange++;
    }
}

/**
 * Returns the 32-bit fat value for the given cluster number
 */
int FatSystem::nextCluster(int cluster)
{
    char buffer[4];

    if (contiguous) {
        return cluster+1;
    }

    readData(fatStart+4*cluster, buffer, sizeof(buffer));

    int next = FAT_READ_LONG(buffer, 0);

    if (next >= 0x0ffffff0) {
        return FAT_LAST;
    } else {
        return next;
    }
}

int FatSystem::clusterAddress(int cluster)
{
    return (dataStart + bytesPerSector*sectorsPerCluster*(cluster-2));
}

vector<FatEntry> FatSystem::getEntries(int cluster)
{
    vector<FatEntry> entries;
    FatFilename filename;

    if (cluster == 0) {
        cluster = rootDirectory;
    }

    do {
        int address = clusterAddress(cluster);
        char buffer[FAT_ENTRY_SIZE];

        int i;
        for (i=0; i<bytesPerSector*sectorsPerCluster; i+=sizeof(buffer)) {
            // Reading data
            readData(address, buffer, sizeof(buffer));
            address += sizeof(buffer);

            // Creating entry
            FatEntry entry;

            entry.attributes = buffer[FAT_ATTRIBUTES];

            if (entry.attributes & FAT_ATTRIBUTES_LONGFILE) {
                // Long file part
                filename.append(buffer);
            } else {
                entry.shortName = string(buffer, 11);
                entry.longName = filename.getFilename();
                entry.cluster = FAT_READ_SHORT(buffer, FAT_CLUSTER_LOW) | (FAT_READ_SHORT(buffer, FAT_CLUSTER_HIGH)<<16);
                entry.size = FAT_READ_LONG(buffer, FAT_FILESIZE);

                if (entry.attributes&FAT_ATTRIBUTES_DIR || entry.attributes&FAT_ATTRIBUTES_FILE) {
                    entries.push_back(entry);
                }
            }
        }

        cluster = nextCluster(cluster);
    } while (cluster != FAT_LAST);

    return entries;
}

void FatSystem::list(FatPath &path)
{
    int cluster;

    if (findDirectory(path, &cluster)) {
        list(cluster);
    }
}

void FatSystem::list(int cluster)
{
    vector<FatEntry> entries = getEntries(cluster);
    vector<FatEntry>::iterator it;

    for (it=entries.begin(); it!=entries.end(); it++) {
        FatEntry &entry = *it;

        if (entry.isErased() && !listDeleted) {
            continue;
        }

        if (entry.isDirectory()) {
            printf("d");
        } else {
            printf("f");
        }

        string name = entry.getFilename();
        if (entry.isDirectory()) {
            name += "/";
        }
        printf(" %-40s", name.c_str());

        printf(" c=%d", entry.cluster);

        if (!entry.isDirectory()) {
            printf(" s=%d", entry.size);
        }

        if (entry.isHidden()) {
            printf(" h");
        }
        if (entry.isErased()) {
            printf(" d");
        }

        printf("\n");
    }
}

void FatSystem::readFile(int cluster, int size, FILE *f)
{
    if (f == NULL) {
        f = stdout;
    }

    while ((size!=0) && cluster!=FAT_LAST) {
        int toRead = size;
        if (toRead > bytesPerCluster || size < 0) {
            toRead = bytesPerCluster;
        }
        char buffer[bytesPerCluster];
        readData(clusterAddress(cluster), buffer, toRead);

        if (size != -1) {
            size -= toRead;
        }

        // Write file data to the given file
        fwrite(buffer, toRead, 1, f);

        cluster = nextCluster(cluster);

        if (cluster == 0) {
            fprintf(stderr, "! One of your file's cluster is 0 (maybe FAT is broken, you should try -c)\n");
        }
    }
}

bool FatSystem::init()
{
    // Parsing header
    parseHeader();

    // Computing values
    fatStart = bytesPerSector*reservedSectors;
    dataStart = fatStart + fats*sectorsPerFat*bytesPerSector;
    bytesPerCluster = bytesPerSector*sectorsPerCluster;
    totalSize = totalSectors*bytesPerSector;
    fatSize = sectorsPerFat*bytesPerSector;

    return strange == 0;
}

void FatSystem::infos()
{
    cout << "FAT Filesystem informations" << endl << endl;

    cout << "Filesystem type: " << fsType << endl;
    cout << "OEM name: " << oemName << endl;
    cout << "Total sectors: " << totalSectors << endl;
    cout << "Disk size: " << totalSize << endl;
    cout << "Bytes per sector: " << bytesPerSector << endl;
    cout << "Sectors per cluster: " << sectorsPerCluster << endl;
    cout << "Bytes per cluster: " << bytesPerCluster << endl;
    cout << "Reserved sectors: " << reservedSectors << endl;
    cout << "Sectors per FAT: " << sectorsPerFat << endl;
    cout << "Fat size: " << fatSize << endl;
    printf("FAT start address: %08x\n", fatStart);
    printf("Data start address: %08x\n", dataStart);
    cout << "Root directory cluster: " << rootDirectory << endl;
    cout << "Disk label: " << diskLabel << endl;
}

bool FatSystem::findDirectory(FatPath &path, int *cluster)
{
    vector<string> parts = path.getParts();
    *cluster = rootDirectory;

    for (int i=0; i<parts.size(); i++) {
        if (parts[i] != "") {
            vector<FatEntry> entries = getEntries(*cluster);
            vector<FatEntry>::iterator it;
            bool found = false;

            for (it=entries.begin(); it!=entries.end(); it++) {
                FatEntry &entry = *it;
                string name = entry.getFilename();
                if (name == parts[i]) {
                    *cluster = entry.cluster;
                    found = true;
                }
            }

            if (!found) {
                cerr << "Error: directory " << path.getPath() << " not found" << endl;
                return false;
            }
        }
    }

    return true;
}

bool FatSystem::findFile(FatPath &path, int *cluster, int *size, bool *erased)
{
    string dirname = path.getDirname();
    string basename = path.getBasename();

    FatPath parent(dirname);
    int parentCluster;
    if (findDirectory(parent, &parentCluster)) {
        vector<FatEntry> entries = getEntries(parentCluster);
        vector<FatEntry>::iterator it;

        for (it=entries.begin(); it!=entries.end(); it++) {
            FatEntry &entry = (*it);
            if (entry.getFilename() == path.getBasename()) {
                *cluster = entry.cluster;
                *size = entry.size;
                *erased = entry.isErased();
                return true;
            }
        }
    }

    return false;
}

void FatSystem::readFile(FatPath &path, FILE *f)
{
    bool contiguousSave = contiguous;
    contiguous = false;
    int cluster, size;
    bool erased;
    if (findFile(path, &cluster, &size, &erased)) {
        contiguous = contiguousSave;
        if (erased && nextCluster(cluster)==0) {
            fprintf(stderr, "! Trying to read a deleted file, auto-enabling contiguous mode\n");
            contiguous = true;
        }
        readFile(cluster, size, f);
    }
}

void FatSystem::setListDeleted(bool listDeleted_)
{
    listDeleted = listDeleted_;
}

void FatSystem::setContiguous(bool contiguous_)
{
    contiguous = contiguous_;
}

void FatSystem::extractEntry(FatEntry &entry, string directory)
{
    vector<FatEntry> entries = getEntries(entry.cluster);
    vector<FatEntry>::iterator it;

    mkdir(directory.c_str(), 0755);

    for (it=entries.begin(); it!=entries.end(); it++) {
        FatEntry &entry = (*it);

        if (!entry.isErased()) {
            string name = entry.getFilename();

            if (name == "." || name == "..") {
                continue;
            }

            string fullname = directory + "/" + name;

            if (entry.isDirectory()) {
                cout << "Entering " << fullname << endl;
                extractEntry(entry, fullname);
            } else {
                cout << "Extracting " << fullname << endl;
                FILE *output = fopen(fullname.c_str(), "w+");
                if (output != NULL) {
                    readFile(entry.cluster, entry.size, output);
                    fclose(output);
                } else {
                    fprintf(stderr, "! Unable to open %s\n", fullname.c_str());
                }
            }
        }
    }
}

void FatSystem::extract(string directory)
{
    FatEntry entry = rootEntry();
    extractEntry(entry, directory);
}

FatEntry FatSystem::rootEntry()
{
    FatEntry entry;
    entry.longName = "/";
    entry.attributes = FAT_ATTRIBUTES_DIR;
    entry.cluster = rootDirectory;

    return entry;
}
<commit_msg>Extracting deleted files<commit_after>#include <unistd.h>
#include <string>
#include <iostream>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>

#include "FatSystem.h"
#include "FatFilename.h"
#include "FatEntry.h"
#include "utils.h"

using namespace std;

/**
 * Opens the FAT resource
 */
FatSystem::FatSystem(string filename)
    : strange(0),
    totalSize(-1),
    listDeleted(false),
    contiguous(false)
{
    fd = open(filename.c_str(), O_RDONLY);
}

FatSystem::~FatSystem()
{
    close(fd);
}

/**
 * Reading some data
 */
void FatSystem::readData(int address, char *buffer, int size)
{
    if (totalSize != -1 && address+size > totalSize) {
        cout << "! Trying to read outside the disk" << endl;
    }

    lseek(fd, address, SEEK_SET);
    read(fd, buffer, size);
}

/**
 * Parses FAT header
 */
void FatSystem::parseHeader()
{
    char buffer[128];

    readData(0x0, buffer, sizeof(buffer));
    bytesPerSector = FAT_READ_SHORT(buffer, FAT_BYTES_PER_SECTOR);
    sectorsPerCluster = buffer[FAT_SECTORS_PER_CLUSTER];
    reservedSectors = FAT_READ_SHORT(buffer, FAT_RESERVED_SECTORS);
    fats = buffer[FAT_FATS];
    sectorsPerFat = FAT_READ_LONG(buffer, FAT_SECTORS_PER_FAT);
    rootDirectory = FAT_READ_LONG(buffer, FAT_ROOT_DIRECTORY);
    totalSectors = FAT_READ_LONG(buffer, FAT_TOTAL_SECTORS);
    diskLabel = string(buffer+FAT_DISK_LABEL, FAT_DISK_LABEL_SIZE);
    oemName = string(buffer+FAT_DISK_OEM, FAT_DISK_OEM_SIZE);
    fsType = string(buffer+FAT_DISK_FS, FAT_DISK_FS_SIZE);

    if (bytesPerSector != 512) {
        printf("WARNING: Bytes per sector is not 512 (%d)\n", bytesPerSector);
        strange++;
    }

    if (sectorsPerCluster > 128) {
        printf("WARNING: Sectors per cluster high (%d)\n", sectorsPerCluster);
        strange++;
    }

    if (reservedSectors != 0x20) {
        printf("WARNING: Reserved sectors !=0x20 (0x%08x)\n", reservedSectors);
        strange++;
    }

    if (fats != 2) {
        printf("WARNING: Fats number different of 2 (%d)\n", fats);
        strange++;
    }

    if (rootDirectory != 2) {
        printf("WARNING: Root directory is not 2 (%d)\n", rootDirectory);
        strange++;
    }
}

/**
 * Returns the 32-bit fat value for the given cluster number
 */
int FatSystem::nextCluster(int cluster)
{
    char buffer[4];

    if (contiguous) {
        return cluster+1;
    }

    readData(fatStart+4*cluster, buffer, sizeof(buffer));

    int next = FAT_READ_LONG(buffer, 0);

    if (next >= 0x0ffffff0) {
        return FAT_LAST;
    } else {
        return next;
    }
}

int FatSystem::clusterAddress(int cluster)
{
    return (dataStart + bytesPerSector*sectorsPerCluster*(cluster-2));
}

vector<FatEntry> FatSystem::getEntries(int cluster)
{
    vector<FatEntry> entries;
    FatFilename filename;

    if (cluster == 0) {
        cluster = rootDirectory;
    }

    do {
        int address = clusterAddress(cluster);
        char buffer[FAT_ENTRY_SIZE];

        int i;
        for (i=0; i<bytesPerSector*sectorsPerCluster; i+=sizeof(buffer)) {
            // Reading data
            readData(address, buffer, sizeof(buffer));
            address += sizeof(buffer);

            // Creating entry
            FatEntry entry;

            entry.attributes = buffer[FAT_ATTRIBUTES];

            if (entry.attributes & FAT_ATTRIBUTES_LONGFILE) {
                // Long file part
                filename.append(buffer);
            } else {
                entry.shortName = string(buffer, 11);
                entry.longName = filename.getFilename();
                entry.cluster = FAT_READ_SHORT(buffer, FAT_CLUSTER_LOW) | (FAT_READ_SHORT(buffer, FAT_CLUSTER_HIGH)<<16);
                entry.size = FAT_READ_LONG(buffer, FAT_FILESIZE);

                if (entry.attributes&FAT_ATTRIBUTES_DIR || entry.attributes&FAT_ATTRIBUTES_FILE) {
                    entries.push_back(entry);
                }
            }
        }

        cluster = nextCluster(cluster);
    } while (cluster != FAT_LAST);

    return entries;
}

void FatSystem::list(FatPath &path)
{
    int cluster;

    if (findDirectory(path, &cluster)) {
        list(cluster);
    }
}

void FatSystem::list(int cluster)
{
    vector<FatEntry> entries = getEntries(cluster);
    vector<FatEntry>::iterator it;

    for (it=entries.begin(); it!=entries.end(); it++) {
        FatEntry &entry = *it;

        if (entry.isErased() && !listDeleted) {
            continue;
        }

        if (entry.isDirectory()) {
            printf("d");
        } else {
            printf("f");
        }

        string name = entry.getFilename();
        if (entry.isDirectory()) {
            name += "/";
        }
        printf(" %-40s", name.c_str());

        printf(" c=%d", entry.cluster);

        if (!entry.isDirectory()) {
            printf(" s=%d", entry.size);
        }

        if (entry.isHidden()) {
            printf(" h");
        }
        if (entry.isErased()) {
            printf(" d");
        }

        printf("\n");
    }
}

void FatSystem::readFile(int cluster, int size, FILE *f)
{
    if (f == NULL) {
        f = stdout;
    }

    while ((size!=0) && cluster!=FAT_LAST) {
        int toRead = size;
        if (toRead > bytesPerCluster || size < 0) {
            toRead = bytesPerCluster;
        }
        char buffer[bytesPerCluster];
        readData(clusterAddress(cluster), buffer, toRead);

        if (size != -1) {
            size -= toRead;
        }

        // Write file data to the given file
        fwrite(buffer, toRead, 1, f);

        cluster = nextCluster(cluster);

        if (cluster == 0) {
            fprintf(stderr, "! One of your file's cluster is 0 (maybe FAT is broken, you should try -c)\n");
        }
    }
}

bool FatSystem::init()
{
    // Parsing header
    parseHeader();

    // Computing values
    fatStart = bytesPerSector*reservedSectors;
    dataStart = fatStart + fats*sectorsPerFat*bytesPerSector;
    bytesPerCluster = bytesPerSector*sectorsPerCluster;
    totalSize = totalSectors*bytesPerSector;
    fatSize = sectorsPerFat*bytesPerSector;

    return strange == 0;
}

void FatSystem::infos()
{
    cout << "FAT Filesystem informations" << endl << endl;

    cout << "Filesystem type: " << fsType << endl;
    cout << "OEM name: " << oemName << endl;
    cout << "Total sectors: " << totalSectors << endl;
    cout << "Disk size: " << totalSize << endl;
    cout << "Bytes per sector: " << bytesPerSector << endl;
    cout << "Sectors per cluster: " << sectorsPerCluster << endl;
    cout << "Bytes per cluster: " << bytesPerCluster << endl;
    cout << "Reserved sectors: " << reservedSectors << endl;
    cout << "Sectors per FAT: " << sectorsPerFat << endl;
    cout << "Fat size: " << fatSize << endl;
    printf("FAT start address: %08x\n", fatStart);
    printf("Data start address: %08x\n", dataStart);
    cout << "Root directory cluster: " << rootDirectory << endl;
    cout << "Disk label: " << diskLabel << endl;
}

bool FatSystem::findDirectory(FatPath &path, int *cluster)
{
    vector<string> parts = path.getParts();
    *cluster = rootDirectory;

    for (int i=0; i<parts.size(); i++) {
        if (parts[i] != "") {
            vector<FatEntry> entries = getEntries(*cluster);
            vector<FatEntry>::iterator it;
            bool found = false;

            for (it=entries.begin(); it!=entries.end(); it++) {
                FatEntry &entry = *it;
                string name = entry.getFilename();
                if (name == parts[i]) {
                    *cluster = entry.cluster;
                    found = true;
                }
            }

            if (!found) {
                cerr << "Error: directory " << path.getPath() << " not found" << endl;
                return false;
            }
        }
    }

    return true;
}

bool FatSystem::findFile(FatPath &path, int *cluster, int *size, bool *erased)
{
    string dirname = path.getDirname();
    string basename = path.getBasename();

    FatPath parent(dirname);
    int parentCluster;
    if (findDirectory(parent, &parentCluster)) {
        vector<FatEntry> entries = getEntries(parentCluster);
        vector<FatEntry>::iterator it;

        for (it=entries.begin(); it!=entries.end(); it++) {
            FatEntry &entry = (*it);
            if (entry.getFilename() == path.getBasename()) {
                *cluster = entry.cluster;
                *size = entry.size;
                *erased = entry.isErased();
                return true;
            }
        }
    }

    return false;
}

void FatSystem::readFile(FatPath &path, FILE *f)
{
    bool contiguousSave = contiguous;
    contiguous = false;
    int cluster, size;
    bool erased;
    if (findFile(path, &cluster, &size, &erased)) {
        contiguous = contiguousSave;
        if (erased && nextCluster(cluster)==0) {
            fprintf(stderr, "! Trying to read a deleted file, auto-enabling contiguous mode\n");
            contiguous = true;
        }
        readFile(cluster, size, f);
    }
}

void FatSystem::setListDeleted(bool listDeleted_)
{
    listDeleted = listDeleted_;
}

void FatSystem::setContiguous(bool contiguous_)
{
    contiguous = contiguous_;
}

void FatSystem::extractEntry(FatEntry &entry, string directory)
{
    vector<FatEntry> entries = getEntries(entry.cluster);
    vector<FatEntry>::iterator it;

    mkdir(directory.c_str(), 0755);

    for (it=entries.begin(); it!=entries.end(); it++) {
        FatEntry &entry = (*it);

        if (listDeleted || (!entry.isErased())) {
            string name = entry.getFilename();

            if (name == "." || name == "..") {
                continue;
            }

            string fullname = directory + "/" + name;

            if (entry.isDirectory()) {
                cout << "Entering " << fullname << endl;
                extractEntry(entry, fullname);
            } else {
                cout << "Extracting " << fullname << endl;
                FILE *output = fopen(fullname.c_str(), "w+");
                if (output != NULL) {
                    bool contiguousSave = contiguous;
                    if (entry.isErased() && nextCluster(entry.cluster)==0) {
                        fprintf(stderr, "! Trying to read a deleted file, auto-enabling contiguous mode\n");
                        contiguous = true;
                    }
                    readFile(entry.cluster, entry.size, output);
                    fclose(output);
                    contiguous = contiguousSave;
                } else {
                    fprintf(stderr, "! Unable to open %s\n", fullname.c_str());
                }
            }
        }
    }
}

void FatSystem::extract(string directory)
{
    FatEntry entry = rootEntry();
    extractEntry(entry, directory);
}

FatEntry FatSystem::rootEntry()
{
    FatEntry entry;
    entry.longName = "/";
    entry.attributes = FAT_ATTRIBUTES_DIR;
    entry.cluster = rootDirectory;

    return entry;
}
<|endoftext|>


<commit_before># define CATCH_CONFIG_RUNNER
# include "catch.hpp"
# include <cmath>
# include <string>

int gcd(int a, int b)
{
	if (b == 0)
	{
	return a;
	}
	else if(a==0)
	{
		return b;
	}
	else
	{
		return gcd(b, a%b);
	}
}

double mileToKilometer(double mile)
{
	double kilometer;
	kilometer = mile*1.60934;
	return kilometer;
}

float ZylinderOberfl(float r, float h)
{
    float oberfl = (2*M_PI*r*r)+(2*M_PI*r*h);
    return oberfl;
}

float ZylinderVol(float r, float h)
{
    float vol = M_PI*(r*r)*h
    return vol;
}

float frac(float x)
{
    int y = (int)x;
    int z = y-x;
    return z;
}

int checksum(int Zahl)
{
    int sum = 0;
	while(Zahl>0)
	{
        sum += Zahl%10;
        Zahl /= 10;
	}
    return sum;
}

int sumMultiples()
{
    int sum = 0;
	for (int i = 0; i <= 1000; i++)
	{
		if (i % 3 == 0)
		{
			sum += i;
		}
		else if (i % 5 == 0)
		{
			sum += i;
		}

	}
    return sum;
}

TEST_CASE("describe_gcd ", "[gcd]")
{
	REQUIRE(gcd(2, 4) == 2);
	REQUIRE(gcd(6, 9) == 3);
	REQUIRE(gcd(3, 7) == 1);
}

TEST_CASE("describe_sumMultiples ", "[sumMultiples]")
{
	REQUIRE(sumMultiples() ==234168);
}

TEST_CASE("describe_checksum ", "[checksum]")
{
	REQUIRE(checksum(15) == 6);
	REQUIRE(checksum(25) == 7);
	REQUIRE(checksum(35) == 8);
}

TEST_CASE("describe_ZylinderVol","[ZylinderVol]")
{
	REQUIRE(ZylinderVol(1,2) == Approx(6.283));
}

TEST_CASE("describe_ZylinderOberfl","[ZylinderOberfl]")
{
	REQUIRE(ZylinderOberfl(1,2) == Approx(18.85));
}

TEST_CASE("describe_mileToKilometer","[mileToKilometer]")
{
	REQUIRE(mileToKilometer(1) == Approx(1.60934));
	REQUIRE(mileToKilometer(2) == Approx(3,21869));
	REQUIRE(mileToKilometer(5) == Approx(8,04672));
}

TEST_CASE("describe_frac","[frac]")
{
	REQUIRE(frac(1.11) == Approx(0.11));
	REQUIRE(frac(45.1234) == Approx(0.1234));
}

int main(int argc, char* argv[])
{
  return Catch::Session().run(argc, argv);
}

<commit_msg>Update tests.cpp<commit_after># define CATCH_CONFIG_RUNNER
# include "catch.hpp"
# include <cmath>
# include <string>

int gcd(int a, int b)
{
	if (b == 0)
	{
		return a;
	}
	else if(a==0)
	{
		return b;
	}
	else if(a<b)
	{
		return gcd(b, a%b);
	}
	else
	{
		return gcd(b, a%b);
	}
}

double mileToKilometer(double mile)
{
	double kilometer;
	kilometer = mile*1.60934;
	return kilometer;
}

float ZylinderOberfl(float r, float h)
{
    float oberfl = (2*M_PI*r*r)+(2*M_PI*r*h);
    return oberfl;
}

float ZylinderVol(float r, float h)
{
    float vol = M_PI*(r*r)*h
    return vol;
}

float frac(float x)
{
    int y = (int)x;
    int z = y-x;
    return z;
}

int checksum(int Zahl)
{
    int sum = 0;
	while(Zahl>0)
	{
        sum += Zahl%10;
        Zahl /= 10;
	}
    return sum;
}

int sumMultiples()
{
    int sum = 0;
	for (int i = 0; i <= 1000; i++)
	{
		if (i % 3 == 0)
		{
			sum += i;
		}
		else if (i % 5 == 0)
		{
			sum += i;
		}

	}
    return sum;
}

TEST_CASE("describe_gcd ", "[gcd]")
{
	REQUIRE(gcd(2, 4) == 2);
	REQUIRE(gcd(6, 9) == 3);
	REQUIRE(gcd(3, 7) == 1);
}

TEST_CASE("describe_sumMultiples ", "[sumMultiples]")
{
	REQUIRE(sumMultiples() ==234168);
}

TEST_CASE("describe_checksum ", "[checksum]")
{
	REQUIRE(checksum(15) == 6);
	REQUIRE(checksum(25) == 7);
	REQUIRE(checksum(35) == 8);
}

TEST_CASE("describe_ZylinderVol","[ZylinderVol]")
{
	REQUIRE(ZylinderVol(1,2) == Approx(6.283));
}

TEST_CASE("describe_ZylinderOberfl","[ZylinderOberfl]")
{
	REQUIRE(ZylinderOberfl(1,2) == Approx(18.85));
}

TEST_CASE("describe_mileToKilometer","[mileToKilometer]")
{
	REQUIRE(mileToKilometer(1) == Approx(1.60934));
	REQUIRE(mileToKilometer(2) == Approx(3,21869));
	REQUIRE(mileToKilometer(5) == Approx(8,04672));
}

TEST_CASE("describe_frac","[frac]")
{
	REQUIRE(frac(1.11) == Approx(0.11));
	REQUIRE(frac(45.1234) == Approx(0.1234));
}

int main(int argc, char* argv[])
{
  return Catch::Session().run(argc, argv);
}

<|endoftext|>