<commit_before>#include "McMaker/TpcEffFitter.h"
#include "Common.h"

// ROOT
#include "TGraphAsymmErrors.h"
#include "TFile.h"

#include "Logger.h"
#include "Reporter.h"
#include "RooPlotLib.h"
using namespace jdb;

void TpcEffFitter::initialize(  ){

	DEBUG( classname(), "( " << config.getFilename() << ", " << nodePath << " )" )
	outputPath = config.getString( nodePath + ".output:path", "" );

	book = unique_ptr<HistoBook>( new HistoBook( outputPath + config.getString( nodePath +  ".output.data", "TpcEff.root" ), config, "", "" ) );
}

void TpcEffFitter::make(){
	DEBUG(classname(), "")

	RooPlotLib rpl;

	gStyle->SetOptFit( 111 );
	string params_file =  config.getString( nodePath + ".output.params" );
	if ( "" == params_file ){
		ERROR( classname(), "Specifiy an output params file for the parameters" )
		return;
	}

	ofstream out( params_file.c_str() );

	out << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" << endl;
	out << "<config>" << endl;

	vector<string> labels = config.getStringVector( nodePath + ".CentralityLabels" );
	vector< int> cbins = config.getIntVector( nodePath + ".CentralityBins" );
	Reporter rp( config, nodePath + "Reporter." );

	double minP0Error = config.getDouble( nodePath + ".Systematics:minP0Error" );

	DEBUG( "Starting plc loop" )
	for ( string plc : Common::species ){
		if ( "E" == plc || "D" == plc )	// skip Electrons and Deuterons if I've got those in the list
			continue;

		for ( string c : Common::sCharges ){

			out << "\t<" << plc << "_" << c << ">" << endl;

			string fnMc = config.getString( nodePath + ".input:url" ) + "TpcEff_" + plc + "_" + c + "_mc" + ".root";
			TFile * fmc = new TFile( fnMc.c_str(), "READ" );
			string fnRc = config.getString( nodePath + ".input:url" ) + "TpcEff_" + plc + "_" + c + "_rc" + ".root";
			TFile * frc = new TFile( fnRc.c_str(), "READ" );

			DEBUG( classname(), "Mc File = " << fmc );
			DEBUG( classname(), "Rc File = " << frc );

			if ( !fmc->IsOpen() || !frc->IsOpen() )
				continue;

			// build an efficiency for each centrality
			for ( int b : cbins ){

				TH1 * hMc = (TH1*)fmc->Get( ("inclusive/pt_" + ts( b ) + "_" + c ).c_str() );
				TH1 * hRc = (TH1*)frc->Get( ("inclusive/pt_" + ts( b ) + "_" + c ).c_str() );

				INFO( classname(), "N bins MC = " << hMc->GetNbinsX() );
				INFO( classname(), "N bins RC = " << hRc->GetNbinsX() );

				for ( int i = 0; i <= hMc->GetNbinsX() + 1; i++ ){
					if ( hMc->GetBinContent( i ) < hRc->GetBinContent( i ) ){
						// set to 100%
						if ( i > 5 )
							hMc->SetBinContent( i, hRc->GetBinContent( i ) );
						else{
							hRc->SetBinContent( i, 0 );
							hMc->SetBinContent( i, 0 );
						}
					}
				}

				hMc->Sumw2();
				hRc->Sumw2();

				TGraphAsymmErrors g;

				g.SetName( (plc + "_" + c + "_" + ts(b)).c_str() );
				g.BayesDivide( hRc, hMc );

				book->add( plc + "_" + c + "_" + ts(b),  &g );

				// do the fit
				TF1 * fitFunc = new TF1( "effFitFunc", "[0] * exp( - pow( [1] / x, [2] ) )", 0.0, 5.0 );
				fitFunc->SetParameters( .85, 0.05, 5.0, -0.05 );
				fitFunc->SetParLimits( 0, 0.5, 1.0 );
				fitFunc->SetParLimits( 1, 0.0, 0.5 );
				fitFunc->SetParLimits( 2, 0.0, 100000 );

				// fist fit shape
				TFitResultPtr fitPointer = g.Fit( fitFunc, "RSWW" );
				fitPointer = g.Fit( fitFunc, "RS" );

				// ensure that uncertainty on efficiency is at least 2%
				// if ( fitFunc->GetParError( 0 ) < minP0Error ) {
				// 	INFO( classname(), "P0 uncertainty below threshold (" << (minP0Error * 100) << "%" );
				// 	INFO( classname(), "Setting P0 error to " << (minP0Error * 100) << "%" );
				// 	fitFunc->SetParError( 0, minP0Error );
				// }

				INFO( classname(), "FitPointer = " << fitPointer );
				TGraphErrors * band = Common::choleskyBands( fitPointer, fitFunc, 5000, 200, &rp );

				rp.newPage();
				rpl.style( &g ).set( "title", Common::plc_label( plc, c ) + " : " + labels[ b ] + ", 68%CL (Red)" ).set( "yr", 0, 1.1 ).set( "optfit", 111 )
					.set( "xr", 0, 4.5 )
					.set("y", "Efficiency x Acceptance").set( "x", "p_{T}^{MC} [GeV/c]" ).draw();

				INFO( classname(), "Stat Box" );
				gStyle->SetStatY( 0.5 );
				gStyle->SetStatX( 0.85 );

				fitFunc->SetLineColor( kRed );
				fitFunc->Draw("same");

				INFO( classname(), "Drawing CL band" );

				band->SetFillColorAlpha( kRed, 0.5 );
				band->Draw( "same e3" );

				rp.savePage();
				rp.saveImage( outputPath + "/img/TpcEff_" + plc + "_" + c + "_" +  + ".png" );

				INFO( classname(), "Exporting Params" );
				exportParams( b, fitFunc, fitPointer, out );

			} // loop centrality bins

			out << "\t</" << plc << "_" << c << ">" << endl;

		} // loop on charge
	} // loop on plc

	out << "</config>" << endl;
	out.close();

}

void TpcEffFitter::exportParams( int bin, TF1 * f, TFitResultPtr result, ofstream &out ){
	INFO( classname(), "(bin=" << bin << ", f=" << f << ", fPtr=" << result << " )" )
	out << "\t\t<TpcEffParams bin=\"" << bin << "\" ";
	out << Common::toXml( f, result );
	out << "/>" << endl;
}<commit_msg>Adding log messages to TpcEffFitter<commit_after>#include "McMaker/TpcEffFitter.h"
#include "Common.h"

// ROOT
#include "TGraphAsymmErrors.h"
#include "TFile.h"

#include "Logger.h"
#include "Reporter.h"
#include "RooPlotLib.h"
using namespace jdb;

void TpcEffFitter::initialize(  ){

	DEBUG( classname(), "( " << config.getFilename() << ", " << nodePath << " )" )
	outputPath = config.getString( nodePath + ".output:path", "" );

	book = unique_ptr<HistoBook>( new HistoBook( outputPath + config.getString( nodePath +  ".output.data", "TpcEff.root" ), config, "", "" ) );
}

void TpcEffFitter::make(){
	DEBUG(classname(), "")

	RooPlotLib rpl;

	gStyle->SetOptFit( 111 );
	string params_file =  config.getString( nodePath + ".output.params" );
	if ( "" == params_file ){
		ERROR( classname(), "Specifiy an output params file for the parameters" )
		return;
	}

	ofstream out( params_file.c_str() );

	out << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" << endl;
	out << "<config>" << endl;

	vector<string> labels = config.getStringVector( nodePath + ".CentralityLabels" );
	vector< int> cbins = config.getIntVector( nodePath + ".CentralityBins" );
	Reporter rp( config, nodePath + "Reporter." );

	double minP0Error = config.getDouble( nodePath + ".Systematics:minP0Error" );

	DEBUG( "Starting plc loop" )
	for ( string plc : Common::species ){
		if ( "E" == plc || "D" == plc )	// skip Electrons and Deuterons if I've got those in the list
			continue;

		for ( string c : Common::sCharges ){

			out << "\t<" << plc << "_" << c << ">" << endl;

			string fnMc = config.getString( nodePath + ".input:url" ) + "TpcEff_" + plc + "_" + c + "_mc" + ".root";
			TFile * fmc = new TFile( fnMc.c_str(), "READ" );
			string fnRc = config.getString( nodePath + ".input:url" ) + "TpcEff_" + plc + "_" + c + "_rc" + ".root";
			TFile * frc = new TFile( fnRc.c_str(), "READ" );

			DEBUG( classname(), "Mc File = " << fmc );
			DEBUG( classname(), "Rc File = " << frc );

			if ( !fmc->IsOpen() || !frc->IsOpen() )
				continue;

			// build an efficiency for each centrality
			for ( int b : cbins ){

				TH1 * hMc = (TH1*)fmc->Get( ("inclusive/pt_" + ts( b ) + "_" + c ).c_str() );
				TH1 * hRc = (TH1*)frc->Get( ("inclusive/pt_" + ts( b ) + "_" + c ).c_str() );

				INFO( classname(), "N bins MC = " << hMc->GetNbinsX() );
				INFO( classname(), "N bins RC = " << hRc->GetNbinsX() );

				for ( int i = 0; i <= hMc->GetNbinsX() + 1; i++ ){
					if ( hMc->GetBinContent( i ) < hRc->GetBinContent( i ) ){
						// set to 100%
						if ( i > 5 )
							hMc->SetBinContent( i, hRc->GetBinContent( i ) );
						else{
							hRc->SetBinContent( i, 0 );
							hMc->SetBinContent( i, 0 );
						}
					}
				}

				hMc->Sumw2();
				hRc->Sumw2();

				TGraphAsymmErrors g;

				g.SetName( (plc + "_" + c + "_" + ts(b)).c_str() );
				g.BayesDivide( hRc, hMc );

				INFO( classname(), "Adding TGraphAsymmErrors to book" );
				book->add( plc + "_" + c + "_" + ts(b),  &g );

				// do the fit
				TF1 * fitFunc = new TF1( "effFitFunc", "[0] * exp( - pow( [1] / x, [2] ) )", 0.0, 5.0 );
				fitFunc->SetParameters( .85, 0.05, 5.0, -0.05 );
				fitFunc->SetParLimits( 0, 0.5, 1.0 );
				fitFunc->SetParLimits( 1, 0.0, 0.5 );
				fitFunc->SetParLimits( 2, 0.0, 100000 );

				// fist fit shape
				TFitResultPtr fitPointer = g.Fit( fitFunc, "RSWW" );
				fitPointer = g.Fit( fitFunc, "RS" );

				// ensure that uncertainty on efficiency is at least 2%
				// if ( fitFunc->GetParError( 0 ) < minP0Error ) {
				// 	INFO( classname(), "P0 uncertainty below threshold (" << (minP0Error * 100) << "%" );
				// 	INFO( classname(), "Setting P0 error to " << (minP0Error * 100) << "%" );
				// 	fitFunc->SetParError( 0, minP0Error );
				// }

				INFO( classname(), "FitPointer = " << fitPointer );
				TGraphErrors * band = Common::choleskyBands( fitPointer, fitFunc, 5000, 200, &rp );

				rp.newPage();
				rpl.style( &g ).set( "title", Common::plc_label( plc, c ) + " : " + labels[ b ] + ", 68%CL (Red)" ).set( "yr", 0, 1.1 ).set( "optfit", 111 )
					.set( "xr", 0, 4.5 )
					.set("y", "Efficiency x Acceptance").set( "x", "p_{T}^{MC} [GeV/c]" ).draw();

				INFO( classname(), "Stat Box" );
				gStyle->SetStatY( 0.5 );
				gStyle->SetStatX( 0.85 );

				fitFunc->SetLineColor( kRed );
				fitFunc->Draw("same");

				INFO( classname(), "Drawing CL band" );

				band->SetFillColorAlpha( kRed, 0.5 );
				band->Draw( "same e3" );

				rp.savePage();
				rp.saveImage( outputPath + "/img/TpcEff_" + plc + "_" + c + "_" +  + ".png" );

				INFO( classname(), "Exporting Params" );
				exportParams( b, fitFunc, fitPointer, out );

			} // loop centrality bins

			out << "\t</" << plc << "_" << c << ">" << endl;

		} // loop on charge
	} // loop on plc

	out << "</config>" << endl;
	out.close();

}

void TpcEffFitter::exportParams( int bin, TF1 * f, TFitResultPtr result, ofstream &out ){
	INFO( classname(), "(bin=" << bin << ", f=" << f << ", fPtr=" << result << " )" )
	out << "\t\t<TpcEffParams bin=\"" << bin << "\" ";
	out << Common::toXml( f, result );
	out << "/>" << endl;
}<|endoftext|>


<commit_before>/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the Qt Mobility Components.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
**   * Redistributions of source code must retain the above copyright
**     notice, this list of conditions and the following disclaimer.
**   * Redistributions in binary form must reproduce the above copyright
**     notice, this list of conditions and the following disclaimer in
**     the documentation and/or other materials provided with the
**     distribution.
**   * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor
**     the names of its contributors may be used to endorse or promote
**     products derived from this software without specific prior written
**     permission.
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
** $QT_END_LICENSE$
**
****************************************************************************/

#include <QtGui/QApplication>
#include "mainwindow.h"

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    MainWindow w;
#if defined(Q_WS_S60)
    w.showMaximized();
#else
    w.show();
#endif

    return a.exec();
}
<commit_msg>Display ndefeditor fullscreen on mobile platforms.<commit_after>/****************************************************************************
**
** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
** All rights reserved.
** Contact: Nokia Corporation (qt-info@nokia.com)
**
** This file is part of the Qt Mobility Components.
**
** $QT_BEGIN_LICENSE:BSD$
** You may use this file under the terms of the BSD license as follows:
**
** "Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions are
** met:
**   * Redistributions of source code must retain the above copyright
**     notice, this list of conditions and the following disclaimer.
**   * Redistributions in binary form must reproduce the above copyright
**     notice, this list of conditions and the following disclaimer in
**     the documentation and/or other materials provided with the
**     distribution.
**   * Neither the name of Nokia Corporation and its Subsidiary(-ies) nor
**     the names of its contributors may be used to endorse or promote
**     products derived from this software without specific prior written
**     permission.
**
** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
** $QT_END_LICENSE$
**
****************************************************************************/

#include <QtGui/QApplication>
#include "mainwindow.h"

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    MainWindow w;

#if defined(Q_WS_S60) || defined(Q_WS_MAEMO_6) || defined(Q_WS_MEEGO)
    w.showFullScreen();
#else
    w.show();
#endif

    return a.exec();
}
<|endoftext|>


<commit_before>// Copyright 2010-2018 Google LLC
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

// Constraint programming example that shows how to use the API.

#include "ortools/base/logging.h"
#include "ortools/constraint_solver/constraint_solver.h"

namespace operations_research {
void RunConstraintProgrammingExample() {
  // Instantiate the solver.
  Solver solver("ConstraintProgrammingExample");
  const int64 numVals = 3;

  // Define decision variables.
  IntVar* const x = solver.MakeIntVar(0, numVals - 1, "x");
  IntVar* const y = solver.MakeIntVar(0, numVals - 1, "y");
  IntVar* const z = solver.MakeIntVar(0, numVals - 1, "z");

  // Define constraints.
  std::vector<IntVar*> xyvars = {x, y};
  solver.AddConstraint(solver.MakeAllDifferent(xyvars));

  LOG(INFO) << "Number of constraints: " << solver.constraints();

  // Create decision builder to search for solutions.
  std::vector<IntVar*> allvars = {x, y, z};
  DecisionBuilder* const db = solver.MakePhase(
      allvars, Solver::CHOOSE_FIRST_UNBOUND, Solver::ASSIGN_MIN_VALUE);

  solver.NewSearch(db);
  while (solver.NextSolution()) {
    LOG(INFO) << "Solution"
              << ": x = " << x->Value() << "; y = " << x->Value()
              << "; z = " << z->Value();
  }
  solver.EndSearch();
  LOG(INFO) << "Number of solutions: " << solver.solutions();
  LOG(INFO) << "";
  LOG(INFO) << "Advanced usage:";
  LOG(INFO) << "Problem solved in " << solver.wall_time() << "ms";
  LOG(INFO) << "Memory usage: " << Solver::MemoryUsage() << " bytes";
}
}  // namespace operations_research

int main(int argc, char** argv) {
  google::InitGoogleLogging(argv[0]);
  FLAGS_logtostderr = 1;
  operations_research::RunConstraintProgrammingExample();
  return EXIT_SUCCESS;
}
<commit_msg>Update constraint_programming_cp.cc<commit_after>// Copyright 2010-2018 Google LLC
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

// Constraint programming example that shows how to use the API.

#include "ortools/base/logging.h"
#include "ortools/constraint_solver/constraint_solver.h"

namespace operations_research {
void RunConstraintProgrammingExample() {
  // Instantiate the solver.
  Solver solver("ConstraintProgrammingExample");
  const int64 numVals = 3;

  // Define decision variables.
  IntVar* const x = solver.MakeIntVar(0, numVals - 1, "x");
  IntVar* const y = solver.MakeIntVar(0, numVals - 1, "y");
  IntVar* const z = solver.MakeIntVar(0, numVals - 1, "z");

  // Define constraints.
  std::vector<IntVar*> xyvars = {x, y};
  solver.AddConstraint(solver.MakeAllDifferent(xyvars));

  LOG(INFO) << "Number of constraints: " << solver.constraints();

  // Create decision builder to search for solutions.
  std::vector<IntVar*> allvars = {x, y, z};
  DecisionBuilder* const db = solver.MakePhase(
      allvars, Solver::CHOOSE_FIRST_UNBOUND, Solver::ASSIGN_MIN_VALUE);

  solver.NewSearch(db);
  while (solver.NextSolution()) {
    LOG(INFO) << "Solution"
              << ": x = " << x->Value() << "; y = " << y->Value()
              << "; z = " << z->Value();
  }
  solver.EndSearch();
  LOG(INFO) << "Number of solutions: " << solver.solutions();
  LOG(INFO) << "";
  LOG(INFO) << "Advanced usage:";
  LOG(INFO) << "Problem solved in " << solver.wall_time() << "ms";
  LOG(INFO) << "Memory usage: " << Solver::MemoryUsage() << " bytes";
}
}  // namespace operations_research

int main(int argc, char** argv) {
  google::InitGoogleLogging(argv[0]);
  FLAGS_logtostderr = 1;
  operations_research::RunConstraintProgrammingExample();
  return EXIT_SUCCESS;
}
<|endoftext|>


<commit_before>#include "Window.h"

#include <QtGui>

#include "ui_MainWindow.h"

#if defined Q_OS_MAC
#include "../OSXLocal.h"
#endif

#include "../Settings.h"

Window::Window()
  : mUI( new Ui::MainWindow )
{
  mUI->setupUi( this );
  setWindowFlags( (Qt::Tool | Qt::CustomizeWindowHint | Qt::WindowCloseButtonHint | Qt::MSWindowsFixedSizeDialogHint) );

  setWindowTitle( qApp->applicationName() );

  CreateActions();
  CreateTrayIcon();

  connect( mTrayIcon, SIGNAL( activated(QSystemTrayIcon::ActivationReason) ), this, SLOT( TrayIconActivated(QSystemTrayIcon::ActivationReason) ) );

  QActionGroup *group = new QActionGroup( this );
  group->setExclusive( true );

  mUI->actionSettings->setActionGroup( group );
  mUI->actionSettings->setProperty( "pageIndex", 0 );

  mUI->actionAccount->setActionGroup( group );
  mUI->actionAccount->setProperty( "pageIndex", 1 );

  mUI->actionLog->setActionGroup( group );
  mUI->actionLog->setProperty( "pageIndex", 2 );

  mUI->actionAbout->setActionGroup( group );
  mUI->actionAbout->setProperty( "pageIndex", 3 );

  mUI->pageWidget->setCurrentIndex( 0 );
  mUI->actionSettings->setChecked( true );
  TabChanged( 0 );

  connect( group, SIGNAL( triggered(QAction*) ), this, SLOT( ActionTriggered(QAction*) ) );
  connect( mUI->pageWidget, SIGNAL( currentChanged(int) ), this, SLOT( TabChanged( int ) ) );

  QTimer::singleShot( 1000, this, SLOT(HandleFirstStartCheck()) );

#ifdef Q_OS_WIN
  // This is a fix for
  // https://bugreports.qt.io/browse/QTBUG-35986
  // If the window was never opened, the WM_ENDSESSION event will
  // not be received by the app (tray icon will disappear
  // but the app will not close)
  // So show, then hide it at the beginning
  // With Qt:Tool the Window is not actually shown
  show();
  hide();
#endif
}

Window::~Window() {
  delete mUI;
}

void Window::ActionTriggered( QAction *action ) {
  int page = action->property( "pageIndex" ).toInt();
  mUI->pageWidget->setCurrentIndex( page );
}

void Window::TabChanged( int index ) {
  QWidget *widget = mUI->pageWidget->widget( index );
  mUI->pageWidget->setFixedHeight( widget->minimumHeight() );
  adjustSize();
}

void Window::ShowNotification( const char *title, const char *message ) {
#if defined Q_OS_WIN || defined Q_OS_LINUX
  mTrayIcon->showMessage( title, message );
#elif defined Q_OS_MAC
  OSX_ShowNotification( title, message );
#endif
}

void Window::HandleFirstStartCheck() {
  // Notify user the first time that the app runs in the taskbar
  QSettings settings;
  if( !settings.contains("taskbarHint") ) {
    settings.setValue( "taskbarHint", true );
#if defined Q_OS_WIN || defined Q_OS_LINUX
    ShowNotification( "Heads up!", "Track-o-Bot runs in your taskbar! Right click the icon for more options." );
#elif defined Q_OS_MAC
    ShowNotification( "Track-o-Bot", "Track-o-Bot runs in your menu bar! Click the icon for more options." );
#endif
  }
}

void Window::TrayIconActivated( QSystemTrayIcon::ActivationReason reason ) {
#ifdef Q_OS_WIN
  if( reason == QSystemTrayIcon::ActivationReason::DoubleClick ) {
    OpenProfileRequested();
  }
#elif defined Q_OS_LINUX
if( reason == QSystemTrayIcon::DoubleClick ) {
    OpenProfileRequested();
}
else if( reason == QSystemTrayIcon::Trigger ) {
    RiseAndShine();
}
#else
  UNUSED_ARG( reason );
#endif
}

void Window::closeEvent( QCloseEvent *event ) {
  if( mTrayIcon->isVisible() ) {
    hide();
    event->ignore();
  }
}

void Window::CreateActions() {
  mOpenProfileAction = new QAction( tr( "Open Profile..." ), this );
  connect( mOpenProfileAction, SIGNAL( triggered() ), this, SLOT( OpenProfileRequested() ) );

  mShowAction = new QAction( tr( "Settings..." ), this );
  connect( mShowAction, SIGNAL( triggered() ), this, SLOT( RiseAndShine() ) );

  mQuitAction = new QAction( tr("Quit"), this );
  connect( mQuitAction, SIGNAL( triggered() ), qApp, SLOT( quit() ) );

  mGameClientRestartRequiredAction = new QAction( tr("Please restart Hearthstone!" ), this );
  mGameClientRestartRequiredAction->setEnabled( false );
}

void Window::CreateTrayIcon() {
  bool is_linux = true;
#if defined Q_OS_WIN || defined Q_OS_MAC
  is_linux = false;
#endif
  mTrayIconMenu = new QMenu( this);
  mTrayIconMenu->addAction( mOpenProfileAction );
  mTrayIconMenu->addSeparator();
  mTrayIconMenu->addAction( mShowAction );
  bool is_kde_plasma = false;
  if(is_linux){
      QString dm = getenv("DESKTOP_SESSION");
      is_kde_plasma = (dm.toLower() == "plasma");
  }
  if(!is_linux || !is_kde_plasma){
    mTrayIconMenu->addSeparator();
    mTrayIconMenu->addAction( mQuitAction );
  }

  mTrayIcon = new QSystemTrayIcon( this );
  mTrayIcon->setContextMenu (mTrayIconMenu );

#if defined Q_OS_MAC
  QIcon::Mode blackMode = QIcon::Normal;
  QIcon::Mode whiteMode = QIcon::Selected;
  if( OSX_YosemiteDarkModeEnabled() ) {
    blackMode = QIcon::Disabled;
    whiteMode = QIcon::Normal;
  }

  QIcon icon;
  icon.addFile( ":/icons/mac_black@2x.png", QSize(), blackMode );
  icon.addFile( ":/icons/mac_black.png", QSize(), blackMode );
  icon.addFile( ":/icons/mac_white.png", QSize(), whiteMode );
  icon.addFile( ":/icons/mac_white@2x.png", QSize(), whiteMode );
#elif defined Q_OS_WIN
  QIcon icon = QIcon( ":/icons/win.ico" );
#elif defined Q_OS_LINUX
  QIcon icon = QIcon( ":/icons/Track-o-Bot.png" );
  icon.addFile( ":/icons/logo.png", QSize() );
#endif

  mTrayIcon->setIcon( icon );
  mTrayIcon->show();
}

void Window::RiseAndShine() {
  show();
  raise();
}

void Window::OpenProfileRequested() {
  emit OpenProfile();
}

void Window::HandleGameClientRestartRequired( bool restartRequired ) {
  static QAction *separator = NULL;

  if( restartRequired ) {
    separator = mTrayIconMenu->insertSeparator( mOpenProfileAction );
    mTrayIconMenu->insertAction( separator, mGameClientRestartRequiredAction );

    ShowNotification( "Game log updated", "Please restart Hearthstone for changes to take effect!" );
  } else {
    mTrayIconMenu->removeAction( mGameClientRestartRequiredAction );
    if( separator ) {
      mTrayIconMenu->removeAction( separator );
    }
  }
}
<commit_msg>Fixes double Quit in systray<commit_after>#include "Window.h"

#include <QtGui>

#include "ui_MainWindow.h"

#if defined Q_OS_MAC
#include "../OSXLocal.h"
#endif

#include "../Settings.h"

Window::Window()
  : mUI( new Ui::MainWindow )
{
  mUI->setupUi( this );
  setWindowFlags( (Qt::Tool | Qt::CustomizeWindowHint | Qt::WindowCloseButtonHint | Qt::MSWindowsFixedSizeDialogHint) );

  setWindowTitle( qApp->applicationName() );

  CreateActions();
  CreateTrayIcon();

  connect( mTrayIcon, SIGNAL( activated(QSystemTrayIcon::ActivationReason) ), this, SLOT( TrayIconActivated(QSystemTrayIcon::ActivationReason) ) );

  QActionGroup *group = new QActionGroup( this );
  group->setExclusive( true );

  mUI->actionSettings->setActionGroup( group );
  mUI->actionSettings->setProperty( "pageIndex", 0 );

  mUI->actionAccount->setActionGroup( group );
  mUI->actionAccount->setProperty( "pageIndex", 1 );

  mUI->actionLog->setActionGroup( group );
  mUI->actionLog->setProperty( "pageIndex", 2 );

  mUI->actionAbout->setActionGroup( group );
  mUI->actionAbout->setProperty( "pageIndex", 3 );

  mUI->pageWidget->setCurrentIndex( 0 );
  mUI->actionSettings->setChecked( true );
  TabChanged( 0 );

  connect( group, SIGNAL( triggered(QAction*) ), this, SLOT( ActionTriggered(QAction*) ) );
  connect( mUI->pageWidget, SIGNAL( currentChanged(int) ), this, SLOT( TabChanged( int ) ) );

  QTimer::singleShot( 1000, this, SLOT(HandleFirstStartCheck()) );

#ifdef Q_OS_WIN
  // This is a fix for
  // https://bugreports.qt.io/browse/QTBUG-35986
  // If the window was never opened, the WM_ENDSESSION event will
  // not be received by the app (tray icon will disappear
  // but the app will not close)
  // So show, then hide it at the beginning
  // With Qt:Tool the Window is not actually shown
  show();
  hide();
#endif
}

Window::~Window() {
  delete mUI;
}

void Window::ActionTriggered( QAction *action ) {
  int page = action->property( "pageIndex" ).toInt();
  mUI->pageWidget->setCurrentIndex( page );
}

void Window::TabChanged( int index ) {
  QWidget *widget = mUI->pageWidget->widget( index );
  mUI->pageWidget->setFixedHeight( widget->minimumHeight() );
  adjustSize();
}

void Window::ShowNotification( const char *title, const char *message ) {
#if defined Q_OS_WIN || defined Q_OS_LINUX
  mTrayIcon->showMessage( title, message );
#elif defined Q_OS_MAC
  OSX_ShowNotification( title, message );
#endif
}

void Window::HandleFirstStartCheck() {
  // Notify user the first time that the app runs in the taskbar
  QSettings settings;
  if( !settings.contains("taskbarHint") ) {
    settings.setValue( "taskbarHint", true );
#if defined Q_OS_WIN || defined Q_OS_LINUX
    ShowNotification( "Heads up!", "Track-o-Bot runs in your taskbar! Right click the icon for more options." );
#elif defined Q_OS_MAC
    ShowNotification( "Track-o-Bot", "Track-o-Bot runs in your menu bar! Click the icon for more options." );
#endif
  }
}

void Window::TrayIconActivated( QSystemTrayIcon::ActivationReason reason ) {
#ifdef Q_OS_WIN
  if( reason == QSystemTrayIcon::ActivationReason::DoubleClick ) {
    OpenProfileRequested();
  }
#elif defined Q_OS_LINUX
if( reason == QSystemTrayIcon::DoubleClick ) {
    OpenProfileRequested();
}
else if( reason == QSystemTrayIcon::Trigger ) {
    RiseAndShine();
}
#else
  UNUSED_ARG( reason );
#endif
}

void Window::closeEvent( QCloseEvent *event ) {
  if( mTrayIcon->isVisible() ) {
    hide();
    event->ignore();
  }
}

void Window::CreateActions() {
  mOpenProfileAction = new QAction( tr( "Open Profile..." ), this );
  connect( mOpenProfileAction, SIGNAL( triggered() ), this, SLOT( OpenProfileRequested() ) );

  mShowAction = new QAction( tr( "Settings..." ), this );
  connect( mShowAction, SIGNAL( triggered() ), this, SLOT( RiseAndShine() ) );

  mQuitAction = new QAction( tr("Quit"), this );
  connect( mQuitAction, SIGNAL( triggered() ), qApp, SLOT( quit() ) );

  mGameClientRestartRequiredAction = new QAction( tr("Please restart Hearthstone!" ), this );
  mGameClientRestartRequiredAction->setEnabled( false );
}

void Window::CreateTrayIcon() {
  bool is_linux = true;
#if defined Q_OS_WIN || defined Q_OS_MAC
  is_linux = false;
#endif
  mTrayIconMenu = new QMenu( this);
  mTrayIconMenu->addAction( mOpenProfileAction );
  mTrayIconMenu->addSeparator();
  mTrayIconMenu->addAction( mShowAction );
  bool is_kde_plasma = false;
  if(is_linux){
      QString dm = getenv("DESKTOP_SESSION");
      // getenv returns something like /usr/share/xsessions/plasma
      // so either we match that or we regexp for plasma
      QRegularExpression plasma_re("plasma$");
      QRegularExpressionMatch plasma_match = plasma_re.match(dm);
      is_kde_plasma = plasma_match.hasMatch();
  }
  if(!is_linux || !is_kde_plasma){
    mTrayIconMenu->addSeparator();
    mTrayIconMenu->addAction( mQuitAction );
  }

  mTrayIcon = new QSystemTrayIcon( this );
  mTrayIcon->setContextMenu (mTrayIconMenu );

#if defined Q_OS_MAC
  QIcon::Mode blackMode = QIcon::Normal;
  QIcon::Mode whiteMode = QIcon::Selected;
  if( OSX_YosemiteDarkModeEnabled() ) {
    blackMode = QIcon::Disabled;
    whiteMode = QIcon::Normal;
  }

  QIcon icon;
  icon.addFile( ":/icons/mac_black@2x.png", QSize(), blackMode );
  icon.addFile( ":/icons/mac_black.png", QSize(), blackMode );
  icon.addFile( ":/icons/mac_white.png", QSize(), whiteMode );
  icon.addFile( ":/icons/mac_white@2x.png", QSize(), whiteMode );
#elif defined Q_OS_WIN
  QIcon icon = QIcon( ":/icons/win.ico" );
#elif defined Q_OS_LINUX
  QIcon icon = QIcon( ":/icons/Track-o-Bot.png" );
  icon.addFile( ":/icons/logo.png", QSize() );
#endif

  mTrayIcon->setIcon( icon );
  mTrayIcon->show();
}

void Window::RiseAndShine() {
  show();
  raise();
}

void Window::OpenProfileRequested() {
  emit OpenProfile();
}

void Window::HandleGameClientRestartRequired( bool restartRequired ) {
  static QAction *separator = NULL;

  if( restartRequired ) {
    separator = mTrayIconMenu->insertSeparator( mOpenProfileAction );
    mTrayIconMenu->insertAction( separator, mGameClientRestartRequiredAction );

    ShowNotification( "Game log updated", "Please restart Hearthstone for changes to take effect!" );
  } else {
    mTrayIconMenu->removeAction( mGameClientRestartRequiredAction );
    if( separator ) {
      mTrayIconMenu->removeAction( separator );
    }
  }
}
<|endoftext|>


<commit_before>#include <cmath>
#include <iostream>

#include <franka/robot.h>

int main(int argc, char** argv) {
  if (argc != 2) {
    std::cerr << "Usage: ./generate_consecutive_motions <robot-hostname>" << std::endl;
    return -1;
  }

  try {
    franka::Robot robot(argv[1]);

    // Set additional parameters always before the control loop, NEVER in the
    // control loop
    // Set collision behavior:
    robot.setCollisionBehavior(
        {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}}, {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}},
        {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}}, {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}},
        {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}}, {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}},
        {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}}, {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}});

    for (int i = 0; i < 5; i++) {
      std::cout << "Executing motion." << std::endl;
      try {
        auto initial_pose = robot.readOnce().q_d;
        double time = 0.0;
        robot.control([=, &time](const franka::RobotState&) -> franka::JointPositions {
          double delta_angle = M_PI / 32 * (1 - std::cos(M_PI / 1.0 * time));

          time += 0.001;
          if (time > 2.0) {
            std::cout << std::endl << "Finished motion." << std::endl;
            return franka::Stop;
          }

          return {{initial_pose[0], initial_pose[1], initial_pose[2], initial_pose[3],
                   initial_pose[4], initial_pose[5], initial_pose[6] + delta_angle}};
        });
      } catch (const franka::ControlException& e) {
        std::cout << e.what() << std::endl;
        std::cout << "Running error recovery..." << std::endl;
        robot.automaticErrorRecovery();
      }
    }
  } catch (const franka::Exception& e) {
    std::cout << e.what() << std::endl;
    return -1;
  }

  return 0;
}
<commit_msg>Change consecutive motion sample to joint velocity.<commit_after>#include <cmath>
#include <iostream>

#include <franka/robot.h>

int main(int argc, char** argv) {
  if (argc != 2) {
    std::cerr << "Usage: ./generate_consecutive_motions <robot-hostname>" << std::endl;
    return -1;
  }

  try {
    franka::Robot robot(argv[1]);

    // Set additional parameters always before the control loop, NEVER in the
    // control loop
    // Set collision behavior:
    robot.setCollisionBehavior(
        {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}}, {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}},
        {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}}, {{10.0, 10.0, 9.0, 9.0, 8.0, 7.0, 6.0}},
        {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}}, {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}},
        {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}}, {{10.0, 10.0, 10.0, 12.5, 12.5, 12.5}});

    for (int i = 0; i < 5; i++) {
      std::cout << "Executing motion." << std::endl;
      try {
        double time_max = 4.0;
        double omega_max = 0.2;
        double time = 0.0;
        robot.control([=, &time](const franka::RobotState&) -> franka::JointVelocities {
          double cycle = std::floor(std::pow(-1.0, (time - std::fmod(time, time_max)) / time_max));
          double omega = cycle * omega_max / 2.0 * (1.0 - std::cos(2.0 * M_PI / time_max * time));

          time += 0.001;
          if (time > 2 * time_max) {
            std::cout << std::endl << "Finished motion." << std::endl;
            return franka::Stop;
          }

          return {{0.0, 0.0, omega, 0.0, 0.0, 0.0, 0.0}};
        });
      } catch (const franka::ControlException& e) {
        std::cout << e.what() << std::endl;
        std::cout << "Running error recovery..." << std::endl;
        robot.automaticErrorRecovery();
      }
    }
  } catch (const franka::Exception& e) {
    std::cout << e.what() << std::endl;
    return -1;
  }

  std::cout << "Finished." << std::endl;

  return 0;
}
<|endoftext|>


<commit_before>#include "StdAfx.h"

#define BUFFERSIZE (2 * 1024 * 1024)
char gBuffer[BUFFERSIZE];

/*
    Construct Ultracomm object, connect to server,
    and set/check parameters.
*/
Ultracomm::Ultracomm(const UltracommOptions& myuopt)
    : uopt(myuopt),
      address(myuopt.opt["address"].as<string>()),
      datatype(myuopt.opt["datatype"].as<int>())
{
    connect();
    ult.setDataToAcquire(datatype);
    set_int_imaging_params();
    check_int_imaging_params();
}

/*
   Connect to the Ultrasonix.
*/
void Ultracomm::connect()
{
    if (!ult.connect(address.c_str()))
    {
        throw ConnectionError();
    }
/*
TODO: throw different errors depending on problem. Note that FD_CONNECT error
is when server address is bad (e.g. 123), and SOCKET_ERROR is when we couldn't connect
(address good but not in research mode). Should also test when address is good
but ultrasound machine not running):

C:\build\ultracomm\bin\Debug>ultracomm --address 123 --output asdf
monitorConnection(): FD_CONNECT had ERROR
Could not connect to Ultrasonix.

C:\build\ultracomm\bin\Debug>ultracomm --address 192.168.1.200 --output asdf
monitorConnection(): WSAEnumNetworkEvents() ret SOCKET_ERROR (10093)
CmonitorConnection(): CONNECTION_COMM lost

ould not connect to Ultrasonix.
*/
}

/*
    Disconnect from Ultrasonix.
*/
void Ultracomm::disconnect()
{
    if (ult.isConnected())
    {
        ult.disconnect();
    }
}

/*
  Put Ultrasonix into freeze state and wait for confirmation.
*/
void Ultracomm::wait_for_freeze()
{
    // 1 = FROZEN; 0 = IMAGING
    if (ult.getFreezeState() != 1)
    {
        ult.toggleFreeze();
    }
    // Wait for server to acknowledge it has frozen.
    // TODO: this would be safer with a timeout.
    while (ult.getFreezeState() != 1) {}
	ult.setCompressionStatus(1);
}

/*
  Put ultrasonix into imaging state.
*/
void Ultracomm::wait_for_unfreeze()
{
    // 1 = FROZEN; 0 = IMAGING
    if (ult.getFreezeState() != 0)
    {
        ult.toggleFreeze();
    }
    // Wait for server to acknowledge it has switched to imaging.
    // TODO: this would be safer with a timeout.
    while (ult.getFreezeState() != 0) {}
}

/*
    Set all integer-type Ultrasonix imaging parameters, as specified on the
    command line or in the parameter file.
*/
void Ultracomm::set_int_imaging_params()
{
    po::variables_map params = uopt.opt;
    po::options_description iopts = uopt.int_params;
    for ( auto iter = iopts.options().begin(); iter != iopts.options().end(); ++iter)
    {
        /*
           Ultracomm program options do not contain spaces. Some of the
           parameters used by the ulterius setParamValue() call do contain
           spaces, and none appear to use underscore. The convention is that
           ultracomm program options containing underscore correspond to
           ulterius parameters that have the same name, but with the
           underscores replaced with spaces (' ').

           optname: the name as used in ultracomm program options (underscores)
           ultname: the name as used by ulterius setParamValue() (spaces)
        */
        string optname = (*iter)->long_name();
        if (params.count(optname)) {
            int val = params[optname].as<int>();
            string ultname = boost::replace_all_copy(optname, "_", " ");
            ult.setParamValue(ultname.c_str(), val);
        }
    }

}

/*
    Verify that integer-type Ultrasonix imaging parameters have value as
    specified by user.
*/
void Ultracomm::check_int_imaging_params()
{
    po::variables_map params = uopt.opt;
    if (params.count("b-depth"))
    {
        int val;
        ult.getParamValue("b-depth", val);
        if (val != params["b-depth"].as<int>())
        {
            throw ParameterMismatchError();
        }
    }
}

/*
    Get data from Ultrasonix and save to file.
*/
void Ultracomm::save_data()
{
    po::variables_map params = uopt.opt;
    const string outname = params["output"].as<string>();
	int num_frames = ult.getCineDataCount((uData)datatype);
    uDataDesc desc;
    if (! ult.getDataDescriptor((uData)datatype, desc))
    {
        throw DataDescriptorError();
    }
    if (! ult.isDataAvailable((uData)datatype))
    {
        throw DataError();
    }
    ofstream outfile (outname, ios::out | ios::binary);
    write_header(outfile, desc, num_frames);

	// TODO: figure out why buffer and sz makes program crash
    //const int sz = 2 * 1024 * 1024;
    //char buffer[BUFFERSIZE];  // TODO: determine appropriate sizes on the fly
//    int num_frames = ult.getCineDataCount((uData)datatype);

	// TODO: framesize assumes desc.ss is always a multiple of 8, and that might not be safe.
	int framesize = (desc.ss / 8) * desc.w * desc.h;
    for (int idx = 0; idx < num_frames; idx++)
    {
        ult.getCineData((uData)datatype, idx, false, (char**)&gBuffer, BUFFERSIZE);
        outfile.write(gBuffer, framesize);
    }
    outfile.close();
}

/*
	TODO: header information is probably correct for .bpr files but probably
	not for other datatypes.
*/
void Ultracomm::write_header(ofstream& outfile, const uDataDesc& desc, const int& num_frames)
{
	const int isize = sizeof(__int32);
    static const int fields[] = {
        datatype,
        num_frames,
        desc.w,
        desc.h,
        desc.ss,
        desc.roi.ulx,
        desc.roi.uly,
        desc.roi.urx,
        desc.roi.ury,
        desc.roi.brx,
        desc.roi.bry,
        desc.roi.blx,
        desc.roi.bly
    };
    for (int i = 0; i < 13; ++i) {
	    outfile.write(reinterpret_cast<const char *>(&(__int32)fields[i]), isize);
    }
	int probe = uopt.opt["probe-id"].as<int>();
	outfile.write(reinterpret_cast<const char *>(&(__int32)probe), isize);
    // FIXME: Determine if these are the correct params to put in the header.
    static const string queries[] = {
        "b-freq",
        "vec-freq",
        "frame rate",
        "b-ldensity"
    };
    for (int i = 0; i < 4; ++i) {
        int val;
        ult.getParamValue(queries[i].c_str(), val);
	    outfile.write(reinterpret_cast<const char *>(&(__int32)val), isize);
    }
    // FIXME: Figure out how to determine the value of the 'extra' field.
    // It will probably be added to queries[], but I don't know the param name.
    // For now we'll hard code it with value 0.
    // Don't forget to update the hard-coded length of queries[] in the for
    // loop if this field gets moved into queries[].
    int extra = 0;
	outfile.write(reinterpret_cast<const char *>(&(__int32)extra), isize);
}
<commit_msg>Improve write_header().<commit_after>#include "StdAfx.h"

#define BUFFERSIZE (2 * 1024 * 1024)
char gBuffer[BUFFERSIZE];

/*
    Construct Ultracomm object, connect to server,
    and set/check parameters.
*/
Ultracomm::Ultracomm(const UltracommOptions& myuopt)
    : uopt(myuopt),
      address(myuopt.opt["address"].as<string>()),
      datatype(myuopt.opt["datatype"].as<int>())
{
    connect();
    ult.setDataToAcquire(datatype);
    set_int_imaging_params();
    check_int_imaging_params();
}

/*
   Connect to the Ultrasonix.
*/
void Ultracomm::connect()
{
    if (!ult.connect(address.c_str()))
    {
        throw ConnectionError();
    }
/*
TODO: throw different errors depending on problem. Note that FD_CONNECT error
is when server address is bad (e.g. 123), and SOCKET_ERROR is when we couldn't connect
(address good but not in research mode). Should also test when address is good
but ultrasound machine not running):

C:\build\ultracomm\bin\Debug>ultracomm --address 123 --output asdf
monitorConnection(): FD_CONNECT had ERROR
Could not connect to Ultrasonix.

C:\build\ultracomm\bin\Debug>ultracomm --address 192.168.1.200 --output asdf
monitorConnection(): WSAEnumNetworkEvents() ret SOCKET_ERROR (10093)
CmonitorConnection(): CONNECTION_COMM lost

ould not connect to Ultrasonix.
*/
}

/*
    Disconnect from Ultrasonix.
*/
void Ultracomm::disconnect()
{
    if (ult.isConnected())
    {
        ult.disconnect();
    }
}

/*
  Put Ultrasonix into freeze state and wait for confirmation.
*/
void Ultracomm::wait_for_freeze()
{
    // 1 = FROZEN; 0 = IMAGING
    if (ult.getFreezeState() != 1)
    {
        ult.toggleFreeze();
    }
    // Wait for server to acknowledge it has frozen.
    // TODO: this would be safer with a timeout.
    while (ult.getFreezeState() != 1) {}
	ult.setCompressionStatus(1);
}

/*
  Put ultrasonix into imaging state.
*/
void Ultracomm::wait_for_unfreeze()
{
    // 1 = FROZEN; 0 = IMAGING
    if (ult.getFreezeState() != 0)
    {
        ult.toggleFreeze();
    }
    // Wait for server to acknowledge it has switched to imaging.
    // TODO: this would be safer with a timeout.
    while (ult.getFreezeState() != 0) {}
}

/*
    Set all integer-type Ultrasonix imaging parameters, as specified on the
    command line or in the parameter file.
*/
void Ultracomm::set_int_imaging_params()
{
    po::variables_map params = uopt.opt;
    po::options_description iopts = uopt.int_params;
    for ( auto iter = iopts.options().begin(); iter != iopts.options().end(); ++iter)
    {
        /*
           Ultracomm program options do not contain spaces. Some of the
           parameters used by the ulterius setParamValue() call do contain
           spaces, and none appear to use underscore. The convention is that
           ultracomm program options containing underscore correspond to
           ulterius parameters that have the same name, but with the
           underscores replaced with spaces (' ').

           optname: the name as used in ultracomm program options (underscores)
           ultname: the name as used by ulterius setParamValue() (spaces)
        */
        string optname = (*iter)->long_name();
        if (params.count(optname)) {
            int val = params[optname].as<int>();
            string ultname = boost::replace_all_copy(optname, "_", " ");
            ult.setParamValue(ultname.c_str(), val);
        }
    }
}

/*
    Verify that integer-type Ultrasonix imaging parameters have value as
    specified by user.
*/
void Ultracomm::check_int_imaging_params()
{
    po::variables_map params = uopt.opt;
    if (params.count("b-depth"))
    {
        int val;
        ult.getParamValue("b-depth", val);
        if (val != params["b-depth"].as<int>())
        {
            throw ParameterMismatchError();
        }
    }
}

/*
    Get data from Ultrasonix and save to file.
*/
void Ultracomm::save_data()
{
    po::variables_map params = uopt.opt;
    const string outname = params["output"].as<string>();
	int num_frames = ult.getCineDataCount((uData)datatype);
    uDataDesc desc;
    if (! ult.getDataDescriptor((uData)datatype, desc))
    {
        throw DataDescriptorError();
    }
    if (! ult.isDataAvailable((uData)datatype))
    {
        throw DataError();
    }
    ofstream outfile (outname, ios::out | ios::binary);
    write_header(outfile, desc, num_frames);

	// TODO: figure out why buffer and sz makes program crash
    //const int sz = 2 * 1024 * 1024;
    //char buffer[BUFFERSIZE];  // TODO: determine appropriate sizes on the fly
//    int num_frames = ult.getCineDataCount((uData)datatype);

	// TODO: framesize assumes desc.ss is always a multiple of 8, and that might not be safe.
	int framesize = (desc.ss / 8) * desc.w * desc.h;
    for (int idx = 0; idx < num_frames; idx++)
    {
        ult.getCineData((uData)datatype, idx, false, (char**)&gBuffer, BUFFERSIZE);
        outfile.write(gBuffer, framesize);
    }
    outfile.close();
}

/*
	TODO: header information is probably correct for .bpr files but possibly
	not for other datatypes.
*/
void Ultracomm::write_header(ofstream& outfile, const uDataDesc& desc, const int& num_frames)
{
    // Integer fields that we can write directly. Luckily these all are
    // consecutive fields in the header.
	const int isize = sizeof(__int32);
    static const int fields[] = {
        datatype,
        num_frames,
        desc.w,
        desc.h,
        desc.ss,
        desc.roi.ulx,
        desc.roi.uly,
        desc.roi.urx,
        desc.roi.ury,
        desc.roi.brx,
        desc.roi.bry,
        desc.roi.blx,
        desc.roi.bly,
        uopt.opt["probe-id"].as<int>()
    };
    for (int i = 0; i < sizeof(fields) / sizeof(fields[0]); ++i) {
	    outfile.write(reinterpret_cast<const char *>(&(__int32)fields[i]), isize);
    }

    // Integer fields that we have to query from Ultrasonix. These are also
    // consecutive in the header.
    // FIXME: Determine if these are the correct params to put in the header.
    static const string queries[] = {
        "b-freq",
        "vec-freq",
        "frame rate",
        "b-ldensity"
    };
    for (int i = 0; i < sizeof(queries) / sizeof(queries[0]); ++i) {
        int val;
        ult.getParamValue(queries[i].c_str(), val);
	    outfile.write(reinterpret_cast<const char *>(&(__int32)val), isize);
    }
    // FIXME: Figure out how to determine the value of the 'extra' field.
    // It will probably be added to queries[], but I don't know the param name.
    // For now we'll hard code it with value 0.
    int extra = 0;
	outfile.write(reinterpret_cast<const char *>(&(__int32)extra), isize);
}
<|endoftext|>


<commit_before>#include "buffer.hh"
#include "assert.hh"
#include "editor.hh"
#include "selectors.hh"

using namespace Kakoune;

void test_buffer()
{
    Buffer buffer("test", Buffer::Type::Scratch, "allo ?\nmais que fais la police\n hein ?\n youpi\n");
    assert(buffer.line_count() == 4);

    BufferIterator i = buffer.begin();
    assert(*i == 'a');
    i += 6;
    assert(buffer.line_and_column_at(i) == BufferCoord{0 COMMA 6});
    i += 1;
    assert(buffer.line_and_column_at(i) == BufferCoord{1 COMMA 0});
    --i;
    assert(buffer.line_and_column_at(i) == BufferCoord{0 COMMA 6});
    ++i;
    assert(buffer.line_and_column_at(i) == BufferCoord{1 COMMA 0});
    buffer.insert(i, "tchou kanaky\n");
    assert(buffer.line_count() == 5);

    BufferIterator begin = buffer.iterator_at({ 4, 1 });
    BufferIterator end = buffer.iterator_at({ 4, 5 }) + 1;
    String str = buffer.string(begin, end);
    assert(str == "youpi");

    // check insert at end behaviour: auto add end of line if necessary
    begin = buffer.end() - 1;
    buffer.insert(buffer.end(), "tchou");
    assert(buffer.string(begin+1, buffer.end()) == "tchou\n");

    begin = buffer.end() - 1;
    buffer.insert(buffer.end(), "kanaky\n");
    assert(buffer.string(begin+1, buffer.end()) == "kanaky\n");
}

void test_editor()
{
    Buffer buffer("test", Buffer::Type::Scratch, "test\n\nyoupi\n");
    Editor editor(buffer);

    using namespace std::placeholders;

    editor.select(select_whole_buffer);
    editor.multi_select(std::bind(select_all_matches, _1, "\\n\\h*"));
    for (auto& sel : editor.selections())
    {
        assert(*sel.begin() == '\n');
        editor.buffer().erase(sel.begin(), sel.end());
    }
}

void test_incremental_inserter()
{
    Buffer buffer("test", Buffer::Type::Scratch, "test\n\nyoupi\nmatin\n");
    Editor editor(buffer);

    editor.select(buffer.begin());
    {
        IncrementalInserter inserter(editor, InsertMode::OpenLineAbove);
        assert(editor.is_editing());
        assert(editor.selections().size() == 1);
        assert(editor.selections().front().first() == buffer.begin());
        assert(editor.selections().front().last() == buffer.begin());
        assert(*buffer.begin() == L'\n');
    }
    assert(not editor.is_editing());
}
void test_string()
{
   assert(int_to_str(124)  == "124");
   assert(int_to_str(-129) == "-129");
   assert(int_to_str(0)    == "0");

   assert(String("youpi ") + "matin" == "youpi matin");

   std::vector<String> splited = split("youpi:matin::tchou", ':');
   assert(splited[0] == "youpi");
   assert(splited[1] == "matin");
   assert(splited[2] == "");
   assert(splited[3] == "tchou");
}

void run_unit_tests()
{
    test_string();
    test_buffer();
    test_editor();
    test_incremental_inserter();
}
<commit_msg>add basic utf8 unit test<commit_after>#include "buffer.hh"
#include "assert.hh"
#include "editor.hh"
#include "selectors.hh"

using namespace Kakoune;

void test_buffer()
{
    Buffer buffer("test", Buffer::Type::Scratch, "allo ?\nmais que fais la police\n hein ?\n youpi\n");
    assert(buffer.line_count() == 4);

    BufferIterator i = buffer.begin();
    assert(*i == 'a');
    i += 6;
    assert(buffer.line_and_column_at(i) == BufferCoord{0 COMMA 6});
    i += 1;
    assert(buffer.line_and_column_at(i) == BufferCoord{1 COMMA 0});
    --i;
    assert(buffer.line_and_column_at(i) == BufferCoord{0 COMMA 6});
    ++i;
    assert(buffer.line_and_column_at(i) == BufferCoord{1 COMMA 0});
    buffer.insert(i, "tchou kanaky\n");
    assert(buffer.line_count() == 5);

    BufferIterator begin = buffer.iterator_at({ 4, 1 });
    BufferIterator end = buffer.iterator_at({ 4, 5 }) + 1;
    String str = buffer.string(begin, end);
    assert(str == "youpi");

    // check insert at end behaviour: auto add end of line if necessary
    begin = buffer.end() - 1;
    buffer.insert(buffer.end(), "tchou");
    assert(buffer.string(begin+1, buffer.end()) == "tchou\n");

    begin = buffer.end() - 1;
    buffer.insert(buffer.end(), "kanaky\n");
    assert(buffer.string(begin+1, buffer.end()) == "kanaky\n");
}

void test_editor()
{
    Buffer buffer("test", Buffer::Type::Scratch, "test\n\nyoupi\n");
    Editor editor(buffer);

    using namespace std::placeholders;

    editor.select(select_whole_buffer);
    editor.multi_select(std::bind(select_all_matches, _1, "\\n\\h*"));
    for (auto& sel : editor.selections())
    {
        assert(*sel.begin() == '\n');
        editor.buffer().erase(sel.begin(), sel.end());
    }
}

void test_incremental_inserter()
{
    Buffer buffer("test", Buffer::Type::Scratch, "test\n\nyoupi\nmatin\n");
    Editor editor(buffer);

    editor.select(buffer.begin());
    {
        IncrementalInserter inserter(editor, InsertMode::OpenLineAbove);
        assert(editor.is_editing());
        assert(editor.selections().size() == 1);
        assert(editor.selections().front().first() == buffer.begin());
        assert(editor.selections().front().last() == buffer.begin());
        assert(*buffer.begin() == L'\n');
    }
    assert(not editor.is_editing());
}

void test_utf8()
{
    String str = "maïs mélange bientôt";
    assert(utf8::distance(str.begin(), str.end()) == 20);
    assert(utf8::codepoint(str.begin() + 2) == 0x00EF);
}

void test_string()
{
   assert(int_to_str(124)  == "124");
   assert(int_to_str(-129) == "-129");
   assert(int_to_str(0)    == "0");

   assert(String("youpi ") + "matin" == "youpi matin");

   std::vector<String> splited = split("youpi:matin::tchou", ':');
   assert(splited[0] == "youpi");
   assert(splited[1] == "matin");
   assert(splited[2] == "");
   assert(splited[3] == "tchou");
}

void run_unit_tests()
{
    test_utf8();
    test_string();
    test_buffer();
    test_editor();
    test_incremental_inserter();
}
<|endoftext|>


<commit_before>// test_0.cpp written by JaeHyuk Kwak
#include "stdafx.h"
#include "unit_test_logic.hpp"
using namespace unit_test_logic_ns;
int main( int, const char ** )
{
	fixture f;
	f.test_case( "Boolean test", []
	{
		test_true( true );
		test_true( 2 <= 3 );
		test_false( false );
	} );
	f.test_case( "Equality test; simple", []
	{
		test( logic( 0 ) == 0 );
		test( logic( 3 ) == 3 );
		test( logic( 0 ) == 0.f, "Forwarding different types except bool" );
	} );
	f.test_case( "Inequality test; simple", []
	{
		test( logic( 0 ) != 1 );
		test( logic( 0 ) != 1.f, "Forwarding different types except bool" );
		test( ( logic( 0 ) != 1 ) != 2, "3 != 4 && 3 != 5" );
	} );
	f.test_case( "Compare '>' test; simple", []
	{
		test( logic( 3 ) > 2 );
		test( logic( 3 ) > 2 > 1 );
	} );
	f.test_case( "Compare '>=' test; simple", []
	{
		test( logic( 3 ) >= 3 );
		test( logic( 3 ) >= 3 >= 2 );
	} );
	f.test_case( "Compare '<' test; simple", []
	{
		test( logic( 3 ) < 4 );
		test( logic( 3 ) < 4 < 5 );
	} );
	f.test_case( "Compare '<=' test; simple", []
	{
		test( logic( 3 ) <= 3 );
		test( logic( 3 ) <= 3 <= 4 );
	} );
	f.test_case( "Unconditional success", []
	{
		test_success();
	} );
	f.test_case_must_fail( "Unconditional fail", []
	{
		test_fail();
	} );
	f.test_case( "Logic OR test; simple", []
	{
		test_true( ( logic( 0 ) == 0 ).out() || false );
		test_true( ( logic( 0 ) == 1 ) .out()|| true );
		test_true( false || ( logic( 0 ) == 0 ).out() );
		test_true( true || ( logic( 0 ) == 1 ).out() );
	} );
	{
		const char *str = "content";
		const char *str2 = "_content" + 1;
		f.test_case( "C-string test; raw-string pointer", [&]
		{
			test( logic( str ) == str );
			test( logic( str ) != str2 );
		} );
		f.test_case_must_fail( "C-string test; raw-string pointer", [&]
		{
			test( logic( str ) == str2, "the content of C-string will be shown" );
		} );
		f.test_case( "std::string test", [&]
		{
			test( logic( string( str ) ) == str2 );
		} );
		f.test_case_must_fail( "std::string test", [&]
		{
			test( logic( string( str ) ) != str2 );
		} );
	}
	f.test_case( "String test; ignore-case", []
	{
		const char *A = "A";
		const char *a = "a";
		test( logic( lowercase_string( A ) ) == lowercase_string( a ) );
	} );
	f.test_case( "Exception catch test", []
	{
		test_must_throw_exception< invalid_argument >( []
		{
			throw invalid_argument( "" );
		} );
	} );
	f.test_case_must_fail( "Exception catch test", []
	{
		test_must_throw_exception< invalid_argument >( []
		{} );
	} );
	f.test_case( "Exception ignore test", []
	{
		test_ignore_exception< invalid_argument >( []
		{
			throw invalid_argument( "" );
		} );
	} );
	f.test_case( "Exception ignore test; no exception thrown", []
	{
		test_ignore_exception< invalid_argument >( []
		{} );
	} );

	// Macro below could be replaced with a template function,
	// but it wasn't any easier to read.
	f.test_case( "Equality test; int", []
	{
		int lvalue_inlogic = 0;
		int lvalue = 0;
		#define TESTING_OPERATOR ==
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Equality test; float", []
	{
		float lvalue_inlogic = 0.f;
		int lvalue = 0.f;
		#define TESTING_OPERATOR ==
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Inequality test; int", []
	{
		int lvalue_inlogic = 2;
		int lvalue = 1;
		#define TESTING_OPERATOR !=
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Inequality test; float", []
	{
		float lvalue_inlogic = 2;
		int lvalue = 1;
		#define TESTING_OPERATOR !=
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Compare '>' test; int", []
	{
		int lvalue_inlogic = 1;
		int lvalue = -1;
		#define TESTING_OPERATOR >
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Compare '>' test; float", []
	{
		float lvalue_inlogic = 1.f;
		int lvalue = -1;
		#define TESTING_OPERATOR >
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Equality test bool", []
	{
		// rvalue-bool type on equality test is not allowed.
		// It is to prevent mistakes that can be caused by precedence.
		//
		// Because operator>= has higher precedence,
		// "logic( 0 ) == 0 >= 0" is same to "logic( 0 ) == true".
		//
		// The intention would be "( logic( 0 ) == 0 ) >= 0",
		// which should result in true because "0 == 0" and "0 >= 0".
		// Note that the second zero and 3rd zero are not compared.
		//
		// But due to the operator precedence, what actually happens is
		// "logic( 0 ) == true",
		// which results in false after type-casting 0 to bool.

#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 1
		test( logic( 0 ) == false, "wouldn't compile to prevent mistake." );
#endif
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 2
		test( logic( 0 ) == 0 >= 0, "mistake that needs to be prevented." );
#endif
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 3
		bool lvalue = false;
		test( logic( 0 ) == lvalue, "L-Value" );
#endif
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 4
		const bool const_lvalue = false;
		test( logic( 0 ) == const_lvalue, "L-Value const" );
#endif

		test_true( 0 == false, "workaround #1" );
		test( ( logic( 0 ) == 0 ) >= 0, "workaround #2" );
	} );
	f.test_case( "Message test", []
	{
		test_true( true, "Message to show when failed" );
		test_true( true, "Message", " to", " show", " when", " failed" );
		test( logic( 3 ) != 4.f, "int( ", 3, " ) != ", 4.f );
	} );
	f.test_case( "Boolean test with Macro", []
	{
		TEST_TRUE( true );
		TEST_TRUE( true );
		TEST_TRUE( 2 <= 3 );
		TEST_FALSE( false, "Message when succeed." );
		TEST_TRUE( true, "Message when failed." );
	} );
	f.test_case_must_fail( "Boolean test with Macro", []
	{
		TEST_TRUE( 2 >= 3 );
	} );
	f.test_case( "Unconditional success with Macro", []
	{
		TEST_SUCCESS();
	} );
	f.test_case_must_fail( "Unconditional fail with Macro", []
	{
		TEST_FAIL();
	} );
	f.test_case( "bool type is not allowed in logic_stream", []
	{
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 5
		test( logic( true ), "R-Value" );
#endif

#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 6
		bool lvalue = true;
		test( logic( lvalue ), "L-Value" );
#endif

#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 7
		const bool const_lvalue = true;
		test( logic( const_lvalue ), "L-Value const" );
#endif
	} );
	return f.failed_count();
}
<commit_msg>Fix mismatching common on one of test cases.<commit_after>// test_0.cpp written by JaeHyuk Kwak
#include "stdafx.h"
#include "unit_test_logic.hpp"
using namespace unit_test_logic_ns;
int main( int, const char ** )
{
	fixture f;
	f.test_case( "Boolean test", []
	{
		test_true( true );
		test_true( 2 <= 3 );
		test_false( false );
	} );
	f.test_case( "Equality test; simple", []
	{
		test( logic( 0 ) == 0 );
		test( logic( 3 ) == 3 );
		test( logic( 0 ) == 0.f, "Forwarding different types except bool" );
	} );
	f.test_case( "Inequality test; simple", []
	{
		test( logic( 0 ) != 1 );
		test( logic( 0 ) != 1.f, "Forwarding different types except bool" );
		test( ( logic( 0 ) != 1 ) != 2, "0 != 1 && 0 != 2" );
	} );
	f.test_case( "Compare '>' test; simple", []
	{
		test( logic( 3 ) > 2 );
		test( logic( 3 ) > 2 > 1 );
	} );
	f.test_case( "Compare '>=' test; simple", []
	{
		test( logic( 3 ) >= 3 );
		test( logic( 3 ) >= 3 >= 2 );
	} );
	f.test_case( "Compare '<' test; simple", []
	{
		test( logic( 3 ) < 4 );
		test( logic( 3 ) < 4 < 5 );
	} );
	f.test_case( "Compare '<=' test; simple", []
	{
		test( logic( 3 ) <= 3 );
		test( logic( 3 ) <= 3 <= 4 );
	} );
	f.test_case( "Unconditional success", []
	{
		test_success();
	} );
	f.test_case_must_fail( "Unconditional fail", []
	{
		test_fail();
	} );
	f.test_case( "Logic OR test; simple", []
	{
		test_true( ( logic( 0 ) == 0 ).out() || false );
		test_true( ( logic( 0 ) == 1 ) .out()|| true );
		test_true( false || ( logic( 0 ) == 0 ).out() );
		test_true( true || ( logic( 0 ) == 1 ).out() );
	} );
	{
		const char *str = "content";
		const char *str2 = "_content" + 1;
		f.test_case( "C-string test; raw-string pointer", [&]
		{
			test( logic( str ) == str );
			test( logic( str ) != str2 );
		} );
		f.test_case_must_fail( "C-string test; raw-string pointer", [&]
		{
			test( logic( str ) == str2, "the content of C-string will be shown" );
		} );
		f.test_case( "std::string test", [&]
		{
			test( logic( string( str ) ) == str2 );
		} );
		f.test_case_must_fail( "std::string test", [&]
		{
			test( logic( string( str ) ) != str2 );
		} );
	}
	f.test_case( "String test; ignore-case", []
	{
		const char *A = "A";
		const char *a = "a";
		test( logic( lowercase_string( A ) ) == lowercase_string( a ) );
	} );
	f.test_case( "Exception catch test", []
	{
		test_must_throw_exception< invalid_argument >( []
		{
			throw invalid_argument( "" );
		} );
	} );
	f.test_case_must_fail( "Exception catch test", []
	{
		test_must_throw_exception< invalid_argument >( []
		{} );
	} );
	f.test_case( "Exception ignore test", []
	{
		test_ignore_exception< invalid_argument >( []
		{
			throw invalid_argument( "" );
		} );
	} );
	f.test_case( "Exception ignore test; no exception thrown", []
	{
		test_ignore_exception< invalid_argument >( []
		{} );
	} );

	// Macro below could be replaced with a template function,
	// but it wasn't any easier to read.
	f.test_case( "Equality test; int", []
	{
		int lvalue_inlogic = 0;
		int lvalue = 0;
		#define TESTING_OPERATOR ==
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Equality test; float", []
	{
		float lvalue_inlogic = 0.f;
		int lvalue = 0.f;
		#define TESTING_OPERATOR ==
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Inequality test; int", []
	{
		int lvalue_inlogic = 2;
		int lvalue = 1;
		#define TESTING_OPERATOR !=
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Inequality test; float", []
	{
		float lvalue_inlogic = 2;
		int lvalue = 1;
		#define TESTING_OPERATOR !=
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Compare '>' test; int", []
	{
		int lvalue_inlogic = 1;
		int lvalue = -1;
		#define TESTING_OPERATOR >
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Compare '>' test; float", []
	{
		float lvalue_inlogic = 1.f;
		int lvalue = -1;
		#define TESTING_OPERATOR >
		#include "test_0.operator.hpp"
		#undef TESTING_OPERATOR
	} );
	f.test_case( "Equality test bool", []
	{
		// rvalue-bool type on equality test is not allowed.
		// It is to prevent mistakes that can be caused by precedence.
		//
		// Because operator>= has higher precedence,
		// "logic( 0 ) == 0 >= 0" is same to "logic( 0 ) == true".
		//
		// The intention would be "( logic( 0 ) == 0 ) >= 0",
		// which should result in true because "0 == 0" and "0 >= 0".
		// Note that the second zero and 3rd zero are not compared.
		//
		// But due to the operator precedence, what actually happens is
		// "logic( 0 ) == true",
		// which results in false after type-casting 0 to bool.

#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 1
		test( logic( 0 ) == false, "wouldn't compile to prevent mistake." );
#endif
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 2
		test( logic( 0 ) == 0 >= 0, "mistake that needs to be prevented." );
#endif
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 3
		bool lvalue = false;
		test( logic( 0 ) == lvalue, "L-Value" );
#endif
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 4
		const bool const_lvalue = false;
		test( logic( 0 ) == const_lvalue, "L-Value const" );
#endif

		test_true( 0 == false, "workaround #1" );
		test( ( logic( 0 ) == 0 ) >= 0, "workaround #2" );
	} );
	f.test_case( "Message test", []
	{
		test_true( true, "Message to show when failed" );
		test_true( true, "Message", " to", " show", " when", " failed" );
		test( logic( 3 ) != 4.f, "int( ", 3, " ) != ", 4.f );
	} );
	f.test_case( "Boolean test with Macro", []
	{
		TEST_TRUE( true );
		TEST_TRUE( true );
		TEST_TRUE( 2 <= 3 );
		TEST_FALSE( false, "Message when succeed." );
		TEST_TRUE( true, "Message when failed." );
	} );
	f.test_case_must_fail( "Boolean test with Macro", []
	{
		TEST_TRUE( 2 >= 3 );
	} );
	f.test_case( "Unconditional success with Macro", []
	{
		TEST_SUCCESS();
	} );
	f.test_case_must_fail( "Unconditional fail with Macro", []
	{
		TEST_FAIL();
	} );
	f.test_case( "bool type is not allowed in logic_stream", []
	{
#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 5
		test( logic( true ), "R-Value" );
#endif

#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 6
		bool lvalue = true;
		test( logic( lvalue ), "L-Value" );
#endif

#if defined( COMPILE_FAIL_TEST ) && COMPILE_FAIL_TEST == 7
		const bool const_lvalue = true;
		test( logic( const_lvalue ), "L-Value const" );
#endif
	} );
	return f.failed_count();
}
<|endoftext|>


<commit_before>// Copyright 2014 The Crashpad Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "util/numeric/in_range_cast.h"

#include <stdint.h>

#include <limits>

#include "gtest/gtest.h"

namespace crashpad {
namespace test {
namespace {

const int32_t kInt32Min = std::numeric_limits<int32_t>::min();
const int64_t kInt64Min = std::numeric_limits<int64_t>::min();

TEST(InRangeCast, Uint32) {
  EXPECT_EQ(0u, InRangeCast<uint32_t>(0, 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(1, 1));
  EXPECT_EQ(2u, InRangeCast<uint32_t>(2, 1));
  EXPECT_EQ(0u, InRangeCast<uint32_t>(-1, 0));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(-1, 1));
  EXPECT_EQ(2u, InRangeCast<uint32_t>(-1, 2));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint32_t>(0xffffffffu, 1));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint32_t>(UINT64_C(0xffffffff), 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(UINT64_C(0x100000000), 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(UINT64_C(0x100000001), 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(kInt32Min, 1));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint32_t>(-1, 0xffffffffu));
}

TEST(InRangeCast, Int32) {
  EXPECT_EQ(0, InRangeCast<int32_t>(0, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(1, 1));
  EXPECT_EQ(2, InRangeCast<int32_t>(2, 1));
  EXPECT_EQ(-1, InRangeCast<int32_t>(-1, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int32_t>(0x7fffffff, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int32_t>(0x7fffffffu, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(0x80000000u, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(0xffffffffu, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(INT64_C(0x80000000), 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(INT64_C(0xffffffff), 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(INT64_C(0x100000000), 1));
  EXPECT_EQ(kInt32Min, InRangeCast<int32_t>(kInt32Min, 1));
  EXPECT_EQ(kInt32Min,
            InRangeCast<int32_t>(implicit_cast<int64_t>(kInt32Min), 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(implicit_cast<int64_t>(kInt32Min) - 1, 1));
  EXPECT_EQ(0, InRangeCast<int32_t>(0xffffffffu, 0));
  EXPECT_EQ(-1, InRangeCast<int32_t>(0xffffffffu, -1));
  EXPECT_EQ(kInt32Min, InRangeCast<int32_t>(0xffffffffu, kInt32Min));
  EXPECT_EQ(0x7fffffff, InRangeCast<int32_t>(0xffffffffu, 0x7fffffff));
}

TEST(InRangeCast, Uint64) {
  EXPECT_EQ(0u, InRangeCast<uint64_t>(0, 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(1, 1));
  EXPECT_EQ(2u, InRangeCast<uint64_t>(2, 1));
  EXPECT_EQ(0u, InRangeCast<uint64_t>(-1, 0));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(-1, 1));
  EXPECT_EQ(2u, InRangeCast<uint64_t>(-1, 2));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint64_t>(0xffffffffu, 1));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint64_t>(UINT64_C(0xffffffff), 1));
  EXPECT_EQ(UINT64_C(0x100000000),
            InRangeCast<uint64_t>(UINT64_C(0x100000000), 1));
  EXPECT_EQ(UINT64_C(0x100000001),
            InRangeCast<uint64_t>(UINT64_C(0x100000001), 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(kInt32Min, 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(INT64_C(-1), 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(kInt32Min, 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(kInt64Min, 1));
  EXPECT_EQ(UINT64_C(0xffffffffffffffff),
            InRangeCast<uint64_t>(-1, UINT64_C(0xffffffffffffffff)));
}

TEST(InRangeCast, Int64) {
  EXPECT_EQ(0, InRangeCast<int64_t>(0, 1));
  EXPECT_EQ(1, InRangeCast<int64_t>(1, 1));
  EXPECT_EQ(2, InRangeCast<int64_t>(2, 1));
  EXPECT_EQ(-1, InRangeCast<int64_t>(-1, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int64_t>(0x7fffffff, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int64_t>(0x7fffffffu, 1));
  EXPECT_EQ(INT64_C(0x80000000), InRangeCast<int64_t>(0x80000000u, 1));
  EXPECT_EQ(INT64_C(0xffffffff), InRangeCast<int64_t>(0xffffffffu, 1));
  EXPECT_EQ(INT64_C(0x80000000), InRangeCast<int64_t>(INT64_C(0x80000000), 1));
  EXPECT_EQ(INT64_C(0xffffffff), InRangeCast<int64_t>(INT64_C(0xffffffff), 1));
  EXPECT_EQ(INT64_C(0x100000000),
            InRangeCast<int64_t>(INT64_C(0x100000000), 1));
  EXPECT_EQ(INT64_C(0x7fffffffffffffff),
            InRangeCast<int64_t>(INT64_C(0x7fffffffffffffff), 1));
  EXPECT_EQ(1, InRangeCast<int64_t>(UINT64_C(0x8000000000000000), 1));
  EXPECT_EQ(1, InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), 1));
  EXPECT_EQ(kInt32Min, InRangeCast<int64_t>(kInt32Min, 1));
  EXPECT_EQ(kInt32Min,
            InRangeCast<int64_t>(implicit_cast<int64_t>(kInt32Min), 1));
  EXPECT_EQ(0, InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), 0));
  EXPECT_EQ(-1, InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), -1));
  EXPECT_EQ(kInt64Min,
            InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), kInt64Min));
  EXPECT_EQ(INT64_C(0x7fffffffffffffff),
            InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff),
                                 INT64_C(0x7fffffffffffffff)));
}

}  // namespace
}  // namespace test
}  // namespace crashpad
<commit_msg>Add a few more expectations to crashpad_util_test InRangeCast<commit_after>// Copyright 2014 The Crashpad Authors. All rights reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//     http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "util/numeric/in_range_cast.h"

#include <stdint.h>

#include <limits>

#include "gtest/gtest.h"

namespace crashpad {
namespace test {
namespace {

const int32_t kInt32Min = std::numeric_limits<int32_t>::min();
const int64_t kInt64Min = std::numeric_limits<int64_t>::min();

TEST(InRangeCast, Uint32) {
  EXPECT_EQ(0u, InRangeCast<uint32_t>(0, 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(1, 1));
  EXPECT_EQ(2u, InRangeCast<uint32_t>(2, 1));
  EXPECT_EQ(0u, InRangeCast<uint32_t>(-1, 0));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(-1, 1));
  EXPECT_EQ(2u, InRangeCast<uint32_t>(-1, 2));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint32_t>(0xffffffffu, 1));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint32_t>(UINT64_C(0xffffffff), 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(UINT64_C(0x100000000), 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(UINT64_C(0x100000001), 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(kInt32Min, 1));
  EXPECT_EQ(1u, InRangeCast<uint32_t>(kInt64Min, 1));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint32_t>(-1, 0xffffffffu));
}

TEST(InRangeCast, Int32) {
  EXPECT_EQ(0, InRangeCast<int32_t>(0, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(1, 1));
  EXPECT_EQ(2, InRangeCast<int32_t>(2, 1));
  EXPECT_EQ(-1, InRangeCast<int32_t>(-1, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int32_t>(0x7fffffff, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int32_t>(0x7fffffffu, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(0x80000000u, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(0xffffffffu, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(INT64_C(0x80000000), 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(INT64_C(0xffffffff), 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(INT64_C(0x100000000), 1));
  EXPECT_EQ(kInt32Min, InRangeCast<int32_t>(kInt32Min, 1));
  EXPECT_EQ(kInt32Min,
            InRangeCast<int32_t>(implicit_cast<int64_t>(kInt32Min), 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(implicit_cast<int64_t>(kInt32Min) - 1, 1));
  EXPECT_EQ(1, InRangeCast<int32_t>(kInt64Min, 1));
  EXPECT_EQ(0, InRangeCast<int32_t>(0xffffffffu, 0));
  EXPECT_EQ(-1, InRangeCast<int32_t>(0xffffffffu, -1));
  EXPECT_EQ(kInt32Min, InRangeCast<int32_t>(0xffffffffu, kInt32Min));
  EXPECT_EQ(0x7fffffff, InRangeCast<int32_t>(0xffffffffu, 0x7fffffff));
}

TEST(InRangeCast, Uint64) {
  EXPECT_EQ(0u, InRangeCast<uint64_t>(0, 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(1, 1));
  EXPECT_EQ(2u, InRangeCast<uint64_t>(2, 1));
  EXPECT_EQ(0u, InRangeCast<uint64_t>(-1, 0));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(-1, 1));
  EXPECT_EQ(2u, InRangeCast<uint64_t>(-1, 2));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint64_t>(0xffffffffu, 1));
  EXPECT_EQ(0xffffffffu, InRangeCast<uint64_t>(UINT64_C(0xffffffff), 1));
  EXPECT_EQ(UINT64_C(0x100000000),
            InRangeCast<uint64_t>(UINT64_C(0x100000000), 1));
  EXPECT_EQ(UINT64_C(0x100000001),
            InRangeCast<uint64_t>(UINT64_C(0x100000001), 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(kInt32Min, 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(INT64_C(-1), 1));
  EXPECT_EQ(1u, InRangeCast<uint64_t>(kInt64Min, 1));
  EXPECT_EQ(UINT64_C(0xffffffffffffffff),
            InRangeCast<uint64_t>(-1, UINT64_C(0xffffffffffffffff)));
}

TEST(InRangeCast, Int64) {
  EXPECT_EQ(0, InRangeCast<int64_t>(0, 1));
  EXPECT_EQ(1, InRangeCast<int64_t>(1, 1));
  EXPECT_EQ(2, InRangeCast<int64_t>(2, 1));
  EXPECT_EQ(-1, InRangeCast<int64_t>(-1, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int64_t>(0x7fffffff, 1));
  EXPECT_EQ(0x7fffffff, InRangeCast<int64_t>(0x7fffffffu, 1));
  EXPECT_EQ(INT64_C(0x80000000), InRangeCast<int64_t>(0x80000000u, 1));
  EXPECT_EQ(INT64_C(0xffffffff), InRangeCast<int64_t>(0xffffffffu, 1));
  EXPECT_EQ(INT64_C(0x80000000), InRangeCast<int64_t>(INT64_C(0x80000000), 1));
  EXPECT_EQ(INT64_C(0xffffffff), InRangeCast<int64_t>(INT64_C(0xffffffff), 1));
  EXPECT_EQ(INT64_C(0x100000000),
            InRangeCast<int64_t>(INT64_C(0x100000000), 1));
  EXPECT_EQ(INT64_C(0x7fffffffffffffff),
            InRangeCast<int64_t>(INT64_C(0x7fffffffffffffff), 1));
  EXPECT_EQ(INT64_C(0x7fffffffffffffff),
            InRangeCast<int64_t>(UINT64_C(0x7fffffffffffffff), 1));
  EXPECT_EQ(1, InRangeCast<int64_t>(UINT64_C(0x8000000000000000), 1));
  EXPECT_EQ(1, InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), 1));
  EXPECT_EQ(kInt32Min, InRangeCast<int64_t>(kInt32Min, 1));
  EXPECT_EQ(kInt32Min,
            InRangeCast<int64_t>(implicit_cast<int64_t>(kInt32Min), 1));
  EXPECT_EQ(kInt64Min, InRangeCast<int64_t>(kInt64Min, 1));
  EXPECT_EQ(0, InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), 0));
  EXPECT_EQ(-1, InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), -1));
  EXPECT_EQ(kInt64Min,
            InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff), kInt64Min));
  EXPECT_EQ(INT64_C(0x7fffffffffffffff),
            InRangeCast<int64_t>(UINT64_C(0xffffffffffffffff),
                                 INT64_C(0x7fffffffffffffff)));
}

}  // namespace
}  // namespace test
}  // namespace crashpad
<|endoftext|>


<commit_before><commit_msg>Refactoring, no change in end result<commit_after><|endoftext|>


<commit_before><commit_msg>Add Asturian, Slovenian, and Spanish translations of keymanes for Windows<commit_after><|endoftext|>


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

Licensed to the OpenCOR team under one or more contributor license agreements.
See the NOTICE.txt file distributed with this work for additional information
regarding copyright ownership. The OpenCOR team licenses this file to you under
the Apache License, Version 2.0 (the "License"); you may not use this file
except in compliance with the License. You may obtain a copy of the License at

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

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

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

//==============================================================================
// Compiler engine class
//==============================================================================

#include "compilerengine.h"
#include "compilermath.h"
#include "corecliutils.h"

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

#include <QApplication>
#include <QFile>
#include <QIODevice>
#include <QTemporaryFile>
#include <QTextStream>

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

#include "llvmdisablewarnings.h"
    #include "llvm/IR/LLVMContext.h"
    #include "llvm/IR/Module.h"
    #include "llvm/Support/TargetSelect.h"
    #include "llvm/Support/Host.h"

    #include "clang/Basic/DiagnosticOptions.h"
    #include "clang/CodeGen/CodeGenAction.h"
    #include "clang/Driver/Compilation.h"
    #include "clang/Driver/Driver.h"
    #include "clang/Driver/Tool.h"
    #include "clang/Frontend/CompilerInstance.h"
    #include "clang/Frontend/TextDiagnosticPrinter.h"
#include "llvmenablewarnings.h"

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

#include <string>

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

namespace OpenCOR {
namespace Compiler {

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

CompilerEngine::CompilerEngine() :
    mExecutionEngine(std::unique_ptr<llvm::ExecutionEngine>()),
    mError(QString())
{
}

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

CompilerEngine::~CompilerEngine()
{
    // Reset ourselves

    reset();
}

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

void CompilerEngine::reset(const bool &pResetError)
{
    // Reset some internal objects

    delete mExecutionEngine.release();

    mExecutionEngine = std::unique_ptr<llvm::ExecutionEngine>();

    if (pResetError)
        mError = QString();
}

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

bool CompilerEngine::hasError() const
{
    // Return whether an error occurred

    return mError.size();
}

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

QString CompilerEngine::error() const
{
    // Return the compiler engine's error

    return mError;
}

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

bool CompilerEngine::compileCode(const QString &pCode)
{
    // Reset our compiler engine

    reset();

    // Determine our target triple
    // Note: normally, we would call llvm::sys::getProcessTriple(), but this
    //       returns the information about the system on which LLVM was built.
    //       In most cases it is fine, but on OS X it may be a problem. Indeed,
    //       with OS X 10.9, Apple decided to extend the C standard by adding
    //       some functions (e.g. __exp10()). So, if the given code needs one of
    //       those functions, then OpenCOR will crash if run on an 'old' version
    //       of OS X. So, to avoid this issue, we set the target triple
    //       ourselves, based on the system on which OpenCOR is being used...

    std::string targetTripleString;

#if defined(Q_OS_WIN)
    targetTripleString = (sizeof(void *) == 4)?"i686-pc-win32":"x86_64-pc-win32";
#elif defined(Q_OS_LINUX)
    targetTripleString = (sizeof(void *) == 4)?"i686-pc-linux-gnu":"x86_64-pc-linux-gnu";
#elif defined(Q_OS_MAC)
    targetTripleString = "x86_64-apple-darwin"+std::to_string(QSysInfo::MacintoshVersion+2);
#else
    #error Unsupported platform
#endif

    llvm::Triple targetTriple(targetTripleString);

    // Check whether the target triple supports the COFF binary format and, if
    // so, set its object format to ELF
    // Note: indeed, for now, MCJIT only works through the ELF object format on
    //       Windows...

    if (targetTriple.isOSBinFormatCOFF())
        targetTriple.setObjectFormat(llvm::Triple::ELF);

    // Get a driver to compile our code

#ifdef QT_DEBUG
    llvm::raw_ostream &outputStream = llvm::outs();
#else
    llvm::raw_ostream &outputStream = llvm::nulls();
#endif
    llvm::IntrusiveRefCntPtr<clang::DiagnosticOptions> diagnosticOptions = new clang::DiagnosticOptions();

    clang::DiagnosticsEngine diagnosticsEngine(llvm::IntrusiveRefCntPtr<clang::DiagnosticIDs>(new clang::DiagnosticIDs()),
                                               &*diagnosticOptions,
                                               new clang::TextDiagnosticPrinter(outputStream, &*diagnosticOptions));

    clang::driver::Driver driver("clang", targetTriple.str(), diagnosticsEngine);

    driver.setCheckInputsExist(false);

    // Get a compilation object to which we pass some arguments

    llvm::StringRef dummyFileName("dummyFile.c");

    llvm::SmallVector<const char *, 16> compilationArguments;

    compilationArguments.push_back("clang");
    compilationArguments.push_back("-fsyntax-only");
    compilationArguments.push_back("-O3");
    compilationArguments.push_back("-ffast-math");
    compilationArguments.push_back("-Werror");
    compilationArguments.push_back(dummyFileName.data());

    std::unique_ptr<clang::driver::Compilation> compilation(driver.BuildCompilation(compilationArguments));

    if (!compilation) {
        mError = tr("the compilation object could not be created");

        return false;
    }

    // The compilation object should have only one command, so if it doesn't
    // then something went wrong

    const clang::driver::JobList &jobList = compilation->getJobs();

    if (    (jobList.size() != 1)
        || !llvm::isa<clang::driver::Command>(*jobList.begin())) {
        mError = tr("the compilation object must contain only one command");

        return false;
    }

    // Retrieve the command job

    const clang::driver::Command &command = llvm::cast<clang::driver::Command>(*jobList.begin());
    QString commandName = command.getCreator().getName();

    if (commandName.compare("clang")) {
        mError = tr("a clang command was expected, but a %1 command was found instead").arg(commandName);

        return false;
    }

    // Create a compiler invocation using our command's arguments

    const clang::driver::ArgStringList &commandArguments = command.getArguments();
    std::unique_ptr<clang::CompilerInvocation> compilerInvocation(new clang::CompilerInvocation());

    clang::CompilerInvocation::CreateFromArgs(*compilerInvocation,
                                              const_cast<const char **>(commandArguments.data()),
                                              const_cast<const char **>(commandArguments.data())+commandArguments.size(),
                                              diagnosticsEngine);

    // Map our dummy file to a memory buffer

    QByteArray codeByteArray = pCode.toUtf8();

    compilerInvocation->getPreprocessorOpts().addRemappedFile(dummyFileName, llvm::MemoryBuffer::getMemBuffer(codeByteArray.constData()).release());

    // Create a compiler instance to handle the actual work

    clang::CompilerInstance compilerInstance;

    compilerInstance.setInvocation(compilerInvocation.release());

    // Create the compiler instance's diagnostics engine

    compilerInstance.createDiagnostics();

    if (!compilerInstance.hasDiagnostics()) {
        mError = tr("the diagnostics engine could not be created");

        return false;
    }

    // Create and execute the frontend to generate an LLVM bitcode module
    // Note: the LLVM team has been meaning to modify
    //       CompilerInstance::ExecuteAction() so that we could specify the
    //       output stream we want to use (rather than always use llvm::errs()),
    //       but they have yet to actually do it, so we modified it ourselves...

    std::unique_ptr<clang::CodeGenAction> codeGenerationAction(new clang::EmitLLVMOnlyAction(&llvm::getGlobalContext()));

    if (!compilerInstance.ExecuteAction(*codeGenerationAction, outputStream)) {
        mError = tr("the code could not be compiled");

        reset(false);

        return false;
    }

    // Retrieve the LLVM bitcode module

    std::unique_ptr<llvm::Module> module = codeGenerationAction->takeModule();

    // Initialise the native target (and its ASM printer), so not only can we
    // then create an execution engine, but more importantly its data layout
    // will match that of our target platform

    llvm::InitializeNativeTarget();
    llvm::InitializeNativeTargetAsmPrinter();

    // Create and keep track of an execution engine

    mExecutionEngine = std::unique_ptr<llvm::ExecutionEngine>(llvm::EngineBuilder(std::move(module)).setEngineKind(llvm::EngineKind::JIT).create());

    if (!mExecutionEngine) {
        mError = tr("the execution engine could not be created");

        delete module.release();

        return false;
    }

    return true;
}

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

void * CompilerEngine::getFunction(const QString &pFunctionName)
{
    // Return the address of the requested function

    if (mExecutionEngine)
        return (void *) mExecutionEngine->getFunctionAddress(qPrintable(pFunctionName));
    else
        return 0;
}

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

}   // namespace Compiler
}   // namespace OpenCOR

//==============================================================================
// End of file
//==============================================================================
<commit_msg>Keeping in sync with issue #611 [ci skip].<commit_after>/*******************************************************************************

Licensed to the OpenCOR team under one or more contributor license agreements.
See the NOTICE.txt file distributed with this work for additional information
regarding copyright ownership. The OpenCOR team licenses this file to you under
the Apache License, Version 2.0 (the "License"); you may not use this file
except in compliance with the License. You may obtain a copy of the License at

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

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

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

//==============================================================================
// Compiler engine class
//==============================================================================

#include "compilerengine.h"
#include "compilermath.h"
#include "corecliutils.h"

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

#include <QApplication>
#include <QFile>
#include <QIODevice>
#include <QTemporaryFile>
#include <QTextStream>

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

#include "llvmdisablewarnings.h"
    #include "llvm/IR/LLVMContext.h"
    #include "llvm/IR/Module.h"
    #include "llvm/Support/TargetSelect.h"
    #include "llvm/Support/Host.h"

    #include "clang/Basic/DiagnosticOptions.h"
    #include "clang/CodeGen/CodeGenAction.h"
    #include "clang/Driver/Compilation.h"
    #include "clang/Driver/Driver.h"
    #include "clang/Driver/Tool.h"
    #include "clang/Frontend/CompilerInstance.h"
    #include "clang/Frontend/TextDiagnosticPrinter.h"
#include "llvmenablewarnings.h"

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

#include <string>

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

namespace OpenCOR {
namespace Compiler {

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

CompilerEngine::CompilerEngine() :
    mExecutionEngine(std::unique_ptr<llvm::ExecutionEngine>()),
    mError(QString())
{
}

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

CompilerEngine::~CompilerEngine()
{
    // Reset ourselves

    reset();
}

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

void CompilerEngine::reset(const bool &pResetError)
{
    // Reset some internal objects

    delete mExecutionEngine.release();

    mExecutionEngine = std::unique_ptr<llvm::ExecutionEngine>();

    if (pResetError)
        mError = QString();
}

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

bool CompilerEngine::hasError() const
{
    // Return whether an error occurred

    return mError.size();
}

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

QString CompilerEngine::error() const
{
    // Return the compiler engine's error

    return mError;
}

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

bool CompilerEngine::compileCode(const QString &pCode)
{
    // Reset our compiler engine

    reset();

    // Determine our target triple
    // Note: normally, we would call llvm::sys::getProcessTriple(), but this
    //       returns the information about the system on which LLVM was built.
    //       In most cases it is fine, but on OS X it may be a problem. Indeed,
    //       with OS X 10.9, Apple decided to extend the C standard by adding
    //       some functions (e.g. __exp10()). So, if the given code needs one of
    //       those functions, then OpenCOR will crash if run on an 'old' version
    //       of OS X. So, to avoid this issue, we set the target triple
    //       ourselves, based on the system on which OpenCOR is being used...

    std::string targetTriple;

#if defined(Q_OS_WIN)
    targetTriple = (sizeof(void *) == 4)?"i686-pc-win32-elf":"x86_64-pc-win32-elf";
    // Note: MCJIT currently works only through the ELF object format, hence we
    //       are appending "-elf"...
#elif defined(Q_OS_LINUX)
    targetTriple = (sizeof(void *) == 4)?"i686-pc-linux-gnu":"x86_64-pc-linux-gnu";
#elif defined(Q_OS_MAC)
    targetTriple = "x86_64-apple-darwin"+std::to_string(QSysInfo::MacintoshVersion+2);
#else
    #error Unsupported platform
#endif

    // Get a driver to compile our code

#ifdef QT_DEBUG
    llvm::raw_ostream &outputStream = llvm::outs();
#else
    llvm::raw_ostream &outputStream = llvm::nulls();
#endif
    llvm::IntrusiveRefCntPtr<clang::DiagnosticOptions> diagnosticOptions = new clang::DiagnosticOptions();

    clang::DiagnosticsEngine diagnosticsEngine(llvm::IntrusiveRefCntPtr<clang::DiagnosticIDs>(new clang::DiagnosticIDs()),
                                               &*diagnosticOptions,
                                               new clang::TextDiagnosticPrinter(outputStream, &*diagnosticOptions));

    clang::driver::Driver driver("clang", targetTriple, diagnosticsEngine);

    driver.setCheckInputsExist(false);

    // Get a compilation object to which we pass some arguments

    llvm::StringRef dummyFileName("dummyFile.c");

    llvm::SmallVector<const char *, 16> compilationArguments;

    compilationArguments.push_back("clang");
    compilationArguments.push_back("-fsyntax-only");
    compilationArguments.push_back("-O3");
    compilationArguments.push_back("-ffast-math");
    compilationArguments.push_back("-Werror");
    compilationArguments.push_back(dummyFileName.data());

    std::unique_ptr<clang::driver::Compilation> compilation(driver.BuildCompilation(compilationArguments));

    if (!compilation) {
        mError = tr("the compilation object could not be created");

        return false;
    }

    // The compilation object should have only one command, so if it doesn't
    // then something went wrong

    const clang::driver::JobList &jobList = compilation->getJobs();

    if (    (jobList.size() != 1)
        || !llvm::isa<clang::driver::Command>(*jobList.begin())) {
        mError = tr("the compilation object must contain only one command");

        return false;
    }

    // Retrieve the command job

    const clang::driver::Command &command = llvm::cast<clang::driver::Command>(*jobList.begin());
    QString commandName = command.getCreator().getName();

    if (commandName.compare("clang")) {
        mError = tr("a clang command was expected, but a %1 command was found instead").arg(commandName);

        return false;
    }

    // Create a compiler invocation using our command's arguments

    const clang::driver::ArgStringList &commandArguments = command.getArguments();
    std::unique_ptr<clang::CompilerInvocation> compilerInvocation(new clang::CompilerInvocation());

    clang::CompilerInvocation::CreateFromArgs(*compilerInvocation,
                                              const_cast<const char **>(commandArguments.data()),
                                              const_cast<const char **>(commandArguments.data())+commandArguments.size(),
                                              diagnosticsEngine);

    // Map our dummy file to a memory buffer

    QByteArray codeByteArray = pCode.toUtf8();

    compilerInvocation->getPreprocessorOpts().addRemappedFile(dummyFileName, llvm::MemoryBuffer::getMemBuffer(codeByteArray.constData()).release());

    // Create a compiler instance to handle the actual work

    clang::CompilerInstance compilerInstance;

    compilerInstance.setInvocation(compilerInvocation.release());

    // Create the compiler instance's diagnostics engine

    compilerInstance.createDiagnostics();

    if (!compilerInstance.hasDiagnostics()) {
        mError = tr("the diagnostics engine could not be created");

        return false;
    }

    // Create and execute the frontend to generate an LLVM bitcode module
    // Note: the LLVM team has been meaning to modify
    //       CompilerInstance::ExecuteAction() so that we could specify the
    //       output stream we want to use (rather than always use llvm::errs()),
    //       but they have yet to actually do it, so we modified it ourselves...

    std::unique_ptr<clang::CodeGenAction> codeGenerationAction(new clang::EmitLLVMOnlyAction(&llvm::getGlobalContext()));

    if (!compilerInstance.ExecuteAction(*codeGenerationAction, outputStream)) {
        mError = tr("the code could not be compiled");

        reset(false);

        return false;
    }

    // Retrieve the LLVM bitcode module

    std::unique_ptr<llvm::Module> module = codeGenerationAction->takeModule();

    // Initialise the native target (and its ASM printer), so not only can we
    // then create an execution engine, but more importantly its data layout
    // will match that of our target platform

    llvm::InitializeNativeTarget();
    llvm::InitializeNativeTargetAsmPrinter();

    // Create and keep track of an execution engine

    mExecutionEngine = std::unique_ptr<llvm::ExecutionEngine>(llvm::EngineBuilder(std::move(module)).setEngineKind(llvm::EngineKind::JIT).create());

    if (!mExecutionEngine) {
        mError = tr("the execution engine could not be created");

        delete module.release();

        return false;
    }

    return true;
}

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

void * CompilerEngine::getFunction(const QString &pFunctionName)
{
    // Return the address of the requested function

    if (mExecutionEngine)
        return (void *) mExecutionEngine->getFunctionAddress(qPrintable(pFunctionName));
    else
        return 0;
}

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

}   // namespace Compiler
}   // namespace OpenCOR

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