<commit_before>/*
 * Copyright(c) Sophist Solutions, Inc. 1990-2011.  All rights reserved
 */
#include	"../StroikaPreComp.h"

#include	<algorithm>
#include	<cstdlib>
#include	<fstream>
#include	<sstream>

#if		qPlatform_POSIX
	#include	<sys/types.h>
	#include	<unistd.h>
	#include	<signal.h>
#endif

#include	"../../Foundation/Characters/Format.h"
#include	"../../Foundation/Containers/Common.h"
#include	"../../Foundation/Debug/Assertions.h"
#include	"../../Foundation/Debug/Trace.h"
#include	"../../Foundation/Execution/CommandLine.h"
#include	"../../Foundation/Execution/Exceptions.h"
#include	"../../Foundation/Execution/Module.h"
#include	"../../Foundation/Execution/ThreadAbortException.h"
#include	"../../Foundation/IO/FileSystem/FileUtils.h"
#include	"../../Foundation/Memory/SmallStackBuffer.h"

#include	"Main.h"

using	namespace	Stroika::Foundation;
using	namespace	Stroika::Foundation::Containers;
using	namespace	Stroika::Foundation::Memory;

using	namespace	Stroika::Frameworks;
using	namespace	Stroika::Frameworks::Service;

/*
 ********************************************************************************
 ****************************** Service::Main::IRep *****************************
 ********************************************************************************
 */
Main::IRep::IRep ()
	: fStopping_ (false)
	, fMustReReadConfig (false)
{
}

Main::IRep::~IRep ()
{
}

void	Main::IRep::OnStartRequest ()
{
	// This procedure ends when the entire service process ends...
	Debug::TraceContextBumper traceCtx (TSTR ("Stroika::Frameworks::Service::Main::IRep::OnStartRequest"));
	MainLoop ();
}

void	Main::IRep::OnStopRequest ()
{
	// default to using thread stuff to send us a signal to abort...
	fStopping_ = true;
}

void	Main::IRep::OnReReadConfigurationRequest ()
{
}

String	Main::IRep::GetServiceStatusMessage () const
{
	return String ();
}

#if		qPlatform_POSIX
String	Main::IRep::GetPIDFileName () const
{
	return L"/tmp/" + GetServiceDescription ().fName + L".pid";
}
#endif

#if		qPlatform_POSIX
void	Main::IRep::SignalHandler (int signum)
{
	// VERY PRIMITIVE IMPL FOR NOW -- LGP 2011-09-24
	switch (signum) {
	case	SIGTERM:
		fStopping_ = true;
		break;
	#if		qCompilerAndStdLib_Supports_constexpr
		case	kSIG_ReReadConfiguration:
	#else
		case	SIGHUP:
	#endif
			fMustReReadConfig = true;
			break;

	}
}
#endif

/*
 ********************************************************************************
 ************************************ Service::Main *****************************
 ********************************************************************************
 */

const	wchar_t	Service::Main::CommandNames::kRunAsService[]		=	L"Run-As-Service";
const	wchar_t	Service::Main::CommandNames::kStart[]				=	L"Start";
const	wchar_t	Service::Main::CommandNames::kStop[]				=	L"Stop";
const	wchar_t	Service::Main::CommandNames::kKill[]				=	L"Kill";
const	wchar_t	Service::Main::CommandNames::kRestart[]				=	L"Restart";
const	wchar_t	Service::Main::CommandNames::kReloadConfiguration[]	=	L"Reload-Configuration";
const	wchar_t	Service::Main::CommandNames::kPause[]				=	L"Pause";
const	wchar_t	Service::Main::CommandNames::kContinue[]			=	L"Continue";

Memory::SharedPtr<Main::IRep>	Main::_sRep;

Main::Main (Memory::SharedPtr<IRep> rep)
{
	Ensure  (_sRep.IsNull ());
	_sRep = rep;
	#if		qPlatform_POSIX
		SetupSignalHanlders_ ();
	#endif
}

#if		qPlatform_POSIX
void	Main::SetupSignalHanlders_ ()
{
	signal (SIGTERM, SignalHandler);
	signal (kSIG_ReReadConfiguration, SignalHandler);
}
#endif

Main::State	Main::GetState () const
{
	#if		qPlatform_POSIX
	if (GetServicePID () != 0) {
		return eRunning;
	}
	#endif
	return eStopped;	// otherwise (esp on other platforms where not implemtned) must  be stopped
}

#if		qPlatform_POSIX
pid_t	Main::GetServicePID () const
{
	ifstream	in (_sRep->GetPIDFileName ().AsTString ().c_str ());
	if (in) {
		pid_t	n = 0;
		in >> n;
		return n;
	}
	return 0;
}
#endif

String		Main::GetServiceStatusMessage () const
{
	const	wchar_t	kTAB[]	=	L"    ";	// use spaces instead of tab so formatting independent of tabstop settings
	ServiceDescription	svd	=	GetServiceDescription ();
	wstringstream	tmp;
	tmp << L"Service '" << svd.fName.As<wstring> () << "'" << endl;
	switch (this->GetState ()) {
		case	eStopped:
			tmp << kTAB << L"State:  " << kTAB << kTAB << kTAB << "STOPPED" << endl;
			break;
		case	eRunning:
			tmp << kTAB << L"State:  " << kTAB << kTAB << kTAB << "Running" << endl;
			#if		qPlatform_POSIX
				tmp << kTAB << L"PID:    " << kTAB << kTAB << kTAB << GetServicePID () << endl;
			#endif
			break;
		case	ePaused:
			tmp << kTAB << L"State:  " << kTAB << kTAB << kTAB << "PAUSED" << endl;
			#if		qPlatform_POSIX
				tmp << kTAB << L"PID:    " << kTAB<< kTAB << kTAB << GetServicePID () << endl;
			#endif
			break;
		default:
			AssertNotReached ();
	}
	tmp << _sRep->GetServiceStatusMessage ().As<wstring> ();
	return tmp.str ();
}

void	Main::RunAsService ()
{
	// VERY PRIMITIVE IMPL - WE NEED LOCKING on tmpfile stuff - add good tempfile supprot to fileuitls or use existing...

	try {
#if		qPlatform_POSIX
		ofstream	out (_sRep->GetPIDFileName ().AsTString ().c_str ());
		out << getpid () << endl;
#endif
		_sRep->OnStartRequest ();
	}
	catch (const Execution::ThreadAbortException& /*threadAbort*/) {
#if		qPlatform_POSIX
		unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
		// ignore this - just means service ended normally
	}
	catch (...) {
		DbgTrace (TSTR ("Unexpected exception ended running service"));
#if		qPlatform_POSIX
		unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
		throw;
	}
}

void	Main::Start ()
{
	// Check not already runnig, (someday) and then for and exec the

#if		qPlatform_POSIX
	// REALLY should use GETSTATE - and return state based on if PID file exsits...
	if (GetServicePID ()  != 0) {
		Execution::DoThrow (Execution::StringException (L"Cannot Start service because its already running"));
	}
#endif
	Characters::TString	thisEXEPath	=	Execution::GetEXEPath ();
#if		qPlatform_POSIX
	pid_t	pid	=	fork ();
	if (pid == 0) {
		// Child - exec -
		//		TODO:		SHOULD BE CAREFUL ABOUT CLOSING FILE DESCRIPTORS BEFORE THIS ACTION - WE DONT WANT HTEM INHERITED!!!
		//					BUT DONT DO WILLYNILLY - THINK THROUGH - I CANNNOT RECALL THE EXACT RIGHT ANSWER
		int	r	=	execl (thisEXEPath.c_str (), thisEXEPath.c_str (), (String (L"--") + String (CommandNames::kRunAsService)).AsTString ().c_str (), nullptr);
		exit (-1);
	}
	else if (pid < 0) {
		// failed to fork - serious error
		Execution::errno_ErrorException::DoThrow (errno);
	}
	else {
		// parent - in this case - no reason to wait - our work is done... Future versions might wait to
		// see if the 'pidfile' got created....
		//		--LGP 2011-09-23
	}
#endif
}

void	Main::Stop ()
{
	// Send signal to server to stop
#if		qPlatform_POSIX
	kill (GetServicePID (), SIGTERM);
#endif
}

void	Main::Kill ()
{
	Stop ();
	// Send signal to server to stop
#if		qPlatform_POSIX
	kill (GetServicePID (), SIGKILL);
	// REALY should WAIT for server to stop and only do this it fails -
	unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
}

void	Main::Restart ()
{
	IgnoreExceptionsForCall (Stop ());
#if		qPlatform_POSIX
	// REALY should WAIT for server to stop and only do this it fails -
	unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
	Start ();
}

void	Main::ReReadConfiguration ()
{
	// SEND APPROPRIATE SIGNAL
#if		qPlatform_POSIX
	pid_t	pid	=	GetServicePID ();
	Assert (pid != 0);	// maybe throw if non-zero???
	kill (GetServicePID (), kSIG_ReReadConfiguration);
#endif
}

void	Main::Pause ()
{
	AssertNotImplemented ();
}

void	Main::Continue ()
{
	AssertNotImplemented ();
}

Main::ServiceDescription	Main::GetServiceDescription () const
{
	return _sRep->GetServiceDescription ();
}

#if		qPlatform_POSIX
void	Main::SignalHandler (int signum)
{
	_sRep->SignalHandler (signum);
}
#endif

bool	Main::_HandleStandardCommandLineArgument (const String& arg)
{
	if (Execution::MatchesCommandLineArgument (arg, CommandNames::kRunAsService)) {
		RunAsService ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kStart)) {
		Start ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kStop)) {
		Stop ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kKill)) {
		Kill ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kRestart)) {
		Restart ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kReloadConfiguration)) {
		ReReadConfiguration ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kPause)) {
		Pause ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kContinue)) {
		Continue ();
		return true;
	}
	/// MANY more neeeded, and fix to use named constants...
	return false;
}

<commit_msg>fixed problems with recent chagne to ErrNoException stuff<commit_after>/*
 * Copyright(c) Sophist Solutions, Inc. 1990-2011.  All rights reserved
 */
#include	"../StroikaPreComp.h"

#include	<algorithm>
#include	<cstdlib>
#include	<fstream>
#include	<sstream>

#if		qPlatform_POSIX
	#include	<sys/types.h>
	#include	<unistd.h>
	#include	<signal.h>
#endif

#include	"../../Foundation/Characters/Format.h"
#include	"../../Foundation/Containers/Common.h"
#include	"../../Foundation/Debug/Assertions.h"
#include	"../../Foundation/Debug/Trace.h"
#include	"../../Foundation/Execution/CommandLine.h"
#include	"../../Foundation/Execution/Exceptions.h"
#include	"../../Foundation/Execution/ErrNoException.h"
#include	"../../Foundation/Execution/Module.h"
#include	"../../Foundation/Execution/ThreadAbortException.h"
#include	"../../Foundation/IO/FileSystem/FileUtils.h"
#include	"../../Foundation/Memory/SmallStackBuffer.h"

#include	"Main.h"

using	namespace	Stroika::Foundation;
using	namespace	Stroika::Foundation::Containers;
using	namespace	Stroika::Foundation::Memory;

using	namespace	Stroika::Frameworks;
using	namespace	Stroika::Frameworks::Service;

/*
 ********************************************************************************
 ****************************** Service::Main::IRep *****************************
 ********************************************************************************
 */
Main::IRep::IRep ()
	: fStopping_ (false)
	, fMustReReadConfig (false)
{
}

Main::IRep::~IRep ()
{
}

void	Main::IRep::OnStartRequest ()
{
	// This procedure ends when the entire service process ends...
	Debug::TraceContextBumper traceCtx (TSTR ("Stroika::Frameworks::Service::Main::IRep::OnStartRequest"));
	MainLoop ();
}

void	Main::IRep::OnStopRequest ()
{
	// default to using thread stuff to send us a signal to abort...
	fStopping_ = true;
}

void	Main::IRep::OnReReadConfigurationRequest ()
{
}

String	Main::IRep::GetServiceStatusMessage () const
{
	return String ();
}

#if		qPlatform_POSIX
String	Main::IRep::GetPIDFileName () const
{
	return L"/tmp/" + GetServiceDescription ().fName + L".pid";
}
#endif

#if		qPlatform_POSIX
void	Main::IRep::SignalHandler (int signum)
{
	// VERY PRIMITIVE IMPL FOR NOW -- LGP 2011-09-24
	switch (signum) {
	case	SIGTERM:
		fStopping_ = true;
		break;
	#if		qCompilerAndStdLib_Supports_constexpr
		case	kSIG_ReReadConfiguration:
	#else
		case	SIGHUP:
	#endif
			fMustReReadConfig = true;
			break;

	}
}
#endif

/*
 ********************************************************************************
 ************************************ Service::Main *****************************
 ********************************************************************************
 */

const	wchar_t	Service::Main::CommandNames::kRunAsService[]		=	L"Run-As-Service";
const	wchar_t	Service::Main::CommandNames::kStart[]				=	L"Start";
const	wchar_t	Service::Main::CommandNames::kStop[]				=	L"Stop";
const	wchar_t	Service::Main::CommandNames::kKill[]				=	L"Kill";
const	wchar_t	Service::Main::CommandNames::kRestart[]				=	L"Restart";
const	wchar_t	Service::Main::CommandNames::kReloadConfiguration[]	=	L"Reload-Configuration";
const	wchar_t	Service::Main::CommandNames::kPause[]				=	L"Pause";
const	wchar_t	Service::Main::CommandNames::kContinue[]			=	L"Continue";

Memory::SharedPtr<Main::IRep>	Main::_sRep;

Main::Main (Memory::SharedPtr<IRep> rep)
{
	Ensure  (_sRep.IsNull ());
	_sRep = rep;
	#if		qPlatform_POSIX
		SetupSignalHanlders_ ();
	#endif
}

#if		qPlatform_POSIX
void	Main::SetupSignalHanlders_ ()
{
	signal (SIGTERM, SignalHandler);
	signal (kSIG_ReReadConfiguration, SignalHandler);
}
#endif

Main::State	Main::GetState () const
{
	#if		qPlatform_POSIX
	if (GetServicePID () != 0) {
		return eRunning;
	}
	#endif
	return eStopped;	// otherwise (esp on other platforms where not implemtned) must  be stopped
}

#if		qPlatform_POSIX
pid_t	Main::GetServicePID () const
{
	ifstream	in (_sRep->GetPIDFileName ().AsTString ().c_str ());
	if (in) {
		pid_t	n = 0;
		in >> n;
		return n;
	}
	return 0;
}
#endif

String		Main::GetServiceStatusMessage () const
{
	const	wchar_t	kTAB[]	=	L"    ";	// use spaces instead of tab so formatting independent of tabstop settings
	ServiceDescription	svd	=	GetServiceDescription ();
	wstringstream	tmp;
	tmp << L"Service '" << svd.fName.As<wstring> () << "'" << endl;
	switch (this->GetState ()) {
		case	eStopped:
			tmp << kTAB << L"State:  " << kTAB << kTAB << kTAB << "STOPPED" << endl;
			break;
		case	eRunning:
			tmp << kTAB << L"State:  " << kTAB << kTAB << kTAB << "Running" << endl;
			#if		qPlatform_POSIX
				tmp << kTAB << L"PID:    " << kTAB << kTAB << kTAB << GetServicePID () << endl;
			#endif
			break;
		case	ePaused:
			tmp << kTAB << L"State:  " << kTAB << kTAB << kTAB << "PAUSED" << endl;
			#if		qPlatform_POSIX
				tmp << kTAB << L"PID:    " << kTAB<< kTAB << kTAB << GetServicePID () << endl;
			#endif
			break;
		default:
			AssertNotReached ();
	}
	tmp << _sRep->GetServiceStatusMessage ().As<wstring> ();
	return tmp.str ();
}

void	Main::RunAsService ()
{
	// VERY PRIMITIVE IMPL - WE NEED LOCKING on tmpfile stuff - add good tempfile supprot to fileuitls or use existing...

	try {
#if		qPlatform_POSIX
		ofstream	out (_sRep->GetPIDFileName ().AsTString ().c_str ());
		out << getpid () << endl;
#endif
		_sRep->OnStartRequest ();
	}
	catch (const Execution::ThreadAbortException& /*threadAbort*/) {
#if		qPlatform_POSIX
		unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
		// ignore this - just means service ended normally
	}
	catch (...) {
		DbgTrace (TSTR ("Unexpected exception ended running service"));
#if		qPlatform_POSIX
		unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
		throw;
	}
}

void	Main::Start ()
{
	// Check not already runnig, (someday) and then for and exec the

#if		qPlatform_POSIX
	// REALLY should use GETSTATE - and return state based on if PID file exsits...
	if (GetServicePID ()  != 0) {
		Execution::DoThrow (Execution::StringException (L"Cannot Start service because its already running"));
	}
#endif
	Characters::TString	thisEXEPath	=	Execution::GetEXEPath ();
#if		qPlatform_POSIX
	pid_t	pid	=	fork ();
	if (pid == 0) {
		// Child - exec -
		//		TODO:		SHOULD BE CAREFUL ABOUT CLOSING FILE DESCRIPTORS BEFORE THIS ACTION - WE DONT WANT HTEM INHERITED!!!
		//					BUT DONT DO WILLYNILLY - THINK THROUGH - I CANNNOT RECALL THE EXACT RIGHT ANSWER
		int	r	=	execl (thisEXEPath.c_str (), thisEXEPath.c_str (), (String (L"--") + String (CommandNames::kRunAsService)).AsTString ().c_str (), nullptr);
		exit (-1);
	}
	else if (pid < 0) {
		// failed to fork - serious error
		Execution::errno_ErrorException::DoThrow (errno);
	}
	else {
		// parent - in this case - no reason to wait - our work is done... Future versions might wait to
		// see if the 'pidfile' got created....
		//		--LGP 2011-09-23
	}
#endif
}

void	Main::Stop ()
{
	// Send signal to server to stop
#if		qPlatform_POSIX
	kill (GetServicePID (), SIGTERM);
#endif
}

void	Main::Kill ()
{
	Stop ();
	// Send signal to server to stop
#if		qPlatform_POSIX
	kill (GetServicePID (), SIGKILL);
	// REALY should WAIT for server to stop and only do this it fails -
	unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
}

void	Main::Restart ()
{
	IgnoreExceptionsForCall (Stop ());
#if		qPlatform_POSIX
	// REALY should WAIT for server to stop and only do this it fails -
	unlink (_sRep->GetPIDFileName ().AsTString ().c_str ());
#endif
	Start ();
}

void	Main::ReReadConfiguration ()
{
	// SEND APPROPRIATE SIGNAL
#if		qPlatform_POSIX
	pid_t	pid	=	GetServicePID ();
	Assert (pid != 0);	// maybe throw if non-zero???
	kill (GetServicePID (), kSIG_ReReadConfiguration);
#endif
}

void	Main::Pause ()
{
	AssertNotImplemented ();
}

void	Main::Continue ()
{
	AssertNotImplemented ();
}

Main::ServiceDescription	Main::GetServiceDescription () const
{
	return _sRep->GetServiceDescription ();
}

#if		qPlatform_POSIX
void	Main::SignalHandler (int signum)
{
	_sRep->SignalHandler (signum);
}
#endif

bool	Main::_HandleStandardCommandLineArgument (const String& arg)
{
	if (Execution::MatchesCommandLineArgument (arg, CommandNames::kRunAsService)) {
		RunAsService ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kStart)) {
		Start ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kStop)) {
		Stop ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kKill)) {
		Kill ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kRestart)) {
		Restart ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kReloadConfiguration)) {
		ReReadConfiguration ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kPause)) {
		Pause ();
		return true;
	}
	else if (Execution::MatchesCommandLineArgument (arg, CommandNames::kContinue)) {
		Continue ();
		return true;
	}
	/// MANY more neeeded, and fix to use named constants...
	return false;
}

<|endoftext|>


<commit_before>
#include <qapplication.h>
#include <qpushbutton.h>

int main(int argc, char **argv)
{
  QApplication app( argc, argv );
  QPushButton  bb( "Insight + Qt", 0 );
  bb.resize( 100, 30 );
  app.setMainWidget( &bb );
  bb.show();
  return app.exec();
}
<commit_msg>ENH: ITK and Qt declarations combined.<commit_after>
#include <qapplication.h>
#include <qpushbutton.h>

#include "itkImage.h"
#include "itkImageFileReader.h"
#include "itkDiscreteGaussianImageFilter.h"

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

  typedef itk::Image< float, 2 > ImageType;

  typedef itk::DiscreteGaussianImageFilter<
                    ImageType,
                    ImageType >  FilterType;

  typedef itk::ImageFileReader< ImageType > ReaderType;

  ReaderType::Pointer reader = ReaderType::New();

  FilterType::Pointer filter = FilterType::New();

  filter->SetInput( reader->GetOutput() );

  // Create Qt Application to let Qt get its
  // parameters from the command line
  QApplication app( argc, argv );

  reader->SetFileName( argv[1] );

  QPushButton  bb( "Start", 0 );
  bb.resize( 100, 30 );

//  QObject::connect( &bb, SIGNAL(clicked()), &a, SLOT(quit()) );

  app.setMainWidget( &bb );
  bb.show();

  return app.exec();

}
<|endoftext|>


<commit_before>/******************************************************************************
 * This file is part of the Gluon Development Platform
 * Copyright (c) 2010 Arjen Hiemstra <ahiemstra@heimr.nl>
 * Copyright (c) 2011 Giulio Camuffo <giuliocamuffo@gmail.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

#include "uimanagercomponent.h"

#include <core/debughelper.h>
#include <graphics/item.h>
#include <graphics/engine.h>
#include <graphics/item.h>
#include <graphics/material.h>
#include <graphics/mesh.h>
#include <graphics/rendertarget.h>
#include <graphics/materialinstance.h>
#include <engine/gameobject.h>
#include <engine/asset.h>

#include <QtCore/QMimeData>
#include <QtCore/QVariant>
#include <QtGui/QMatrix4x4>
#include <QtGui/QColor>
#include <QtGui/QGraphicsView>
#include <QtGui/QGraphicsScene>
#include <QtGui/QGraphicsWidget>
#include <QtGui/QPixmap>
#include <QtOpenGL/QGLFramebufferObject>
#include <QtDeclarative/QDeclarativeEngine>
#include <QtDeclarative/QDeclarativeExpression>
#include <QtDeclarative/QDeclarativeContext>
#include <QtDeclarative/qdeclarative.h>
#include <QtScript/QScriptValue>
#include <QtScript/QScriptEngine>
#include <QtScript/QScriptValueIterator>
#include <texture.h>
#include <game.h>

#include "uiasset.h"
#include "engineaccess.h"

REGISTER_OBJECTTYPE( GluonEngine, UiManagerComponent )

using namespace GluonEngine;
using namespace GluonGraphics;

template <typename Tp>
QScriptValue scriptValueFromQObject( QScriptEngine *engine, Tp const& qobject)
{
    return engine->newQObject( qobject );
}

template <typename Tp>
void scriptValueToQObject(const QScriptValue &value, Tp &qobject)
{
    qobject = qobject_cast<Tp>( value.toQObject() );
}

template <typename Tp>
int qScriptRegisterQObjectMetaType( QScriptEngine *engine )
{
    return qScriptRegisterMetaType<Tp>( engine, scriptValueFromQObject, scriptValueToQObject );
}

class UiManagerComponent::UiManagerComponentPrivate
{
    public:
        UiManagerComponentPrivate( UiManagerComponent *component )
            : q(component)
            , scene(0)
            , ui(0)
            , target(0)
            , updateFunction(0)
        {
        }

        void setupBindings( QScriptEngine* engine )
        {
            //FIXME: this code is duplicated with the scripting conponent.
            //It should be moved to a common place.

            engine->importExtension( "jsmoke.qtcore" );
            engine->importExtension( "jsmoke.qtgui" );
            engine->importExtension( "jsmoke.qtopengl" );

            qScriptRegisterQObjectMetaType<GameObject*>( engine );
            qScriptRegisterQObjectMetaType<GluonObject*>( engine );
            qScriptRegisterQObjectMetaType<Component*>( engine );
            qScriptRegisterQObjectMetaType<Asset*>( engine );
            qScriptRegisterQObjectMetaType<Scene*>( engine );
            qScriptRegisterQObjectMetaType<GameProject*>( engine );

            QScriptEngine::QObjectWrapOptions wrapOptions = QScriptEngine::AutoCreateDynamicProperties | QScriptEngine::ExcludeDeleteLater | QScriptEngine::PreferExistingWrapperObject;
            QScriptEngine::ValueOwnership ownership = QScriptEngine::QtOwnership;
            QScriptValue object = engine->globalObject();

            QScriptValue component = engine->newQObject( q, ownership, wrapOptions );
            object.setProperty( "Component", component );

            QScriptValue gameObj = engine->newQObject( q->gameObject(), ownership, wrapOptions );
            object.setProperty( "GameObject", gameObj );

            QScriptValue sceneObj = engine->newQObject( q->gameObject()->scene(), ownership, wrapOptions );
            object.setProperty( "Scene", sceneObj );

            QScriptValue gameProjectObj = engine->newQObject( GluonEngine::Game::instance()->gameProject(), ownership, wrapOptions );
            object.setProperty( "GameProject", gameProjectObj );

            QScriptValue game = engine->newQObject( GluonEngine::Game::instance(), ownership, wrapOptions );
            object.setProperty( "Game", game );
        }

        UiManagerComponent* q;
        QPixmap pixmap;
        QGraphicsView* view;
        QGraphicsScene* scene;
        UiAsset *ui;
        QSizeF size;
        Item *item;
        EngineAccess* engineAccess;
        RenderTarget* target;

        QDeclarativeExpression *updateFunction;
};

UiManagerComponent::UiManagerComponent( QObject* parent )
    : Component( parent )
    , d( new UiManagerComponentPrivate( this ) )
{

}

UiManagerComponent::UiManagerComponent( const UiManagerComponent& other )
    : Component( other )
    , d( other.d )
{
}

UiManagerComponent::~UiManagerComponent()
{
    delete d;
}

QString UiManagerComponent::category() const
{
    return QString( "Graphics Rendering" );
}

void UiManagerComponent::initialize()
{
//     d->fbo = GluonGraphics::Engine::instance()->fbo();
//     d->pixmap = QPixmap( widget->size() );
//     d->pixmap.fill( Qt::transparent );
//     d->view->setParent(widget->parentWidget());
//     d->view->setAttribute(Qt::WA_TranslucentBackground);
//     d->view->setAttribute(Qt::WA_NoSystemBackground);
//     d->view->viewport()->setAttribute(Qt::WA_TranslucentBackground);
//     d->view->viewport()->setAttribute(Qt::WA_NoSystemBackground);
//     d->view->setStyleSheet("border: none");
//     QPalette p = d->view->viewport()->palette();
//     p.setColor(QPalette::Base, Qt::transparent);
//     d->view->viewport()->setPalette(p);
//     d->view->setScene(d->scene);
//     d->view->setSceneRect(QRectF(0,0,1000,1000));

//     d->view->resize(widget->size());
//     d->view->show();
//     d->scene->setBackgroundBrush(Qt::blue);

//     d->texture = widget->bindTexture(d->pixmap);
//     widget->update();
//     widget->updateGL();
//     widget->makeCurrent();

    if( !d->scene )
    {
        d->scene = new QGraphicsScene( this );
        d->scene->setSceneRect(QRectF(QPointF(0,0), QSize(1024,768)));

        d->target = new RenderTarget(1024,768,this);
        d->target->setMaterialInstance(Engine::instance()->material("default")->createInstance("qmlTarget"));
        Engine::instance()->addRenderTarget(d->target, 1);
    }

    if( d->ui && !d->ui->isLoaded() )
    {
        qmlRegisterType<GluonEngine::GameObject>("org.kde.gluon", 1, 0, "GameObject" );
        qmlRegisterInterface<GluonEngine::GameObject>("gameObject");

        d->ui->load();

        QDeclarativeEngine* engine = d->ui->engine();

        d->engineAccess = new EngineAccess(this);
        engine->rootContext()->setContextProperty( "__engineAccess", d->engineAccess );

        //Glorious hack:steal the engine
        QDeclarativeExpression *expr = new QDeclarativeExpression( engine->rootContext(), d->ui->widget(),
                                                                   "__engineAccess.setEngine( this )" );
        expr->evaluate();
        delete expr;
    }

    if( d->ui && d->ui->isLoaded() )
    {
        d->ui->execute();

        QGraphicsWidget* gWidget = d->ui->widget();
        if( gWidget )
        {
            d->scene->addItem( gWidget );

            d->updateFunction = new QDeclarativeExpression( d->ui->engine()->rootContext(),
                                                            d->ui->widget(), "update()" );
        }
    }
}

void UiManagerComponent::setScriptEngine( QScriptValue &value )
{
    QScriptEngine* engine = value.engine();

    QScriptValue originalGlobalObject = engine->globalObject();
    QScriptValue newGlobalObject = engine->newObject();

    QString eval = QLatin1String( "eval" );
    QString version = QLatin1String( "version" );

    QScriptValueIterator iter( originalGlobalObject );
    QVector<QString> names;
    QVector<QScriptValue> values;
    QVector<QScriptValue::PropertyFlags> flags;
    while ( iter.hasNext() )
    {
        iter.next();

        QString name = iter.name();

        if ( name == version )
        {
            continue;
        }

        if ( name != eval )
        {
            names.append( name );
            values.append( iter.value() );
            flags.append( iter.flags() | QScriptValue::Undeletable );
        }
        newGlobalObject.setProperty( iter.scriptName(), iter.value() );
    }

    engine->setGlobalObject( newGlobalObject );

    d->setupBindings( engine );

    delete d->engineAccess;
    d->ui->engine()->rootContext()->setContextProperty( "__engineAccess", 0 );
}

void UiManagerComponent::start()
{

}

void UiManagerComponent::draw( int timeLapse )
{
    Q_UNUSED( timeLapse )

    if( !d->scene || !d->ui || !d->ui->widget() )
    {
        return;
    }

    QPainter p( d->target->framebufferObject() );
    d->scene->render( &p );
}

void UiManagerComponent::update( int elapsedMilliseconds )
{
    if( d->updateFunction )
    {
        d->updateFunction->evaluate();

        if( d->updateFunction->hasError() )
        {
            debug( d->updateFunction->error().toString() );
        }
    }
}

void UiManagerComponent::cleanup()
{
    if( !d->ui )
    {
        return;
    }

    QGraphicsWidget* widget = d->ui->widget();
    if( d->scene && widget && widget->scene() == d->scene )
    {
        d->scene->removeItem( widget );
    }

    delete d->scene;
    d->scene = 0;

    delete d->updateFunction;
    d->updateFunction = 0;

    delete d->target;
    d->target = 0;
}

void UiManagerComponent::setUi(UiAsset* ui)
{
    d->ui = ui;
}

UiAsset* UiManagerComponent::ui() const
{
    return d->ui;
}

void UiManagerComponent::setSize( const QSizeF& size )
{
    d->size = size;
}

QSizeF UiManagerComponent::size() const
{
    return d->size;
}

Q_EXPORT_PLUGIN2( gluon_component_uimanager, GluonEngine::UiManagerComponent );

#include "uimanagercomponent.moc"
<commit_msg>Create a custom fbo and bind it before drawing.<commit_after>/******************************************************************************
 * This file is part of the Gluon Development Platform
 * Copyright (c) 2010 Arjen Hiemstra <ahiemstra@heimr.nl>
 * Copyright (c) 2011 Giulio Camuffo <giuliocamuffo@gmail.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

#include "uimanagercomponent.h"

#include <core/debughelper.h>
#include <graphics/item.h>
#include <graphics/engine.h>
#include <graphics/item.h>
#include <graphics/material.h>
#include <graphics/mesh.h>
#include <graphics/rendertarget.h>
#include <graphics/materialinstance.h>
#include <engine/gameobject.h>
#include <engine/asset.h>

#include <QtCore/QMimeData>
#include <QtCore/QVariant>
#include <QtGui/QMatrix4x4>
#include <QtGui/QColor>
#include <QtGui/QGraphicsView>
#include <QtGui/QGraphicsScene>
#include <QtGui/QGraphicsWidget>
#include <QtGui/QPixmap>
#include <QtOpenGL/QGLFramebufferObject>
#include <QtDeclarative/QDeclarativeEngine>
#include <QtDeclarative/QDeclarativeExpression>
#include <QtDeclarative/QDeclarativeContext>
#include <QtDeclarative/qdeclarative.h>
#include <QtScript/QScriptValue>
#include <QtScript/QScriptEngine>
#include <QtScript/QScriptValueIterator>
#include <texture.h>
#include <game.h>

#include "uiasset.h"
#include "engineaccess.h"

REGISTER_OBJECTTYPE( GluonEngine, UiManagerComponent )

using namespace GluonEngine;
using namespace GluonGraphics;

template <typename Tp>
QScriptValue scriptValueFromQObject( QScriptEngine *engine, Tp const& qobject)
{
    return engine->newQObject( qobject );
}

template <typename Tp>
void scriptValueToQObject(const QScriptValue &value, Tp &qobject)
{
    qobject = qobject_cast<Tp>( value.toQObject() );
}

template <typename Tp>
int qScriptRegisterQObjectMetaType( QScriptEngine *engine )
{
    return qScriptRegisterMetaType<Tp>( engine, scriptValueFromQObject, scriptValueToQObject );
}

class UiManagerComponent::UiManagerComponentPrivate
{
    public:
        UiManagerComponentPrivate( UiManagerComponent *component )
            : q(component)
            , scene(0)
            , ui(0)
            , target(0)
            , updateFunction(0)
        {
        }

        void setupBindings( QScriptEngine* engine )
        {
            //FIXME: this code is duplicated with the scripting conponent.
            //It should be moved to a common place.

            engine->importExtension( "jsmoke.qtcore" );
            engine->importExtension( "jsmoke.qtgui" );
            engine->importExtension( "jsmoke.qtopengl" );

            qScriptRegisterQObjectMetaType<GameObject*>( engine );
            qScriptRegisterQObjectMetaType<GluonObject*>( engine );
            qScriptRegisterQObjectMetaType<Component*>( engine );
            qScriptRegisterQObjectMetaType<Asset*>( engine );
            qScriptRegisterQObjectMetaType<Scene*>( engine );
            qScriptRegisterQObjectMetaType<GameProject*>( engine );

            QScriptEngine::QObjectWrapOptions wrapOptions = QScriptEngine::AutoCreateDynamicProperties | QScriptEngine::ExcludeDeleteLater | QScriptEngine::PreferExistingWrapperObject;
            QScriptEngine::ValueOwnership ownership = QScriptEngine::QtOwnership;
            QScriptValue object = engine->globalObject();

            QScriptValue component = engine->newQObject( q, ownership, wrapOptions );
            object.setProperty( "Component", component );

            QScriptValue gameObj = engine->newQObject( q->gameObject(), ownership, wrapOptions );
            object.setProperty( "GameObject", gameObj );

            QScriptValue sceneObj = engine->newQObject( q->gameObject()->scene(), ownership, wrapOptions );
            object.setProperty( "Scene", sceneObj );

            QScriptValue gameProjectObj = engine->newQObject( GluonEngine::Game::instance()->gameProject(), ownership, wrapOptions );
            object.setProperty( "GameProject", gameProjectObj );

            QScriptValue game = engine->newQObject( GluonEngine::Game::instance(), ownership, wrapOptions );
            object.setProperty( "Game", game );
        }

        UiManagerComponent* q;
        QPixmap pixmap;
        QGraphicsView* view;
        QGraphicsScene* scene;
        UiAsset *ui;
        QSizeF size;
        Item *item;
        EngineAccess* engineAccess;
        RenderTarget* target;

        QDeclarativeExpression *updateFunction;
};

UiManagerComponent::UiManagerComponent( QObject* parent )
    : Component( parent )
    , d( new UiManagerComponentPrivate( this ) )
{

}

UiManagerComponent::UiManagerComponent( const UiManagerComponent& other )
    : Component( other )
    , d( other.d )
{
}

UiManagerComponent::~UiManagerComponent()
{
    delete d;
}

QString UiManagerComponent::category() const
{
    return QString( "Graphics Rendering" );
}

void UiManagerComponent::initialize()
{
//     d->fbo = GluonGraphics::Engine::instance()->fbo();
//     d->pixmap = QPixmap( widget->size() );
//     d->pixmap.fill( Qt::transparent );
//     d->view->setParent(widget->parentWidget());
//     d->view->setAttribute(Qt::WA_TranslucentBackground);
//     d->view->setAttribute(Qt::WA_NoSystemBackground);
//     d->view->viewport()->setAttribute(Qt::WA_TranslucentBackground);
//     d->view->viewport()->setAttribute(Qt::WA_NoSystemBackground);
//     d->view->setStyleSheet("border: none");
//     QPalette p = d->view->viewport()->palette();
//     p.setColor(QPalette::Base, Qt::transparent);
//     d->view->viewport()->setPalette(p);
//     d->view->setScene(d->scene);
//     d->view->setSceneRect(QRectF(0,0,1000,1000));

//     d->view->resize(widget->size());
//     d->view->show();
//     d->scene->setBackgroundBrush(Qt::blue);

//     d->texture = widget->bindTexture(d->pixmap);
//     widget->update();
//     widget->updateGL();
//     widget->makeCurrent();

    if( !d->scene )
    {
        d->scene = new QGraphicsScene( this );
        d->scene->setSceneRect(QRectF(QPointF(0,0), QSize(1024,768)));

        d->target = new RenderTarget(this);
        d->target->setFramebufferObject(new QGLFramebufferObject(1024, 512, QGLFramebufferObject::CombinedDepthStencil));
        d->target->setMaterialInstance(Engine::instance()->material("default")->createInstance("qmlTarget"));
        Engine::instance()->addRenderTarget(d->target, 1);
    }

    if( d->ui && !d->ui->isLoaded() )
    {
        qmlRegisterType<GluonEngine::GameObject>("org.kde.gluon", 1, 0, "GameObject" );
        qmlRegisterInterface<GluonEngine::GameObject>("gameObject");

        d->ui->load();

        QDeclarativeEngine* engine = d->ui->engine();

        d->engineAccess = new EngineAccess(this);
        engine->rootContext()->setContextProperty( "__engineAccess", d->engineAccess );

        //Glorious hack:steal the engine
        QDeclarativeExpression *expr = new QDeclarativeExpression( engine->rootContext(), d->ui->widget(),
                                                                   "__engineAccess.setEngine( this )" );
        expr->evaluate();
        delete expr;
    }

    if( d->ui && d->ui->isLoaded() )
    {
        d->ui->execute();

        QGraphicsWidget* gWidget = d->ui->widget();
        if( gWidget )
        {
            d->scene->addItem( gWidget );

            d->updateFunction = new QDeclarativeExpression( d->ui->engine()->rootContext(),
                                                            d->ui->widget(), "update()" );
        }
    }
}

void UiManagerComponent::setScriptEngine( QScriptValue &value )
{
    QScriptEngine* engine = value.engine();

    QScriptValue originalGlobalObject = engine->globalObject();
    QScriptValue newGlobalObject = engine->newObject();

    QString eval = QLatin1String( "eval" );
    QString version = QLatin1String( "version" );

    QScriptValueIterator iter( originalGlobalObject );
    QVector<QString> names;
    QVector<QScriptValue> values;
    QVector<QScriptValue::PropertyFlags> flags;
    while ( iter.hasNext() )
    {
        iter.next();

        QString name = iter.name();

        if ( name == version )
        {
            continue;
        }

        if ( name != eval )
        {
            names.append( name );
            values.append( iter.value() );
            flags.append( iter.flags() | QScriptValue::Undeletable );
        }
        newGlobalObject.setProperty( iter.scriptName(), iter.value() );
    }

    engine->setGlobalObject( newGlobalObject );

    d->setupBindings( engine );

    delete d->engineAccess;
    d->ui->engine()->rootContext()->setContextProperty( "__engineAccess", 0 );
}

void UiManagerComponent::start()
{

}

void UiManagerComponent::draw( int timeLapse )
{
    Q_UNUSED( timeLapse )

    if( !d->scene || !d->ui || !d->ui->widget() )
    {
        return;
    }

    d->target->bind();

    QPainter p( d->target->framebufferObject() );
    d->scene->render( &p );
    p.end();

    d->target->release();
}

void UiManagerComponent::update( int elapsedMilliseconds )
{
    if( d->updateFunction )
    {
        d->updateFunction->evaluate();

        if( d->updateFunction->hasError() )
        {
            debug( d->updateFunction->error().toString() );
        }
    }
}

void UiManagerComponent::cleanup()
{
    if( !d->ui )
    {
        return;
    }

    QGraphicsWidget* widget = d->ui->widget();
    if( d->scene && widget && widget->scene() == d->scene )
    {
        d->scene->removeItem( widget );
    }

    delete d->scene;
    d->scene = 0;

    delete d->updateFunction;
    d->updateFunction = 0;

    delete d->target;
    d->target = 0;
}

void UiManagerComponent::setUi(UiAsset* ui)
{
    d->ui = ui;
}

UiAsset* UiManagerComponent::ui() const
{
    return d->ui;
}

void UiManagerComponent::setSize( const QSizeF& size )
{
    d->size = size;
}

QSizeF UiManagerComponent::size() const
{
    return d->size;
}

Q_EXPORT_PLUGIN2( gluon_component_uimanager, GluonEngine::UiManagerComponent );

#include "uimanagercomponent.moc"
<|endoftext|>


<commit_before>#include "compress_keyword_encoding.h"
#include "bytebuffer.h"

#include <stdexcept>
#include <sstream>
#include <map>
#include <unordered_map>

#include <iostream>

std::string initializeSymbols()
{
    std::string s;
    for(int i = 1; i < 255; ++i)
        s += i;

    return s;
}

bool CompressKeywordEncoding::CompressImpl(const ByteBuffer& input, ByteBuffer& output)
{
    std::string symbols = initializeSymbols();

    const char * inChars = (const char *)input.Data();

    size_t symIndex;
    char c;
    for (size_t i=0; i < input.Size(); ++i)
    {
        c = inChars[i];

        if ((symIndex = symbols.find(c)) != std::string::npos)
            symbols.erase(symbols.begin() + symIndex);
    }

    std::map<std::string, unsigned int>::iterator it;
    std::map<std::string, unsigned int> stringFrequencies;

    std::istringstream in((char *)input.Data());
    std::string temp;
    while (in.good())
    {
        in >> temp;
        it = stringFrequencies.find(temp);

        if (it != stringFrequencies.end())
            ++it->second;
        else
            stringFrequencies.insert(it, std::make_pair(temp, 1));
    }

    std::map<unsigned int, std::vector<std::string>> reverseStringFrequencies;
    std::map<unsigned int, std::vector<std::string>>::iterator it1;

    for (const auto& elem: stringFrequencies)
    {
        it1 = reverseStringFrequencies.find(elem.second);
        if (it1 == reverseStringFrequencies.end())
            it1 = reverseStringFrequencies.insert(it1, std::make_pair(elem.second, std::vector<std::string>()));

        it1->second.push_back(elem.first);
    }

    std::unordered_map<std::string, char> encodedStrings;
    std::unordered_map<std::string, char>::iterator encodedStringsIt;

    std::map<unsigned int, std::vector<std::string>>::reverse_iterator it2 = reverseStringFrequencies.rbegin();
    for (size_t i = 0; i < symbols.size() && it2 != reverseStringFrequencies.rend(); ++it2)
    {
        for (size_t j = 0; j < it2->second.size() && i < symbols.size(); ++j)
        {
            if ((it2->second[j].size() > 2 /* min word size */ && it2->first > 1 /* min freq */) ||
                (it2->second[j].size() > 1 /* min word size */ && it2->first > 2 /* min freq */))
            {
                encodedStrings.insert(std::make_pair(it2->second[j], symbols[i++]));
                std::cout << it2->second[j] << std::endl;
            }
        }
    }

    output.WriteDynInt(encodedStrings.size());
    for(encodedStringsIt = encodedStrings.begin(); encodedStringsIt != encodedStrings.end(); ++encodedStringsIt)
    {
        output.WriteUInt8(encodedStringsIt->second);
        output.WriteString(encodedStringsIt->first);
    }

    in = std::istringstream(std::string((const char *)input.Data(), input.Size()));

    std::string str = in.str();

    std::ostringstream out;

    while (in.good())
    {
        std::streamoff prev = in.tellg();
        in >> temp;
        std::streamoff after = in.tellg();

        if ((encodedStringsIt = encodedStrings.find(temp)) != encodedStrings.end())
            output.WriteString(std::string(1, encodedStringsIt->second));
        else
            output.WriteString(temp);

        std::string str2;
        if (after != -1)
            output.WriteString((str2 = str.substr(prev, after - prev - temp.size())));
        else
            output.WriteString(str.substr(prev, input.Size() - prev - str2.size()));
    }

    return true;
}

bool CompressKeywordEncoding::DecompressImpl(const ByteBuffer& input, ByteBuffer& output)
{
    ByteBuffer* hack = const_cast<ByteBuffer*>(&input);

    std::unordered_map<char, std::string> encodedSymbols;
    std::unordered_map<char, std::string>::iterator encodedSymbolsIt;

    size_t numTableEntries = hack->ReadDynInt();
    for(; numTableEntries > 0; --numTableEntries)
        encodedSymbols.insert(std::make_pair((char)hack->ReadUInt8(), hack->ReadString()));

    std::stringstream ss;

    std::string temp, spaces;
    while (hack->CanRead())
    {
        temp = hack->ReadString();
        spaces = hack->ReadString();

        if (hack->CanRead())
        {
            ss << spaces;

            if (temp.size() > 0 && (encodedSymbolsIt = encodedSymbols.find(temp[0])) != encodedSymbols.end())
                ss << encodedSymbolsIt->second;
            else
                ss << temp;
        }

        if (!hack->CanRead()) // last iter
            ss << spaces;
    };

    std::string r = ss.str();
    output.WriteBuffer(r.c_str(), r.size());
    //output.WriteUInt8(0);

    return true;
}
<commit_msg>Keyword encoding is now properly compressing however it's slow as shit.<commit_after>#include "compress_keyword_encoding.h"
#include "bytebuffer.h"

#include <stdexcept>
#include <sstream>
#include <map>
#include <unordered_map>

#include <iostream>
#include <regex>
#include <cctype>
#include <algorithm>

#include "utils.h"

std::vector<uint8> InitializeSymbols()
{
    std::vector<uint8> vec;
    for (uint8 i = 0; i < 255; ++i)
        if (std::isprint(i) && i != '$') // $ is used by regex replace
            vec.push_back(i);

    return vec;
}

bool CompressKeywordEncoding::CompressImpl(const ByteBuffer& input, ByteBuffer& output)
{

    // regex is used to match words and build frequency map

    std::cmatch sm;
    std::regex e("\\b\\S+\\b"); // word

    dict<std::string, unsigned int>::type_unordered_map stringFrequencies;
    dict<std::string, unsigned int>::init(stringFrequencies, "");

    {
        std::string str((const char*)input.Data(), input.Size());
        while (std::regex_search(str.c_str(), sm, e))
        {
            for (auto x : sm)
                stringFrequencies[x.str()]++;
            str = sm.suffix().str();
        }
    }

    // remove used symbols

    std::vector<uint8> symbols = InitializeSymbols();
    for (size_t i = 0; i < input.Size(); ++i)
        std::remove(symbols.begin(), symbols.end(), input.Data()[i]);

    if (symbols.empty())
        std::cerr << "Empty symbols!!" << std::endl;

    // invert frequency map, key by frequency

    std::map<unsigned int, std::vector<std::string>> reverseStringFrequencies;
    std::map<unsigned int, std::vector<std::string>>::iterator it1;

    for (const auto& elem: stringFrequencies)
    {
        it1 = reverseStringFrequencies.find(elem.second);
        if (it1 == reverseStringFrequencies.end())
            it1 = reverseStringFrequencies.insert(it1, std::make_pair(elem.second, std::vector<std::string>()));

        it1->second.push_back(elem.first);
    }

    // pick symbols for common words

    std::unordered_map<std::string, uint8> encodedStrings;
    std::unordered_map<std::string, uint8>::iterator encodedStringsIt;
    std::map<unsigned int, std::vector<std::string>>::reverse_iterator it2 = reverseStringFrequencies.rbegin();
    for (size_t i = 0; i < symbols.size() && it2 != reverseStringFrequencies.rend(); ++it2)
    {
        for (size_t j = 0; j < it2->second.size() && i < symbols.size(); ++j)
        {
            //if ((it2->second[j].size() > 2 /* min word size */ && it2->first > 1 /* min freq */) ||
            //    (it2->second[j].size() > 1 /* min word size */ && it2->first > 2 /* min freq */))
            {
                encodedStrings.insert(std::make_pair(it2->second[j], symbols[i++]));
            }
        }
    }

    // write symbol - word map

    output.WriteDynInt(encodedStrings.size());
    for (encodedStringsIt = encodedStrings.begin(); encodedStringsIt != encodedStrings.end(); ++encodedStringsIt)
    {
        output.WriteUInt8(encodedStringsIt->second);
        output.WriteString(encodedStringsIt->first);
    }

    // modify and write text

    {
        std::string str((const char*)input.Data(), input.Size());

        for (std::unordered_map<std::string, uint8>::value_type p : encodedStrings)
        {
            std::regex rx("\\b" + p.first + "\\b");
            str = std::regex_replace(str, rx, std::string(1, p.second));
        }

        output.WriteBuffer(str.data(), str.size());
    }

    return true;
}

bool CompressKeywordEncoding::DecompressImpl(const ByteBuffer& input, ByteBuffer& output)
{
    ByteBuffer* hack = const_cast<ByteBuffer*>(&input);

    std::unordered_map<uint8, std::string> encodedSymbols; // symbol -> word

    size_t numTableEntries = hack->ReadDynInt();
    for(; numTableEntries > 0; --numTableEntries)
    {
        uint8 c = hack->ReadUInt8();
        std::string str = hack->ReadString();
        encodedSymbols[c] = str;
    }

    std::string str(&(*((const char *)input.Data() + hack->GetReadPos())), input.Size() - hack->GetReadPos());

    std::unordered_map<uint8, std::string>::const_iterator itr;
    while (hack->CanRead())
    {
        uint8 c = hack->ReadUInt8();

        itr = encodedSymbols.find(c);
        if (itr != encodedSymbols.end())
            output.WriteBuffer(itr->second.data(), itr->second.size());
        else
            output.WriteUInt8(c);
    }

    return true;
}
<|endoftext|>


<commit_before>#include <iostream> // cout
#include <fstream> // ifstream
#include <sstream> // istringstream
#include <math.h> // log;exp
#include <vector> // vector
#include <algorithm> // for_each
using namespace std;

int main(int argc, char* argv[]){
    string str, a,b,c; // define variables and constants.
    int i=0, loc;
    double val1=1.0, val2=1.0, val, logval1=0, logval2=0;
    const double valMax = 1e64;
    vector<int> vectorSeqNo1,vectorSeqNo2,vectorLoc1,vectorLoc2;
    vector<double> vectorVal1, vectorVal2;

    ifstream file(argv[1]); // open file. Filename as argument of main.

    // loop over lines in file until end-of-file.
    while (getline(file,str)){
      if (str[0]=='#'||str.empty()){;}else{ // check if line should be ignored, if first char is '#' or empty line.
	istringstream ss(str); // get columns.
	ss >> a >> b >> c; // split columns at spaces. Does not handle cases with spaces in SeqNo.
	val = stod(c);
	if ((any_of(b.begin(),b.end(),::isdigit)) && (!isnan(val))){ // error handling. loc must be digit, and nan values are not allowed.
	  loc = stoi(b);
	  if(loc==1){ // create data array corresponding to loc=1.
	    vectorSeqNo1.push_back(stoi(a));  // storing SeqNo to have data structure of file... Not sure if necessary.
	    vectorLoc1.push_back(loc); // store Loc for loc count.
	    vectorVal1.push_back(val); // store Values for GeoMean calculations.
	  }
	  else if (loc==2){ // create data array corresponding to loc=2. Same as in loc=1.
	    vectorSeqNo2.push_back(stoi(a));
	    vectorLoc2.push_back(loc);
	    vectorVal2.push_back(val);
	  }
	  //else{if(!isnan(val)){cout<<"str: "<<str<<"      b:"<<b<<" c: "<<c<<endl;}} //show the exceptions that were not handled.
	}
      }
      loc=0; i++; // update counter for line count, and reset location for lines skipped.
    }

    // loop through vector containing values. Calculate GeoMean.
    for_each(vectorVal1.begin(), vectorVal1.end(), [&] (double val){
      val1 *= val; // multiply the values of the vector until close-to-overflow,
      if (val1 > valMax){logval1+=log(val1);val1=1.0;} // then log it and add onto logval.
    });

   // same as in for loc=1.
    for_each(vectorVal2.begin(), vectorVal2.end(), [&] (double val){
      val2 *= val;
      if (val2 > valMax){logval2+=log(val2);val2=1.0;}
    });

   // output results.
    cout << "File: " << argv[1] << " with " <<  i << " lines" << endl;
    cout << "Valid values Loc1: " << vectorLoc1.size() << " with GeoMean: " << exp((logval1+log(val1))/vectorLoc1.size()) << endl;
    cout << "Valid values Loc2: " << vectorLoc2.size() << " with GeoMean: " << exp((logval2+log(val2))/vectorLoc2.size()) << endl;
    return 0;
}<commit_msg>no newline at end of file?<commit_after>#include <iostream> // cout
#include <fstream> // ifstream
#include <sstream> // istringstream
#include <math.h> // log;exp
#include <vector> // vector
#include <algorithm> // for_each
using namespace std;

int main(int argc, char* argv[]){
    string str, a,b,c; // define variables and constants.
    int i=0, loc;
    double val1=1.0, val2=1.0, val, logval1=0, logval2=0;
    const double valMax = 1e64;
    vector<int> vectorSeqNo1,vectorSeqNo2,vectorLoc1,vectorLoc2;
    vector<double> vectorVal1, vectorVal2;

    ifstream file(argv[1]); // open file. Filename as argument of main.

    // loop over lines in file until end-of-file.
    while (getline(file,str)){
      if (str[0]=='#'||str.empty()){;}else{ // check if line should be ignored, if first char is '#' or empty line.
	istringstream ss(str); // get columns.
	ss >> a >> b >> c; // split columns at spaces. Does not handle cases with spaces in SeqNo.
	val = stod(c);
	if ((any_of(b.begin(),b.end(),::isdigit)) && (!isnan(val))){ // error handling. loc must be digit, and nan values are not allowed.
	  loc = stoi(b);
	  if(loc==1){ // create data array corresponding to loc=1.
	    vectorSeqNo1.push_back(stoi(a));  // storing SeqNo to have data structure of file... Not sure if necessary.
	    vectorLoc1.push_back(loc); // store Loc for loc count.
	    vectorVal1.push_back(val); // store Values for GeoMean calculations.
	  }
	  else if (loc==2){ // create data array corresponding to loc=2. Same as in loc=1.
	    vectorSeqNo2.push_back(stoi(a));
	    vectorLoc2.push_back(loc);
	    vectorVal2.push_back(val);
	  }
	  //else{if(!isnan(val)){cout<<"str: "<<str<<"      b:"<<b<<" c: "<<c<<endl;}} //show the exceptions that were not handled.
	}
      }
      loc=0; i++; // update counter for line count, and reset location for lines skipped.
    }

    // loop through vector containing values. Calculate GeoMean.
    for_each(vectorVal1.begin(), vectorVal1.end(), [&] (double val){
      val1 *= val; // multiply the values of the vector until close-to-overflow,
      if (val1 > valMax){logval1+=log(val1);val1=1.0;} // then log it and add onto logval.
    });

   // same as in for loc=1.
    for_each(vectorVal2.begin(), vectorVal2.end(), [&] (double val){
      val2 *= val;
      if (val2 > valMax){logval2+=log(val2);val2=1.0;}
    });

   // output results.
    cout << "File: " << argv[1] << " with " <<  i << " lines" << endl;
    cout << "Valid values Loc1: " << vectorLoc1.size() << " with GeoMean: " << exp((logval1+log(val1))/vectorLoc1.size()) << endl;
    cout << "Valid values Loc2: " << vectorLoc2.size() << " with GeoMean: " << exp((logval2+log(val2))/vectorLoc2.size()) << endl;
    return 0;
}

<|endoftext|>


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

Copyright (c) 2000-2013 Torus Knot Software Ltd

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

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

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

namespace Ogre {

	//---------------------------------------------------------------------
    GLHardwareVertexBuffer::GLHardwareVertexBuffer(HardwareBufferManagerBase* mgr, size_t vertexSize,
        size_t numVertices, HardwareBuffer::Usage usage, bool useShadowBuffer)
        : HardwareVertexBuffer(mgr, vertexSize, numVertices, usage, false, useShadowBuffer)
    {
        glGenBuffersARB( 1, &mBufferId );

        if (!mBufferId)
        {
            OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
                "Cannot create GL vertex buffer",
                "GLHardwareVertexBuffer::GLHardwareVertexBuffer");
        }

        static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

        // Initialise mapped buffer and set usage
        glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
            GLHardwareBufferManager::getGLUsage(usage));

        //std::cerr << "creating vertex buffer = " << mBufferId << std::endl;
    }
	//---------------------------------------------------------------------
    GLHardwareVertexBuffer::~GLHardwareVertexBuffer()
    {
        static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->deleteGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);
    }
	//---------------------------------------------------------------------
    void* GLHardwareVertexBuffer::lockImpl(size_t offset,
        size_t length, LockOptions options)
    {
        if(mIsLocked)
        {
            OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
                "Invalid attempt to lock an vertex buffer that has already been locked",
                "GLHardwareVertexBuffer::lock");
        }

		void* retPtr = 0;

		GLHardwareBufferManager* glBufManager = static_cast<GLHardwareBufferManager*>(HardwareBufferManager::getSingletonPtr());

		// Try to use scratch buffers for smaller buffers
		if( length < glBufManager->getGLMapBufferThreshold() )
		{
			// if this fails, we fall back on mapping
			retPtr = glBufManager->allocateScratch((uint32)length);

			if (retPtr)
			{
				mLockedToScratch = true;
				mScratchOffset = offset;
				mScratchSize = length;
				mScratchPtr = retPtr;
				mScratchUploadOnUnlock = (options != HBL_READ_ONLY);

				if (options != HBL_DISCARD && options != HBL_NO_OVERWRITE)
				{
					// have to read back the data before returning the pointer
					readData(offset, length, retPtr);
				}
			}
		}

		if (!retPtr)
		{
            GLenum access = 0;
			// Use glMapBuffer
            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);
			// Use glMapBuffer
			if(options == HBL_DISCARD || options == HBL_NO_OVERWRITE) // TODO: check possibility to use GL_MAP_UNSYNCHRONIZED_BIT for HBL_NO_OVERWRITE locking promise
			{
				// Discard the buffer
				glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
					GLHardwareBufferManager::getGLUsage(mUsage));
			}
			if (mUsage & HBU_WRITE_ONLY)
				access = GL_WRITE_ONLY_ARB;
			else if (options == HBL_READ_ONLY)
				access = GL_READ_ONLY_ARB;
			else
				access = GL_READ_WRITE_ARB;

			void* pBuffer = glMapBufferARB( GL_ARRAY_BUFFER_ARB, access);
            if(pBuffer == 0)
			{
				OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
					"Vertex Buffer: Out of memory", "GLHardwareVertexBuffer::lock");
			}

			// return offsetted
			retPtr = static_cast<void*>(
				static_cast<unsigned char*>(pBuffer) + offset);

			mLockedToScratch = false;
		}
		mIsLocked = true;
		return retPtr;
    }
	//---------------------------------------------------------------------
	void GLHardwareVertexBuffer::unlockImpl(void)
    {
		if (mLockedToScratch)
		{
			if (mScratchUploadOnUnlock)
			{
				// have to write the data back to vertex buffer
				writeData(mScratchOffset, mScratchSize, mScratchPtr,
					mScratchOffset == 0 && mScratchSize == getSizeInBytes());
			}

			// deallocate from scratch buffer
			static_cast<GLHardwareBufferManager*>(
				HardwareBufferManager::getSingletonPtr())->deallocateScratch(mScratchPtr);

			mLockedToScratch = false;
		}
		else
		{
            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

			if(!glUnmapBufferARB( GL_ARRAY_BUFFER_ARB ))
			{
				OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
					"Buffer data corrupted, please reload",
					"GLHardwareVertexBuffer::unlock");
			}
		}

        mIsLocked = false;
    }
	//---------------------------------------------------------------------
    void GLHardwareVertexBuffer::readData(size_t offset, size_t length,
        void* pDest)
    {
        if(mUseShadowBuffer)
        {
            // get data from the shadow buffer
            void* srcData = mShadowBuffer->lock(offset, length, HBL_READ_ONLY);
            memcpy(pDest, srcData, length);
            mShadowBuffer->unlock();
        }
        else
        {
            // get data from the real buffer
            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

            glGetBufferSubDataARB(GL_ARRAY_BUFFER_ARB, offset, length, pDest);
        }
    }
	//---------------------------------------------------------------------
    void GLHardwareVertexBuffer::writeData(size_t offset, size_t length,
            const void* pSource, bool discardWholeBuffer)
    {
        static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

        // Update the shadow buffer
        if(mUseShadowBuffer)
        {
            void* destData = mShadowBuffer->lock(offset, length,
                discardWholeBuffer ? HBL_DISCARD : HBL_NORMAL);
            memcpy(destData, pSource, length);
            mShadowBuffer->unlock();
        }

        if (offset == 0 && length == mSizeInBytes)
        {
            glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, pSource,
                GLHardwareBufferManager::getGLUsage(mUsage));
        }
        else
        {
            if(discardWholeBuffer)
            {
                glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
                    GLHardwareBufferManager::getGLUsage(mUsage));
            }

            // Now update the real buffer
            glBufferSubDataARB(GL_ARRAY_BUFFER_ARB, offset, length, pSource);
        }
    }
	//---------------------------------------------------------------------
    void GLHardwareVertexBuffer::_updateFromShadow(void)
    {
        if (mUseShadowBuffer && mShadowUpdated && !mSuppressHardwareUpdate)
        {
            const void *srcData = mShadowBuffer->lock(
                mLockStart, mLockSize, HBL_READ_ONLY);

            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

            // Update whole buffer if possible, otherwise normal
            if (mLockStart == 0 && mLockSize == mSizeInBytes)
            {
                glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, srcData,
                    GLHardwareBufferManager::getGLUsage(mUsage));
            }
            else
            {
                glBufferSubDataARB(GL_ARRAY_BUFFER_ARB, mLockStart, mLockSize, srcData);
            }

            mShadowBuffer->unlock();
            mShadowUpdated = false;
        }
    }
}
<commit_msg>Recover GLHardwareVertexBuffer if glBufferDataARB fails (happens on OSX Mavericks)<commit_after>/*
-----------------------------------------------------------------------------
This source file is part of OGRE
    (Object-oriented Graphics Rendering Engine)
For the latest info, see http://www.ogre3d.org/

Copyright (c) 2000-2013 Torus Knot Software Ltd

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

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

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

namespace Ogre {

	//---------------------------------------------------------------------
    GLHardwareVertexBuffer::GLHardwareVertexBuffer(HardwareBufferManagerBase* mgr, size_t vertexSize,
        size_t numVertices, HardwareBuffer::Usage usage, bool useShadowBuffer)
        : HardwareVertexBuffer(mgr, vertexSize, numVertices, usage, false, useShadowBuffer)
    {
        glGenBuffersARB( 1, &mBufferId );

        if (!mBufferId)
        {
            OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
                "Cannot create GL vertex buffer",
                "GLHardwareVertexBuffer::GLHardwareVertexBuffer");
        }

        static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

        // Initialise mapped buffer and set usage
        glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
            GLHardwareBufferManager::getGLUsage(usage));

        //std::cerr << "creating vertex buffer = " << mBufferId << std::endl;
    }
	//---------------------------------------------------------------------
    GLHardwareVertexBuffer::~GLHardwareVertexBuffer()
    {
        static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->deleteGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);
    }
	//---------------------------------------------------------------------
    void* GLHardwareVertexBuffer::lockImpl(size_t offset,
        size_t length, LockOptions options)
    {
        if(mIsLocked)
        {
            OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
                "Invalid attempt to lock an vertex buffer that has already been locked",
                "GLHardwareVertexBuffer::lock");
        }

		void* retPtr = 0;

		GLHardwareBufferManager* glBufManager = static_cast<GLHardwareBufferManager*>(HardwareBufferManager::getSingletonPtr());

		// Try to use scratch buffers for smaller buffers
		if( length < glBufManager->getGLMapBufferThreshold() )
		{
			// if this fails, we fall back on mapping
			retPtr = glBufManager->allocateScratch((uint32)length);

			if (retPtr)
			{
				mLockedToScratch = true;
				mScratchOffset = offset;
				mScratchSize = length;
				mScratchPtr = retPtr;
				mScratchUploadOnUnlock = (options != HBL_READ_ONLY);

				if (options != HBL_DISCARD && options != HBL_NO_OVERWRITE)
				{
					// have to read back the data before returning the pointer
					readData(offset, length, retPtr);
				}
			}
		}

		if (!retPtr)
		{
            GLenum access = 0;
			// Use glMapBuffer
            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);
			// Use glMapBuffer
			if(options == HBL_DISCARD || options == HBL_NO_OVERWRITE) // TODO: check possibility to use GL_MAP_UNSYNCHRONIZED_BIT for HBL_NO_OVERWRITE locking promise
			{
				// Discard the buffer
				glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
					GLHardwareBufferManager::getGLUsage(mUsage));

                GLenum error = glGetError();
                if(error != 0)
                {
                    String glErrDesc;
                    const char* glerrStr = (const char*)gluErrorString(error);
                    if (glerrStr)
                        glErrDesc = glerrStr;

                    LogManager::getSingleton().logMessage("GLHardwareVertexBuffer::lock - Error: failed to Discard the buffer. Try to recreate the buffer", LML_CRITICAL);

                    static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->deleteGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);
                    mBufferId = 0;

                    glGenBuffersARB( 1, &mBufferId );

                    static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

                    glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
                                    GLHardwareBufferManager::getGLUsage(mUsage));
                }
			}

			if (mUsage & HBU_WRITE_ONLY)
				access = GL_WRITE_ONLY_ARB;
			else if (options == HBL_READ_ONLY)
				access = GL_READ_ONLY_ARB;
			else
				access = GL_READ_WRITE_ARB;

			void* pBuffer = glMapBufferARB( GL_ARRAY_BUFFER_ARB, access);
            if(pBuffer == 0)
			{
				OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
					"Vertex Buffer: Out of memory", "GLHardwareVertexBuffer::lock");
			}

			// return offsetted
			retPtr = static_cast<void*>(
				static_cast<unsigned char*>(pBuffer) + offset);

			mLockedToScratch = false;
		}
		mIsLocked = true;
		return retPtr;
    }
	//---------------------------------------------------------------------
	void GLHardwareVertexBuffer::unlockImpl(void)
    {
		if (mLockedToScratch)
		{
			if (mScratchUploadOnUnlock)
			{
				// have to write the data back to vertex buffer
				writeData(mScratchOffset, mScratchSize, mScratchPtr,
					mScratchOffset == 0 && mScratchSize == getSizeInBytes());
			}

			// deallocate from scratch buffer
			static_cast<GLHardwareBufferManager*>(
				HardwareBufferManager::getSingletonPtr())->deallocateScratch(mScratchPtr);

			mLockedToScratch = false;
		}
		else
		{
            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

			if(!glUnmapBufferARB( GL_ARRAY_BUFFER_ARB ))
			{
				OGRE_EXCEPT(Exception::ERR_INTERNAL_ERROR,
					"Buffer data corrupted, please reload",
					"GLHardwareVertexBuffer::unlock");
			}
		}

        mIsLocked = false;
    }
	//---------------------------------------------------------------------
    void GLHardwareVertexBuffer::readData(size_t offset, size_t length,
        void* pDest)
    {
        if(mUseShadowBuffer)
        {
            // get data from the shadow buffer
            void* srcData = mShadowBuffer->lock(offset, length, HBL_READ_ONLY);
            memcpy(pDest, srcData, length);
            mShadowBuffer->unlock();
        }
        else
        {
            // get data from the real buffer
            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

            glGetBufferSubDataARB(GL_ARRAY_BUFFER_ARB, offset, length, pDest);
        }
    }
	//---------------------------------------------------------------------
    void GLHardwareVertexBuffer::writeData(size_t offset, size_t length,
            const void* pSource, bool discardWholeBuffer)
    {
        static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

        // Update the shadow buffer
        if(mUseShadowBuffer)
        {
            void* destData = mShadowBuffer->lock(offset, length,
                discardWholeBuffer ? HBL_DISCARD : HBL_NORMAL);
            memcpy(destData, pSource, length);
            mShadowBuffer->unlock();
        }

        if (offset == 0 && length == mSizeInBytes)
        {
            glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, pSource,
                GLHardwareBufferManager::getGLUsage(mUsage));
        }
        else
        {
            if(discardWholeBuffer)
            {
                glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, NULL,
                    GLHardwareBufferManager::getGLUsage(mUsage));
            }

            // Now update the real buffer
            glBufferSubDataARB(GL_ARRAY_BUFFER_ARB, offset, length, pSource);
        }
    }
	//---------------------------------------------------------------------
    void GLHardwareVertexBuffer::_updateFromShadow(void)
    {
        if (mUseShadowBuffer && mShadowUpdated && !mSuppressHardwareUpdate)
        {
            const void *srcData = mShadowBuffer->lock(
                mLockStart, mLockSize, HBL_READ_ONLY);

            static_cast<GLHardwareBufferManagerBase*>(mMgr)->getStateCacheManager()->bindGLBuffer(GL_ARRAY_BUFFER_ARB, mBufferId);

            // Update whole buffer if possible, otherwise normal
            if (mLockStart == 0 && mLockSize == mSizeInBytes)
            {
                glBufferDataARB(GL_ARRAY_BUFFER_ARB, mSizeInBytes, srcData,
                    GLHardwareBufferManager::getGLUsage(mUsage));
            }
            else
            {
                glBufferSubDataARB(GL_ARRAY_BUFFER_ARB, mLockStart, mLockSize, srcData);
            }

            mShadowBuffer->unlock();
            mShadowUpdated = false;
        }
    }
}
<|endoftext|>


<commit_before>#include "../Simulator/Simulator.h"
#include "../Models/FourLayerVisionSpikingModel.h"

#include "../SpikeAnalyser/SpikeAnalyser.h"
#include "../Helpers/TimerWithMessages.h"
#include "../Helpers/TerminalHelpers.h"

// Use the following line to compile the binary
// make FILE='JITest' EXPERIMENT_DIRECTORY='Experiments'  model -j8

// The function which will autorun when the executable is created
int main (int argc, char *argv[]){

	TimerWithMessages * experiment_timer = new TimerWithMessages();

	// Simulator Parameters
	// float timestep = 0.00002;
	float timestep = 0.00002;
	bool high_fidelity_spike_storage = true;

	// bool simulate_network_to_test_untrained = true;
	// bool simulate_network_to_train_network = true;
	// bool simulate_network_to_test_trained = true;

	// // Parameters for OPTIMISATION + Information Analysis
	// const float optimal_max_firing_rate = 100.0f;//set if optimizing based on maxfr //Maximum rate (spikes/sec) 87 +- 46  (*1)
	// //*1 Bair, W., & Movshon, J. A. (2004).  Adaptive Temporal Integration of Motion in Direction-Selective Neurons in Macaque Visual Cortex. The Journal of Neuroscience, 24(33), 7305遯ｶ�ｿｽ7323.
	// int number_of_bins = 5;
	// bool useThresholdForMaxFR = true;
	// const float presentation_time_per_stimulus_per_epoch_test = 0.5f;
	// float max_firing_rate = optimal_max_firing_rate*presentation_time_per_stimulus_per_epoch_test;

	float presentation_time_per_stimulus_per_epoch = 0.2;

	// SIMULATOR OPTIONS
	Simulator_Options * simulator_options = new Simulator_Options();

	simulator_options->run_simulation_general_options->presentation_time_per_stimulus_per_epoch = presentation_time_per_stimulus_per_epoch;
	simulator_options->run_simulation_general_options->number_of_epochs = 1;
	simulator_options->run_simulation_general_options->apply_stdp_to_relevant_synapses = false;
	simulator_options->run_simulation_general_options->stimulus_presentation_order_seed = 1;

	simulator_options->recording_electrodes_options->count_neuron_spikes_recording_electrodes_bool = true;

	simulator_options->stimuli_presentation_options->presentation_format = PRESENTATION_FORMAT_OBJECT_BY_OBJECT_RESET_BETWEEN_OBJECTS;
	simulator_options->stimuli_presentation_options->object_order = OBJECT_ORDER_ORIGINAL;
	simulator_options->stimuli_presentation_options->transform_order = TRANSFORM_ORDER_ORIGINAL;

	// OPTIMISATION
	int number_of_optimisation_stages = 5;
	int* indices_of_neuron_group_of_interest_for_each_optimisation_stage = (int*)malloc(number_of_optimisation_stages*sizeof(int));
	float* ideal_output_scores_for_each_optimisation_stage = (float*)malloc(number_of_optimisation_stages*sizeof(float));
	float* final_optimal_parameter_for_each_optimisation_stage = (float*)malloc(number_of_optimisation_stages*sizeof(float));

	indices_of_neuron_group_of_interest_for_each_optimisation_stage[0] = 0;
	indices_of_neuron_group_of_interest_for_each_optimisation_stage[1] = 0;
	indices_of_neuron_group_of_interest_for_each_optimisation_stage[2] = 1;
	indices_of_neuron_group_of_interest_for_each_optimisation_stage[3] = 0;
	indices_of_neuron_group_of_interest_for_each_optimisation_stage[4] = 2;

	ideal_output_scores_for_each_optimisation_stage[0] = 100.0;
	ideal_output_scores_for_each_optimisation_stage[1] = 150.0;
	ideal_output_scores_for_each_optimisation_stage[2] = 150.0;
	ideal_output_scores_for_each_optimisation_stage[3] = 100.0;
	ideal_output_scores_for_each_optimisation_stage[4] = 100.0;

	float initial_optimisation_parameter_min = 1.0f*pow(10, -12);;
	float initial_optimisation_parameter_max = 1.0*pow(10, 1);

	float optimisation_ideal_output_score = 100.0;
	float optimisation_threshold = 5.0;

	for (int optimisation_stage = 0; optimisation_stage < number_of_optimisation_stages; optimisation_stage++) {

		float optimisation_parameter_min = initial_optimisation_parameter_min;
		float optimisation_parameter_max = initial_optimisation_parameter_max;

		float final_optimal_parameter = 0.0; // Eventually have an array of these to use on subsequent optimisation_stage iterations :)
		int number_of_iterations_for_optimisation_stage = 0;

		float previous_optimisation_output_score = -1.0;

		while (true) {

			number_of_iterations_for_optimisation_stage++;

			// MODEL
			FourLayerVisionSpikingModel * four_layer_vision_spiking_model = new FourLayerVisionSpikingModel();
			four_layer_vision_spiking_model->SetTimestep(timestep);

			float test_optimisation_parameter_value = (optimisation_parameter_max + optimisation_parameter_min) / 2.0;

			if (optimisation_stage >= 0) {
				four_layer_vision_spiking_model->number_of_non_input_layers = 1;
				four_layer_vision_spiking_model->INHIBITORY_NEURONS_ON = false;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_FF[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 1) {
				four_layer_vision_spiking_model->E2E_L_SYNAPSES_ON = true;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_FF[0] = final_optimal_parameter_for_each_optimisation_stage[0];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_L[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 2) {
				four_layer_vision_spiking_model->INHIBITORY_NEURONS_ON = true;
				four_layer_vision_spiking_model->E2I_L_SYNAPSES_ON = true;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_L[0] = final_optimal_parameter_for_each_optimisation_stage[1];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2I_L[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 3) {
				four_layer_vision_spiking_model->I2E_L_SYNAPSES_ON = true;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2I_L[0] = final_optimal_parameter_for_each_optimisation_stage[2];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_I2E_L[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 4) {
				four_layer_vision_spiking_model->number_of_non_input_layers = 2;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_I2E_L[0] = final_optimal_parameter_for_each_optimisation_stage[3];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_FF[1] = test_optimisation_parameter_value;
			}

			four_layer_vision_spiking_model->finalise_model();
			four_layer_vision_spiking_model->copy_model_to_device(high_fidelity_spike_storage);

			// CREATE SIMULATOR
			Simulator * simulator = new Simulator(four_layer_vision_spiking_model, simulator_options);

			// RUN SIMULATION
			SpikeAnalyser * spike_analyser = new SpikeAnalyser(four_layer_vision_spiking_model->spiking_neurons, four_layer_vision_spiking_model->input_spiking_neurons);
			simulator->RunSimulation(spike_analyser);
			spike_analyser->calculate_various_neuron_spike_totals_and_averages(presentation_time_per_stimulus_per_epoch);

			float optimisation_output_score = spike_analyser->max_number_of_spikes_per_neuron_group_per_second[indices_of_neuron_group_of_interest_for_each_optimisation_stage[optimisation_stage]];

			// printf("previous_optimisation_output_score: %f\n", previous_optimisation_output_score);
			// printf("number_of_iterations_for_optimisation_stage: %d\n", number_of_iterations_for_optimisation_stage);
			// printf("optimisation_parameter_max: %.12f\n", optimisation_parameter_max);
			// printf("optimisation_parameter_min: %.12f\n", optimisation_parameter_min);
			// printf("test_optimisation_parameter_value: %.12f\n", test_optimisation_parameter_value);
			// printf("optimisation_output_score: %f\n", optimisation_output_score);

			if (optimisation_output_score <= optimisation_ideal_output_score) {

				if (optimisation_ideal_output_score - optimisation_output_score < optimisation_threshold) {
					final_optimal_parameter_for_each_optimisation_stage[optimisation_stage] = optimisation_output_score;
					break;
				} else {
					optimisation_parameter_min = test_optimisation_parameter_value;
				}

			} else if (optimisation_output_score >= optimisation_ideal_output_score) {

				if (optimisation_output_score - optimisation_ideal_output_score < optimisation_threshold) {
					final_optimal_parameter_for_each_optimisation_stage[optimisation_stage] = optimisation_output_score;
					break;
				} else {
					optimisation_parameter_max = test_optimisation_parameter_value;
				}

			}

			// printf("NEW optimisation_parameter_max: %.12f\n", optimisation_parameter_max);
			// printf("NEW optimisation_parameter_min: %.12f\n", optimisation_parameter_min);

			print_line_of_dashes_with_blank_lines_either_side();

			free(four_layer_vision_spiking_model);
			free(simulator);

			previous_optimisation_output_score = optimisation_output_score;

		}

		printf("final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]: %f\n", final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]);
		printf("number_of_iterations_for_optimisation_stage: %d\n", number_of_iterations_for_optimisation_stage);

	}

	print_line_of_dashes_with_blank_lines_either_side();

	for (int optimisation_stage = 0; optimisation_stage < number_of_optimisation_stages; optimisation_stage++) {

		printf("final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]: %f\n", final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]);

	}

	/////////// END OF EXPERIMENT ///////////
	experiment_timer->stop_timer_and_log_time_and_message("Experiment Completed.", true);

	return 0;
}<commit_msg>Further JITest optimisation work + GPU usage reporting<commit_after>#include "../Simulator/Simulator.h"
#include "../Models/FourLayerVisionSpikingModel.h"

#include "../SpikeAnalyser/SpikeAnalyser.h"
#include "../Helpers/TimerWithMessages.h"
#include "../Helpers/TerminalHelpers.h"

#include "cuda_profiler_api.h"

// Use the following line to compile the binary
// make FILE='JITest' EXPERIMENT_DIRECTORY='Experiments'  model -j8

// The function which will autorun when the executable is created
int main (int argc, char *argv[]){

	TimerWithMessages * experiment_timer = new TimerWithMessages();

	// Simulator Parameters
	// float timestep = 0.00002;
	float timestep = 0.00002;
	bool high_fidelity_spike_storage = true;

	// bool simulate_network_to_test_untrained = true;
	// bool simulate_network_to_train_network = true;
	// bool simulate_network_to_test_trained = true;

	// // Parameters for OPTIMISATION + Information Analysis
	// const float optimal_max_firing_rate = 100.0f;//set if optimizing based on maxfr //Maximum rate (spikes/sec) 87 +- 46  (*1)
	// //*1 Bair, W., & Movshon, J. A. (2004).  Adaptive Temporal Integration of Motion in Direction-Selective Neurons in Macaque Visual Cortex. The Journal of Neuroscience, 24(33), 7305遯ｶ�ｿｽ7323.
	// int number_of_bins = 5;
	// bool useThresholdForMaxFR = true;
	// const float presentation_time_per_stimulus_per_epoch_test = 0.5f;
	// float max_firing_rate = optimal_max_firing_rate*presentation_time_per_stimulus_per_epoch_test;

	float presentation_time_per_stimulus_per_epoch = 0.2;

	// SIMULATOR OPTIONS
	Simulator_Options * simulator_options = new Simulator_Options();

	simulator_options->run_simulation_general_options->presentation_time_per_stimulus_per_epoch = presentation_time_per_stimulus_per_epoch;
	simulator_options->run_simulation_general_options->number_of_epochs = 1;
	simulator_options->run_simulation_general_options->apply_stdp_to_relevant_synapses = false;
	simulator_options->run_simulation_general_options->stimulus_presentation_order_seed = 1;

	simulator_options->recording_electrodes_options->count_neuron_spikes_recording_electrodes_bool = true;

	simulator_options->stimuli_presentation_options->presentation_format = PRESENTATION_FORMAT_OBJECT_BY_OBJECT_RESET_BETWEEN_OBJECTS;
	simulator_options->stimuli_presentation_options->object_order = OBJECT_ORDER_ORIGINAL;
	simulator_options->stimuli_presentation_options->transform_order = TRANSFORM_ORDER_ORIGINAL;

	// OPTIMISATION
	int number_of_optimisation_stages = 1;
	int* indices_of_neuron_group_of_interest_for_each_optimisation_stage = (int*)malloc(number_of_optimisation_stages*sizeof(int));
	float* ideal_output_scores_for_each_optimisation_stage = (float*)malloc(number_of_optimisation_stages*sizeof(float));
	float* final_optimal_parameter_for_each_optimisation_stage = (float*)malloc(number_of_optimisation_stages*sizeof(float));

	if (number_of_optimisation_stages >= 1) {
		indices_of_neuron_group_of_interest_for_each_optimisation_stage[0] = 0;
		ideal_output_scores_for_each_optimisation_stage[0] = 100.0;
	}
	if (number_of_optimisation_stages >= 2) {
		indices_of_neuron_group_of_interest_for_each_optimisation_stage[1] = 0;
		ideal_output_scores_for_each_optimisation_stage[1] = 150.0;
	}
	if (number_of_optimisation_stages >= 3) {
		indices_of_neuron_group_of_interest_for_each_optimisation_stage[2] = 1;
		ideal_output_scores_for_each_optimisation_stage[2] = 150.0;
	}
	if (number_of_optimisation_stages >= 4) {
		indices_of_neuron_group_of_interest_for_each_optimisation_stage[3] = 0;
		ideal_output_scores_for_each_optimisation_stage[3] = 100.0;
	}
	if (number_of_optimisation_stages >= 5) {
		indices_of_neuron_group_of_interest_for_each_optimisation_stage[4] = 2;
		ideal_output_scores_for_each_optimisation_stage[4] = 100.0;
	}

	float initial_optimisation_parameter_min = 1.0f*pow(10, -12);;
	float initial_optimisation_parameter_max = 1.0*pow(10, -3);

	float optimisation_ideal_output_score = 100.0;
	float optimisation_threshold = 5.0;

	for (int optimisation_stage = 0; optimisation_stage < number_of_optimisation_stages; optimisation_stage++) {

		float optimisation_parameter_min = initial_optimisation_parameter_min;
		float optimisation_parameter_max = initial_optimisation_parameter_max;

		float final_optimal_parameter = 0.0; // Eventually have an array of these to use on subsequent optimisation_stage iterations :)
		int number_of_iterations_for_optimisation_stage = 0;

		float previous_optimisation_output_score = -1.0;

		// while (true) {
		for (int temp_i = 0; temp_i < 3; temp_i++) {

			number_of_iterations_for_optimisation_stage++;

			// MODEL
			FourLayerVisionSpikingModel * four_layer_vision_spiking_model = new FourLayerVisionSpikingModel();
			four_layer_vision_spiking_model->SetTimestep(timestep);

			float test_optimisation_parameter_value = (optimisation_parameter_max + optimisation_parameter_min) / 2.0;

			if (optimisation_stage >= 0) {
				four_layer_vision_spiking_model->number_of_non_input_layers = 1;
				four_layer_vision_spiking_model->INHIBITORY_NEURONS_ON = false;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_FF[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 1) {
				four_layer_vision_spiking_model->E2E_L_SYNAPSES_ON = true;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_FF[0] = final_optimal_parameter_for_each_optimisation_stage[0];
			four_layer_vision_spiking_model->finalise_model();
			four_layer_vision_spiking_model->copy_model_to_device(high_fidelity_spike_storage);

			// CREATE SIMULATOR
			Simulator * simulator = new Simulator(four_layer_vision_spiking_model, simulator_options);

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_L[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 2) {
				four_layer_vision_spiking_model->INHIBITORY_NEURONS_ON = true;
				four_layer_vision_spiking_model->E2I_L_SYNAPSES_ON = true;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_L[0] = final_optimal_parameter_for_each_optimisation_stage[1];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2I_L[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 3) {
				four_layer_vision_spiking_model->I2E_L_SYNAPSES_ON = true;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2I_L[0] = final_optimal_parameter_for_each_optimisation_stage[2];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_I2E_L[0] = test_optimisation_parameter_value;
			}

			if (optimisation_stage >= 4) {
				four_layer_vision_spiking_model->number_of_non_input_layers = 2;

				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_I2E_L[0] = final_optimal_parameter_for_each_optimisation_stage[3];
				four_layer_vision_spiking_model->LBL_biological_conductance_scaling_constant_lambda_E2E_FF[1] = test_optimisation_parameter_value;
			}

			four_layer_vision_spiking_model->finalise_model();
			four_layer_vision_spiking_model->copy_model_to_device(high_fidelity_spike_storage);

			// CREATE SIMULATOR
			Simulator * simulator = new Simulator(four_layer_vision_spiking_model, simulator_options);

			// RUN SIMULATION
			SpikeAnalyser * spike_analyser = new SpikeAnalyser(four_layer_vision_spiking_model->spiking_neurons, four_layer_vision_spiking_model->input_spiking_neurons);
			simulator->RunSimulation(spike_analyser);
			spike_analyser->calculate_various_neuron_spike_totals_and_averages(presentation_time_per_stimulus_per_epoch);

			float optimisation_output_score = spike_analyser->max_number_of_spikes_per_neuron_group_per_second[indices_of_neuron_group_of_interest_for_each_optimisation_stage[optimisation_stage]];

			printf("previous_optimisation_output_score: %f\n", previous_optimisation_output_score);
			printf("number_of_iterations_for_optimisation_stage: %d\n", number_of_iterations_for_optimisation_stage);
			printf("optimisation_parameter_max: %.12f\n", optimisation_parameter_max);
			printf("optimisation_parameter_min: %.12f\n", optimisation_parameter_min);
			printf("test_optimisation_parameter_value: %.12f\n", test_optimisation_parameter_value);
			printf("optimisation_output_score: %f\n", optimisation_output_score);

			if (optimisation_output_score <= optimisation_ideal_output_score) {

				if (optimisation_ideal_output_score - optimisation_output_score < optimisation_threshold) {
					final_optimal_parameter_for_each_optimisation_stage[optimisation_stage] = optimisation_output_score;
					break;
				} else {
					optimisation_parameter_min = test_optimisation_parameter_value;
				}

			} else if (optimisation_output_score >= optimisation_ideal_output_score) {

				if (optimisation_output_score - optimisation_ideal_output_score < optimisation_threshold) {
					final_optimal_parameter_for_each_optimisation_stage[optimisation_stage] = optimisation_output_score;
					break;
				} else {
					optimisation_parameter_max = test_optimisation_parameter_value;
				}

			}

			printf("NEW optimisation_parameter_max: %.12f\n", optimisation_parameter_max);
			printf("NEW optimisation_parameter_min: %.12f\n", optimisation_parameter_min);

			print_line_of_dashes_with_blank_lines_either_side();

			free(four_layer_vision_spiking_model);
			free(simulator);

			previous_optimisation_output_score = optimisation_output_score;

			// show memory usage of GPU

	        size_t free_byte ;

	        size_t total_byte ;

	       	cudaError_t cuda_status = cudaMemGetInfo( &free_byte, &total_byte ) ;

	        if ( cudaSuccess != cuda_status ){

	            printf("Error: cudaMemGetInfo fails, %s \n", cudaGetErrorString(cuda_status) );

	            exit(1);

	        }

	        double free_db = (double)free_byte ;

	        double total_db = (double)total_byte ;

	        double used_db = total_db - free_db ;

	        printf("GPU memory usage: used = %f, free = %f MB, total = %f MB\n",

	            used_db/1024.0/1024.0, free_db/1024.0/1024.0, total_db/1024.0/1024.0);

		}

		printf("final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]: %f\n", final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]);
		printf("number_of_iterations_for_optimisation_stage: %d\n", number_of_iterations_for_optimisation_stage);

	}

	print_line_of_dashes_with_blank_lines_either_side();

	for (int optimisation_stage = 0; optimisation_stage < number_of_optimisation_stages; optimisation_stage++) {

		printf("final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]: %f\n", final_optimal_parameter_for_each_optimisation_stage[optimisation_stage]);

	}

	/////////// END OF EXPERIMENT ///////////
	experiment_timer->stop_timer_and_log_time_and_message("Experiment Completed.", true);

	cudaProfilerStop();

	return 0;
}<|endoftext|>