<commit_before>/*
    Copyright 2002-2014 CEA LIST

    This file is part of LIMA.

    LIMA is free software: you can redistribute it and/or modify
    it under the terms of the GNU Affero General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    LIMA is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU Affero General Public License for more details.

    You should have received a copy of the GNU Affero General Public License
    along with LIMA.  If not, see <http://www.gnu.org/licenses/>
*/
/************************************************************************
 *
 * @file       SemanticRoleLabelingLoader.cpp
 * @author     Clémence Filmont <clemence.filmont@cea.fr>
 * @date       2014--
 * copyright   Copyright (C) 2014 by CEA LIST
 * Project     mm_linguisticprocessing
 *
 *
 ***********************************************************************/

#include "SemanticRoleLabelingLoader.h"
#include "common/AbstractFactoryPattern/SimpleFactory.h"
#include "common/Data/strwstrtools.h"
#include "linguisticProcessing/core/Automaton/recognizerData.h"
#include "common/MediaticData/mediaticData.h"
#include "linguisticProcessing/common/annotationGraph/AnnotationData.h"
#include "linguisticProcessing/common/annotationGraph/AnnotationGraph.h"
#include "linguisticProcessing/core/LinguisticAnalysisStructure/LinguisticGraph.h"
#include "linguisticProcessing/LinguisticProcessingCommon.h"
#include <utility>
#include <iostream>
#include<fstream>

using namespace std;
using namespace Lima::LinguisticProcessing::LinguisticAnalysisStructure;
using namespace Lima::LinguisticProcessing::ApplyRecognizer;
using namespace Lima::Common::XMLConfigurationFiles;
using namespace Lima::Common::AnnotationGraphs;
using namespace Lima::LinguisticProcessing::SemanticAnalysis;
using namespace Lima::Common::AnnotationGraphs;

namespace Lima {
namespace LinguisticProcessing {
namespace SemanticAnalysis {

SimpleFactory<MediaProcessUnit,SemanticRoleLabelingLoader> SemanticRoleLabelingFactory(SEMANTICROLELABELINGLOADER_CLASSID);

//***********************************************************************
SemanticRoleLabelingLoader::SemanticRoleLabelingLoader():
m_language(0),
m_graph("PosGraph"),
m_suffix(".conll")
{}

SemanticRoleLabelingLoader::~SemanticRoleLabelingLoader()
{
}

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

void SemanticRoleLabelingLoader::init(Common::XMLConfigurationFiles::GroupConfigurationStructure& unitConfiguration, Manager* manager){

  SEMANTICANALYSISLOGINIT;
  m_language=manager->getInitializationParameters().media;
  AnalysisLoader::init(unitConfiguration,manager);
  try
  {
    m_graph=unitConfiguration.getParamsValueAtKey("graph");
  }
  catch (NoSuchParam& ) {} // keep default value
  try
  {
    m_suffix=unitConfiguration.getParamsValueAtKey("outputSuffix");
  }
   catch (NoSuchParam& ) {} // keep default value
    AnalysisLoader::init(unitConfiguration,manager);
  }

LimaStatusCode SemanticRoleLabelingLoader::process(AnalysisContent& analysis) const{
  SEMANTICANALYSISLOGINIT;
  AnalysisGraph* tokenList=static_cast<AnalysisGraph*>(analysis.getData(m_graph));
  if (tokenList==0) {
    LERROR << "graph " << m_graph << " has not been produced: check pipeline" << LENDL;
    return MISSING_DATA;
  }
  LinguisticGraph* resultGraph=tokenList->getGraph();
  AnnotationData* annotationData = static_cast<AnnotationData*>(analysis.getData("AnnotationData"));
  LimaConllTokenIdMapping* limaConllMapping= static_cast<LimaConllTokenIdMapping*>(analysis.getData("LimaConllTokenIdMapping"));

  QFile file("/home/clemence/textes_test/jamaica_out.conll");
  if (!file.open(QIODevice::ReadOnly))
    qDebug() << "cannot open file" << endl;
  int sentenceNb=1;
  std::map <int, QString> sentences;
  while (!file.atEnd()) {
    QByteArray text=file.readLine();
    QString textString = QString::fromUtf8(text.constData());
    //One assume that the input file does not start with a blank line
    if (textString.size()<3){
      sentenceNb++;
    }else {
      QString becomingSentence=sentences[sentenceNb]+textString;
      sentences[sentenceNb]= becomingSentence;
    }
  }

  SemanticRoleLabelingLoader::ConllHandler cHandler(m_language, analysis, tokenList);
  LimaString predicateTypeAnnotation="predicate";
  LimaString roleTypeAnnotation="semantic role";
  for (std::map<int,QString>::iterator it=sentences.begin(); it!=sentences.end(); ++it){
    int sentenceIndex=it->first;
    QString sentence=it->second;
    if(cHandler.extractSemanticInformation(sentenceIndex, limaConllMapping,sentence)){
      LDEBUG << "there are " << cHandler.m_verbalClassNb << "verbal classes for this sentence " << LENDL;
      for (int vClassIndex=0;vClassIndex<cHandler.m_verbalClassNb;vClassIndex++){
        LinguisticGraphVertex posGraphPredicateVertex=cHandler.m_verbalClasses[vClassIndex].first;
        LimaString verbalClass=cHandler.m_verbalClasses[vClassIndex].second;

        AnnotationGraphVertex annotPredicateVertex=annotationData->createAnnotationVertex();
        annotationData->addMatching("PosGraph", posGraphPredicateVertex, "annot", annotPredicateVertex);
        annotationData->annotate(annotPredicateVertex, predicateTypeAnnotation, verbalClass);

        LDEBUG << " A vertex was created for the verbal class "<< annotationData->stringAnnotation(annotPredicateVertex, predicateTypeAnnotation)<< LENDL;
        std::vector <pair<LinguisticGraphVertex,QString>>::iterator semRoleIt;
        for (semRoleIt=cHandler.m_semanticRoles[vClassIndex].begin();         semRoleIt!=cHandler.m_semanticRoles[vClassIndex].end();semRoleIt++){
          LinguisticGraphVertex posGraphRoleVertex=(*semRoleIt).first;
          LimaString semanticRole=(*semRoleIt).second;

          AnnotationGraphVertex annotRoleVertex=annotationData->createAnnotationVertex();
          annotationData->addMatching("PosGraph", posGraphRoleVertex, "annot", annotRoleVertex);
          AnnotationGraphEdge roleEdge=annotationData->createAnnotationEdge(annotPredicateVertex, annotRoleVertex);
          annotationData->annotate(roleEdge, roleTypeAnnotation,semanticRole);

          LDEBUG << " An edge annotated " << annotationData->stringAnnotation(roleEdge, roleTypeAnnotation)<< "was created between " << verbalClass << " and the Lima vertex " << posGraphRoleVertex << LENDL;
        }
      }
    }
  }
  return SUCCESS_ID;
}

SemanticRoleLabelingLoader::ConllHandler::ConllHandler(MediaId language, AnalysisContent& analysis, LinguisticAnalysisStructure::AnalysisGraph* graph):
m_language(language),
m_analysis(analysis),
m_graph(graph),
m_descriptorSeparator("\t+"),
m_tokenSeparator("\n+"),
m_verbalClasses(),
m_semanticRoles(),
m_verbalClassNb()
{
  SEMANTICANALYSISLOGINIT;
  LDEBUG << "SemanticRoleLabelingLoader::ConllHandler constructor";
}
SemanticRoleLabelingLoader::ConllHandler::~ConllHandler(){
  delete [] m_semanticRoles;
  delete [] m_verbalClasses;
}

// designed to be repeated on each sentence
bool SemanticRoleLabelingLoader::ConllHandler::extractSemanticInformation(int sentenceI, LimaConllTokenIdMapping* limaConllMapping, const QString & sent){
  SEMANTICANALYSISLOGINIT;
  SemanticRoleLabelingLoader::ConllHandler cHandler(m_language, m_analysis, m_graph);
  QStringList sentenceTokens=cHandler.splitSegment(sent, m_tokenSeparator);
  QStringList::const_iterator tokensIterator;
  QString firstSentenceToken=(*sentenceTokens.constBegin());
  int descriptorsNb=cHandler.splitSegment(firstSentenceToken, m_descriptorSeparator).size();
  m_verbalClassNb=descriptorsNb-11;
  if (m_verbalClassNb!=0){
    LDEBUG << sentenceI << " : \n" << sent << LENDL;
    int classIndex=0;
    m_verbalClasses=new std::pair<LinguisticGraphVertex, QString>[m_verbalClassNb];
    m_semanticRoles=new std::vector<std::pair<LinguisticGraphVertex,QString>>[m_verbalClassNb];
    //repeated on each token of the sentence, that is on each line
    for (tokensIterator = sentenceTokens.constBegin(); tokensIterator != sentenceTokens.constEnd();
            ++tokensIterator){
      int  roleNumbers=0;
      QStringList descriptors=cHandler.splitSegment((*tokensIterator),m_descriptorSeparator);
      if (descriptors.size()>=10){
        int conllTokenId=descriptors[0].toInt();
        QString conllToken=descriptors[1];
        if(descriptors[10]!="-"){
          QString verbalClass=descriptors[10];
          QString vClass=descriptors[10];
          LinguisticGraphVertex limaTokenId=cHandler.getLimaTokenId(conllTokenId, sentenceI, limaConllMapping);
          m_verbalClasses[classIndex]=make_pair(limaTokenId, vClass);
          classIndex++;
          continue;
        }
        else{
          for (int roleTargetFieldIndex=0; roleTargetFieldIndex<m_verbalClassNb;roleTargetFieldIndex++){
            if (descriptors[11+roleTargetFieldIndex]!="-"){
              QString semanticRoleLabel=descriptors[11+roleTargetFieldIndex];
              LinguisticGraphVertex limaTokenId=cHandler.getLimaTokenId(conllTokenId, sentenceI,   limaConllMapping);
              std::vector<std::pair<LinguisticGraphVertex,QString>> sRoles;
              m_semanticRoles[roleTargetFieldIndex].push_back(make_pair(limaTokenId,semanticRoleLabel));
              roleNumbers++;
            }
          }
        }
      }
    }
    return classIndex;
  }
}

QStringList SemanticRoleLabelingLoader::ConllHandler::splitSegment(const QString & segment, QRegExp separator){
  QStringList segmentsSplited;
  segmentsSplited =segment.split(QRegExp(separator),QString::SkipEmptyParts);
  return segmentsSplited;
}

LinguisticGraphVertex SemanticRoleLabelingLoader::ConllHandler::getLimaTokenId(int conllTokenId, int sentenceI, LimaConllTokenIdMapping* limaConllMapping){
  SEMANTICANALYSISLOGINIT;
  std::map< int,std::map< int,LinguisticGraphVertex>>::iterator limaConllMappingIt;
  limaConllMappingIt=limaConllMapping->find(sentenceI);
  if (limaConllMappingIt == limaConllMapping->end()) {
    LERROR << "Sentence " << sentenceI << " not found";
    // TODO exit or raise an exception
  }
  std::map< int,LinguisticGraphVertex> limaConllId=(*limaConllMappingIt).second;
  std::map< int,LinguisticGraphVertex>::iterator limaConllIdIt=limaConllId.find(conllTokenId);
  if (limaConllIdIt==limaConllId.end()) {
    LERROR << "Conll token id " << conllTokenId << " not found";
    // TODO exit or raise an exception
  }
  LinguisticGraphVertex limaTokenId=limaConllIdIt->second;
  return limaTokenId;
}

}
}
} // end namespace

<commit_msg>Take into account token that are both verbal class and role filler<commit_after>/*
    Copyright 2002-2014 CEA LIST

    This file is part of LIMA.

    LIMA is free software: you can redistribute it and/or modify
    it under the terms of the GNU Affero General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    LIMA is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU Affero General Public License for more details.

    You should have received a copy of the GNU Affero General Public License
    along with LIMA.  If not, see <http://www.gnu.org/licenses/>
*/
/************************************************************************
 *
 * @file       SemanticRoleLabelingLoader.cpp
 * @author     Clémence Filmont <clemence.filmont@cea.fr>
 * @date       2014--
 * copyright   Copyright (C) 2014 by CEA LIST
 * Project     mm_linguisticprocessing
 *
 *
 ***********************************************************************/

#include "SemanticRoleLabelingLoader.h"
#include "common/AbstractFactoryPattern/SimpleFactory.h"
#include "common/Data/strwstrtools.h"
#include "linguisticProcessing/core/Automaton/recognizerData.h"
#include "common/MediaticData/mediaticData.h"
#include "linguisticProcessing/common/annotationGraph/AnnotationData.h"
#include "linguisticProcessing/common/annotationGraph/AnnotationGraph.h"
#include "linguisticProcessing/core/LinguisticAnalysisStructure/LinguisticGraph.h"
#include "linguisticProcessing/LinguisticProcessingCommon.h"
#include <utility>
#include <iostream>
#include<fstream>

using namespace std;
using namespace Lima::LinguisticProcessing::LinguisticAnalysisStructure;
using namespace Lima::LinguisticProcessing::ApplyRecognizer;
using namespace Lima::Common::XMLConfigurationFiles;
using namespace Lima::Common::AnnotationGraphs;
using namespace Lima::LinguisticProcessing::SemanticAnalysis;
using namespace Lima::Common::AnnotationGraphs;

namespace Lima {
namespace LinguisticProcessing {
namespace SemanticAnalysis {

SimpleFactory<MediaProcessUnit,SemanticRoleLabelingLoader> SemanticRoleLabelingFactory(SEMANTICROLELABELINGLOADER_CLASSID);

//***********************************************************************
SemanticRoleLabelingLoader::SemanticRoleLabelingLoader():
m_language(0),
m_graph("PosGraph"),
m_suffix(".conll")
{}

SemanticRoleLabelingLoader::~SemanticRoleLabelingLoader()
{
}

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

void SemanticRoleLabelingLoader::init(Common::XMLConfigurationFiles::GroupConfigurationStructure& unitConfiguration, Manager* manager){

  SEMANTICANALYSISLOGINIT;
  m_language=manager->getInitializationParameters().media;
  AnalysisLoader::init(unitConfiguration,manager);
  try
  {
    m_graph=unitConfiguration.getParamsValueAtKey("graph");
  }
  catch (NoSuchParam& ) {} // keep default value
  try
  {
    m_suffix=unitConfiguration.getParamsValueAtKey("outputSuffix");
  }
   catch (NoSuchParam& ) {} // keep default value
    AnalysisLoader::init(unitConfiguration,manager);
  }

LimaStatusCode SemanticRoleLabelingLoader::process(AnalysisContent& analysis) const{
  SEMANTICANALYSISLOGINIT;
  AnalysisGraph* tokenList=static_cast<AnalysisGraph*>(analysis.getData(m_graph));
  if (tokenList==0) {
    LERROR << "graph " << m_graph << " has not been produced: check pipeline" << LENDL;
    return MISSING_DATA;
  }
  LinguisticGraph* resultGraph=tokenList->getGraph();
  AnnotationData* annotationData = static_cast<AnnotationData*>(analysis.getData("AnnotationData"));
  LimaConllTokenIdMapping* limaConllMapping= static_cast<LimaConllTokenIdMapping*>(analysis.getData("LimaConllTokenIdMapping"));

  QFile file("/home/clemence/textes_test/jamaica.outpython.conll");
  if (!file.open(QIODevice::ReadOnly))
    qDebug() << "cannot open file" << endl;
  int sentenceNb=1;
  std::map <int, QString> sentences;
  while (!file.atEnd()) {
    QByteArray text=file.readLine();
    QString textString = QString::fromUtf8(text.constData());
    //One assume that the input file does not start with a blank line
    if (textString.size()<3){
      sentenceNb++;
    }else {
      QString becomingSentence=sentences[sentenceNb]+textString;
      sentences[sentenceNb]= becomingSentence;
    }
  }

  SemanticRoleLabelingLoader::ConllHandler cHandler(m_language, analysis, tokenList);
  LimaString predicateTypeAnnotation="predicate";
  LimaString roleTypeAnnotation="semantic role";
  for (std::map<int,QString>::iterator it=sentences.begin(); it!=sentences.end(); ++it){
    int sentenceIndex=it->first;
    QString sentence=it->second;
    if(cHandler.extractSemanticInformation(sentenceIndex, limaConllMapping,sentence)){
      LDEBUG << "there is/are " << cHandler.m_verbalClassNb << "verbal class(es) for this sentence " << LENDL;
      for (int vClassIndex=0;vClassIndex<cHandler.m_verbalClassNb;vClassIndex++){
        LinguisticGraphVertex posGraphPredicateVertex=cHandler.m_verbalClasses[vClassIndex].first;
        LimaString verbalClass=cHandler.m_verbalClasses[vClassIndex].second;

        AnnotationGraphVertex annotPredicateVertex=annotationData->createAnnotationVertex();
        annotationData->addMatching("PosGraph", posGraphPredicateVertex, "annot", annotPredicateVertex);
        annotationData->annotate(annotPredicateVertex, Common::Misc::utf8stdstring2limastring("predicate"), verbalClass);

        LDEBUG << " A vertex was created for the verbal class "<< annotationData->stringAnnotation(annotPredicateVertex, predicateTypeAnnotation)<< LENDL;
        std::vector <pair<LinguisticGraphVertex,QString>>::iterator semRoleIt;
        for (semRoleIt=cHandler.m_semanticRoles[vClassIndex].begin();         semRoleIt!=cHandler.m_semanticRoles[vClassIndex].end();semRoleIt++){
          LinguisticGraphVertex posGraphRoleVertex=(*semRoleIt).first;
          LimaString semanticRole=(*semRoleIt).second;

          AnnotationGraphVertex annotRoleVertex=annotationData->createAnnotationVertex();
          annotationData->addMatching("PosGraph", posGraphRoleVertex, "annot", annotRoleVertex);
          AnnotationGraphEdge roleEdge=annotationData->createAnnotationEdge(annotPredicateVertex, annotRoleVertex);
          annotationData->annotate(roleEdge, roleTypeAnnotation,semanticRole);

          LDEBUG << " An edge annotated " << annotationData->stringAnnotation(roleEdge, roleTypeAnnotation)<< "was created between " << verbalClass << " and the Lima vertex " << posGraphRoleVertex << LENDL;
        }
      }
    }
  }
  return SUCCESS_ID;
}

SemanticRoleLabelingLoader::ConllHandler::ConllHandler(MediaId language, AnalysisContent& analysis, LinguisticAnalysisStructure::AnalysisGraph* graph):
m_language(language),
m_analysis(analysis),
m_graph(graph),
m_descriptorSeparator("\t+"),
m_tokenSeparator("\n+"),
m_verbalClasses(),
m_semanticRoles(),
m_verbalClassNb()
{
  SEMANTICANALYSISLOGINIT;
  LDEBUG << "SemanticRoleLabelingLoader::ConllHandler constructor";
}
SemanticRoleLabelingLoader::ConllHandler::~ConllHandler(){
  delete [] m_semanticRoles;
  delete [] m_verbalClasses;
}

// designed to be repeated on each sentence
bool SemanticRoleLabelingLoader::ConllHandler::extractSemanticInformation(int sentenceI, LimaConllTokenIdMapping* limaConllMapping, const QString & sent){
  SEMANTICANALYSISLOGINIT;
  SemanticRoleLabelingLoader::ConllHandler cHandler(m_language, m_analysis, m_graph);
  QStringList sentenceTokens=cHandler.splitSegment(sent, m_tokenSeparator);
  QStringList::const_iterator tokensIterator;
  QString firstSentenceToken=(*sentenceTokens.constBegin());
  int descriptorsNb=cHandler.splitSegment(firstSentenceToken, m_descriptorSeparator).size();
  m_verbalClassNb=descriptorsNb-11;
  if (m_verbalClassNb!=0){
    LDEBUG << sentenceI << " : \n" << sent << LENDL;
    int classIndex=0;
    m_verbalClasses=new std::pair<LinguisticGraphVertex, QString>[m_verbalClassNb];
    m_semanticRoles=new std::vector<std::pair<LinguisticGraphVertex,QString>>[m_verbalClassNb];
    //repeated on each token of the sentence, that is on each line
    for (tokensIterator = sentenceTokens.constBegin(); tokensIterator != sentenceTokens.constEnd();
            ++tokensIterator){
      int  roleNumbers=0;
      QStringList descriptors=cHandler.splitSegment((*tokensIterator),m_descriptorSeparator);
      if (descriptors.size()>=10){
        int conllTokenId=descriptors[0].toInt();
        QString conllToken=descriptors[1];
        if(descriptors[10]!="-"){
            QString verbalClass=descriptors[10];
            QString vClass=descriptors[10];
            LinguisticGraphVertex limaTokenId=cHandler.getLimaTokenId(conllTokenId, sentenceI, limaConllMapping);
            m_verbalClasses[classIndex]=make_pair(limaTokenId, vClass);
            classIndex++;
          }
          for (int roleTargetFieldIndex=0; roleTargetFieldIndex<m_verbalClassNb;roleTargetFieldIndex++){
            if (descriptors[11+roleTargetFieldIndex]!="-"){
              QString semanticRoleLabel=descriptors[11+roleTargetFieldIndex];
              LinguisticGraphVertex limaTokenId=cHandler.getLimaTokenId(conllTokenId, sentenceI,   limaConllMapping);
              LDEBUG << "The Lima token id matching the conll token id " << conllTokenId << " is " << limaTokenId<< LENDL;
              std::vector<std::pair<LinguisticGraphVertex,QString>> sRoles;
              m_semanticRoles[roleTargetFieldIndex].push_back(make_pair(limaTokenId,semanticRoleLabel));
              roleNumbers++;
            }
          }
        }
      }
    return classIndex;
  }
}

QStringList SemanticRoleLabelingLoader::ConllHandler::splitSegment(const QString & segment, QRegExp separator){
  QStringList segmentsSplited;
  segmentsSplited =segment.split(QRegExp(separator),QString::SkipEmptyParts);
  return segmentsSplited;
}

LinguisticGraphVertex SemanticRoleLabelingLoader::ConllHandler::getLimaTokenId(int conllTokenId, int sentenceI, LimaConllTokenIdMapping* limaConllMapping){
  SEMANTICANALYSISLOGINIT;
  std::map< int,std::map< int,LinguisticGraphVertex>>::iterator limaConllMappingIt;
  limaConllMappingIt=limaConllMapping->find(sentenceI);
  if (limaConllMappingIt == limaConllMapping->end()) {
    LERROR << "Sentence " << sentenceI << " not found";
    // TODO exit or raise an exception
  }
  std::map< int,LinguisticGraphVertex> limaConllId=(*limaConllMappingIt).second;
  std::map< int,LinguisticGraphVertex>::iterator limaConllIdIt=limaConllId.find(conllTokenId);
  if (limaConllIdIt==limaConllId.end()) {
    LERROR << "Conll token id " << conllTokenId << " not found";
    // TODO exit or raise an exception
  }
  LinguisticGraphVertex limaTokenId=limaConllIdIt->second;
  return limaTokenId;
}

}
}
} // end namespace

<|endoftext|>


<commit_before>/* Copyright (c) 2012-present Advanced Micro Devices, Inc.

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

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

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

#include "commandqueue.hpp"
#include "thread/monitor.hpp"
#include "device/device.hpp"
#include "platform/context.hpp"

/*!
 * \file commandQueue.cpp
 * \brief  Definitions for HostQueue object.
 *
 * \author Laurent Morichetti
 * \date   October 2008
 */

namespace amd {

HostQueue::HostQueue(Context& context, Device& device, cl_command_queue_properties properties,
                     uint queueRTCUs, Priority priority, const std::vector<uint32_t>& cuMask)
    : CommandQueue(context, device, properties, device.info().queueProperties_, queueRTCUs,
                   priority, cuMask),
      lastEnqueueCommand_(nullptr),
      head_(nullptr),
      tail_(nullptr) {
  if (AMD_DIRECT_DISPATCH) {
    // Initialize the queue
    thread_.Init(this);
  } else {
    if (thread_.state() >= Thread::INITIALIZED) {
      ScopedLock sl(queueLock_);
      thread_.start(this);
      queueLock_.wait();
    }
  }
}

bool HostQueue::terminate() {
  if (AMD_DIRECT_DISPATCH) {
    thread_.Release();
  } else {
    if (Os::isThreadAlive(thread_)) {
      Command* marker = nullptr;

      // Send a finish if the queue is still accepting commands.
      {
        ScopedLock sl(queueLock_);
        if (thread_.acceptingCommands_) {
          marker = new Marker(*this, false);
          if (marker != nullptr) {
            append(*marker);
            queueLock_.notify();
          }
        }
      }
      if (marker != nullptr) {
        marker->awaitCompletion();
        marker->release();
      }

      // Wake-up the command loop, so it can exit
      {
        ScopedLock sl(queueLock_);
        thread_.acceptingCommands_ = false;
        queueLock_.notify();
      }

      // FIXME_lmoriche: fix termination handshake
      while (thread_.state() < Thread::FINISHED) {
        Os::yield();
      }
    }
  }

  if (Agent::shouldPostCommandQueueEvents()) {
    Agent::postCommandQueueFree(as_cl(this->asCommandQueue()));
  }

  return true;
}

void HostQueue::finish() {
  Command* command = nullptr;
  if (IS_HIP) {
    command = getLastQueuedCommand(true);
    if (nullptr != command) {
      command->awaitCompletion();
      command->release();
    }
  }
  if (nullptr == command) {
    // Send a finish to make sure we finished all commands
    command = new Marker(*this, false);
    if (command == NULL) {
      return;
    }
    ClPrint(LOG_DEBUG, LOG_CMD, "marker is queued");
    command->enqueue();
    command->awaitCompletion();
    command->release();
  }
  ClPrint(LOG_DEBUG, LOG_CMD, "All commands finished");
}

void HostQueue::loop(device::VirtualDevice* virtualDevice) {
  // Notify the caller that the queue is ready to accept commands.
  {
    ScopedLock sl(queueLock_);
    thread_.acceptingCommands_ = true;
    queueLock_.notify();
  }
  // Create a command batch with all the commands present in the queue.
  Command* head = NULL;
  Command* tail = NULL;
  while (true) {
    // Get one command from the queue
    Command* command = queue_.dequeue();
    if (command == NULL) {
      ScopedLock sl(queueLock_);
      while ((command = queue_.dequeue()) == NULL) {
        if (!thread_.acceptingCommands_) {
          return;
        }
        queueLock_.wait();
      }
    }

    command->retain();

    // Process the command's event wait list.
    const Command::EventWaitList& events = command->eventWaitList();
    bool dependencyFailed = false;

    for (const auto& it : events) {
      // Only wait if the command is enqueued into another queue.
      if (it->command().queue() != this) {
        // Runtime has to flush the current batch only if the dependent wait is blocking
        if (it->command().status() != CL_COMPLETE) {
          virtualDevice->flush(head, true);
          tail = head = NULL;
          dependencyFailed |= !it->awaitCompletion();
        }
      }
    }

    // Insert the command to the linked list.
    if (NULL == head) {  // if the list is empty
      head = tail = command;
    } else {
      tail->setNext(command);
      tail = command;
    }

    if (dependencyFailed) {
      command->setStatus(CL_EXEC_STATUS_ERROR_FOR_EVENTS_IN_WAIT_LIST);
      continue;
    }

    ClPrint(LOG_DEBUG, LOG_CMD, "command (%s) is submitted: %p", getOclCommandKindString(command->type()), command);

    command->setStatus(CL_SUBMITTED);

    // Submit to the device queue.
    command->submit(*virtualDevice);

    // if this is a user invisible marker command, then flush
    if (0 == command->type()) {
      virtualDevice->flush(head);
      tail = head = NULL;
    }
  }  // while (true) {
}

void HostQueue::append(Command& command) {
  // We retain the command here. It will be released when its status
  // changes to CL_COMPLETE
  if ((command.getWaitBits() & 0x1) != 0) {
    finish();
  }
  command.retain();
  command.setStatus(CL_QUEUED);
  queue_.enqueue(&command);
  if (!IS_HIP) {
    return;
  }

  if (command.waitingEvent() == nullptr) {
    // Set last submitted command
    Command* prevLastEnqueueCommand;
    command.retain();
    {
       // lastCmdLock_ ensures that lastEnqueueCommand() can retain the command before it is swapped
       // out. We want to keep this critical section as short as possible, so the command should be
       // released outside this section.
       ScopedLock l(lastCmdLock_);

       prevLastEnqueueCommand = lastEnqueueCommand_;
       lastEnqueueCommand_ = &command;
    }

    if (prevLastEnqueueCommand != nullptr) {
      prevLastEnqueueCommand->release();
    }
  }
}

bool HostQueue::isEmpty() {
  // Get a snapshot of queue size
  return queue_.empty();
}

Command* HostQueue::getLastQueuedCommand(bool retain) {
  if (AMD_DIRECT_DISPATCH) {
    // The batch update must be lock protected to avoid a race condition
    // when multiple threads submit/flush/update the batch at the same time
    ScopedLock sl(vdev()->execution());

    // Since the lastCmdLock_ is acquired, it is safe to read and retain the lastEnqueueCommand.
    // It is guaranteed that the pointer will not change.
    if (retain && lastEnqueueCommand_ != nullptr) {
      lastEnqueueCommand_->retain();
    }
    return lastEnqueueCommand_;
  } else {
    // Get last submitted command
    ScopedLock l(lastCmdLock_);

    // Since the lastCmdLock_ is acquired, it is safe to read and retain the lastEnqueueCommand.
    // It is guaranteed that the pointer will not change.
    if (retain && lastEnqueueCommand_ != nullptr) {
      lastEnqueueCommand_->retain();
    }
    return lastEnqueueCommand_;
  }
}

DeviceQueue::~DeviceQueue() {
  delete virtualDevice_;
  ScopedLock lock(context().lock());
  context().removeDeviceQueue(device(), this);
}

bool DeviceQueue::create() {
  static const bool InteropQueue = true;
  const bool defaultDeviceQueue = properties().test(CL_QUEUE_ON_DEVICE_DEFAULT);
  bool result = false;

  virtualDevice_ = device().createVirtualDevice(this);
  if (virtualDevice_ != NULL) {
    result = true;
    context().addDeviceQueue(device(), this, defaultDeviceQueue);
  }

  return result;
}

}  // namespace amd
<commit_msg>SWDEV-285318 - Wait for the queue before destruction<commit_after>/* Copyright (c) 2012-present Advanced Micro Devices, Inc.

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

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

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

#include "commandqueue.hpp"
#include "thread/monitor.hpp"
#include "device/device.hpp"
#include "platform/context.hpp"

/*!
 * \file commandQueue.cpp
 * \brief  Definitions for HostQueue object.
 *
 * \author Laurent Morichetti
 * \date   October 2008
 */

namespace amd {

HostQueue::HostQueue(Context& context, Device& device, cl_command_queue_properties properties,
                     uint queueRTCUs, Priority priority, const std::vector<uint32_t>& cuMask)
    : CommandQueue(context, device, properties, device.info().queueProperties_, queueRTCUs,
                   priority, cuMask),
      lastEnqueueCommand_(nullptr),
      head_(nullptr),
      tail_(nullptr) {
  if (AMD_DIRECT_DISPATCH) {
    // Initialize the queue
    thread_.Init(this);
  } else {
    if (thread_.state() >= Thread::INITIALIZED) {
      ScopedLock sl(queueLock_);
      thread_.start(this);
      queueLock_.wait();
    }
  }
}

bool HostQueue::terminate() {
  if (AMD_DIRECT_DISPATCH) {
    Command* marker = new Marker(*this, true);
    if (marker != nullptr) {
      marker->enqueue();
      marker->awaitCompletion();
      marker->release();
    }
    thread_.acceptingCommands_ = false;
    thread_.Release();
  } else {
    if (Os::isThreadAlive(thread_)) {
      Command* marker = nullptr;

      // Send a finish if the queue is still accepting commands.
      {
        ScopedLock sl(queueLock_);
        if (thread_.acceptingCommands_) {
          marker = new Marker(*this, false);
          if (marker != nullptr) {
            append(*marker);
            queueLock_.notify();
          }
        }
      }
      if (marker != nullptr) {
        marker->awaitCompletion();
        marker->release();
      }

      // Wake-up the command loop, so it can exit
      {
        ScopedLock sl(queueLock_);
        thread_.acceptingCommands_ = false;
        queueLock_.notify();
      }

      // FIXME_lmoriche: fix termination handshake
      while (thread_.state() < Thread::FINISHED) {
        Os::yield();
      }
    }
  }

  if (Agent::shouldPostCommandQueueEvents()) {
    Agent::postCommandQueueFree(as_cl(this->asCommandQueue()));
  }

  return true;
}

void HostQueue::finish() {
  Command* command = nullptr;
  if (IS_HIP) {
    command = getLastQueuedCommand(true);
    if (nullptr != command) {
      command->awaitCompletion();
      command->release();
    }
  }
  if (nullptr == command) {
    // Send a finish to make sure we finished all commands
    command = new Marker(*this, false);
    if (command == NULL) {
      return;
    }
    ClPrint(LOG_DEBUG, LOG_CMD, "marker is queued");
    command->enqueue();
    command->awaitCompletion();
    command->release();
  }
  ClPrint(LOG_DEBUG, LOG_CMD, "All commands finished");
}

void HostQueue::loop(device::VirtualDevice* virtualDevice) {
  // Notify the caller that the queue is ready to accept commands.
  {
    ScopedLock sl(queueLock_);
    thread_.acceptingCommands_ = true;
    queueLock_.notify();
  }
  // Create a command batch with all the commands present in the queue.
  Command* head = NULL;
  Command* tail = NULL;
  while (true) {
    // Get one command from the queue
    Command* command = queue_.dequeue();
    if (command == NULL) {
      ScopedLock sl(queueLock_);
      while ((command = queue_.dequeue()) == NULL) {
        if (!thread_.acceptingCommands_) {
          return;
        }
        queueLock_.wait();
      }
    }

    command->retain();

    // Process the command's event wait list.
    const Command::EventWaitList& events = command->eventWaitList();
    bool dependencyFailed = false;

    for (const auto& it : events) {
      // Only wait if the command is enqueued into another queue.
      if (it->command().queue() != this) {
        // Runtime has to flush the current batch only if the dependent wait is blocking
        if (it->command().status() != CL_COMPLETE) {
          virtualDevice->flush(head, true);
          tail = head = NULL;
          dependencyFailed |= !it->awaitCompletion();
        }
      }
    }

    // Insert the command to the linked list.
    if (NULL == head) {  // if the list is empty
      head = tail = command;
    } else {
      tail->setNext(command);
      tail = command;
    }

    if (dependencyFailed) {
      command->setStatus(CL_EXEC_STATUS_ERROR_FOR_EVENTS_IN_WAIT_LIST);
      continue;
    }

    ClPrint(LOG_DEBUG, LOG_CMD, "command (%s) is submitted: %p", getOclCommandKindString(command->type()), command);

    command->setStatus(CL_SUBMITTED);

    // Submit to the device queue.
    command->submit(*virtualDevice);

    // if this is a user invisible marker command, then flush
    if (0 == command->type()) {
      virtualDevice->flush(head);
      tail = head = NULL;
    }
  }  // while (true) {
}

void HostQueue::append(Command& command) {
  // We retain the command here. It will be released when its status
  // changes to CL_COMPLETE
  if ((command.getWaitBits() & 0x1) != 0) {
    finish();
  }
  command.retain();
  command.setStatus(CL_QUEUED);
  queue_.enqueue(&command);
  if (!IS_HIP) {
    return;
  }

  if (command.waitingEvent() == nullptr) {
    // Set last submitted command
    Command* prevLastEnqueueCommand;
    command.retain();
    {
       // lastCmdLock_ ensures that lastEnqueueCommand() can retain the command before it is swapped
       // out. We want to keep this critical section as short as possible, so the command should be
       // released outside this section.
       ScopedLock l(lastCmdLock_);

       prevLastEnqueueCommand = lastEnqueueCommand_;
       lastEnqueueCommand_ = &command;
    }

    if (prevLastEnqueueCommand != nullptr) {
      prevLastEnqueueCommand->release();
    }
  }
}

bool HostQueue::isEmpty() {
  // Get a snapshot of queue size
  return queue_.empty();
}

Command* HostQueue::getLastQueuedCommand(bool retain) {
  if (AMD_DIRECT_DISPATCH) {
    // The batch update must be lock protected to avoid a race condition
    // when multiple threads submit/flush/update the batch at the same time
    ScopedLock sl(vdev()->execution());

    // Since the lastCmdLock_ is acquired, it is safe to read and retain the lastEnqueueCommand.
    // It is guaranteed that the pointer will not change.
    if (retain && lastEnqueueCommand_ != nullptr) {
      lastEnqueueCommand_->retain();
    }
    return lastEnqueueCommand_;
  } else {
    // Get last submitted command
    ScopedLock l(lastCmdLock_);

    // Since the lastCmdLock_ is acquired, it is safe to read and retain the lastEnqueueCommand.
    // It is guaranteed that the pointer will not change.
    if (retain && lastEnqueueCommand_ != nullptr) {
      lastEnqueueCommand_->retain();
    }
    return lastEnqueueCommand_;
  }
}

DeviceQueue::~DeviceQueue() {
  delete virtualDevice_;
  ScopedLock lock(context().lock());
  context().removeDeviceQueue(device(), this);
}

bool DeviceQueue::create() {
  static const bool InteropQueue = true;
  const bool defaultDeviceQueue = properties().test(CL_QUEUE_ON_DEVICE_DEFAULT);
  bool result = false;

  virtualDevice_ = device().createVirtualDevice(this);
  if (virtualDevice_ != NULL) {
    result = true;
    context().addDeviceQueue(device(), this, defaultDeviceQueue);
  }

  return result;
}

}  // namespace amd
<|endoftext|>


<commit_before>/*
Uses the sound_play library of ROS to play sound on the OS' default sound driver.
Listening on:
	/tawi/motors/wheels to geometry_msgs::Twist (directions to drive)
Publishing on:

*/
#include <threemxl/platform/io/configuration/XMLConfiguration.h>
#include <threemxl/dxlassert.h>
#include <ros/ros.h>
#include <threemxl/C3mxlROS.h>
#include <geometry_msgs/Twist.h>
#include "drivingDriver.h"

void DrivingDriver::init(){
	ID = 436436436;
	sub = handle.subscribe<geometry_msgs::Twist>("/tawi/motors/drive", 1, &DrivingDriver::driveCallback, this);
	//Parameters set in launch file.
	ROS_ASSERT(handle.getParam("motor_port", motor_port_name));
	ROS_ASSERT(handle.getParam("motor_config", motor_config_name));
	ROS_ASSERT(handle.getParam("wheel_diameter", wheelDiameter));
	ROS_ASSERT(handle.getParam("wheel_base", wheelBase));

	ROS_ASSERT(motor_config_xml.loadFile(motor_config_name));

	initMotors();

	DXL_SAFE_CALL(left_motor->set3MxlMode(motor_config_left.m3mxlMode));
	DXL_SAFE_CALL(right_motor->set3MxlMode(motor_config_right.m3mxlMode));

	ROS_INFO("Driver initialized");
}

void DrivingDriver::driveCallback(const geometry_msgs::Twist::ConstPtr &msg){

	double v_x = msg->linear.x*0.1;//(wheelDiameter/2);
	double v_theta = msg->angular.z * 0.1; //(wheelBase/wheelDiameter);

	double leftMotorVelocity = v_x - v_theta;
	double rightMotorVelocity = v_x + v_theta;
	ROS_INFO("driveCallback %f", leftMotorVelocity);

	left_motor->setSpeed(fix_max_speed(leftMotorVelocity));
	right_motor->setSpeed(fix_max_speed(rightMotorVelocity));

}

int DrivingDriver::getID() {
	return ID;
}

double DrivingDriver::fix_max_speed(double value){
	if(value > 1.35){
		return 1.35;
	}
	if(value < -1.35){
		return -1.35;
	}
	return value;
}

int DrivingDriver::getState(){
	return state;
}

bool DrivingDriver::setPower(int level){
	currentPower = level;
}

int DrivingDriver::getPower(){
	return currentPower;
}

bool DrivingDriver::drive(){

	return true;
}

bool DrivingDriver::stop() {
	//dingen
	return false;
}

void DrivingDriver::initMotors(){

	ros::Rate init_rate(10);

	motor_config_left.readConfig(motor_config_xml.root().section("left"));
	left_motor = new C3mxlROS(motor_port_name.c_str());
	left_motor->setConfig(&motor_config_left);

	while (ros::ok() && left_motor->init() != DXL_SUCCESS) {
		ROS_WARN_ONCE("Couldn't initialize left wheel motor, will continue trying every second");
		init_rate.sleep();
	}

	motor_config_right.readConfig(motor_config_xml.root().section("right"));
	right_motor = new C3mxlROS(motor_port_name.c_str());
	right_motor->setConfig(&motor_config_right);

	while (ros::ok() && right_motor->init() != DXL_SUCCESS) {
		ROS_WARN_ONCE("Couldn't initialize right wheel motor, will continue trying every second");
		init_rate.sleep();
	}

	left_motor->set3MxlMode(SPEED_MODE);
	right_motor->set3MxlMode(SPEED_MODE);
}

void DrivingDriver::spin() {
	ROS_INFO("Spinning da spin");

	ros::Rate r(10);

	while(ros::ok()) {

		ros::spinOnce();
		r.sleep();
	}
}

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

	ros::init(argc, argv, "drivingDriver");
	DrivingDriver dd;
	dd.spin();

	return 0;
}
<commit_msg>removed callback prints<commit_after>/*
Uses the sound_play library of ROS to play sound on the OS' default sound driver.
Listening on:
	/tawi/motors/wheels to geometry_msgs::Twist (directions to drive)
Publishing on:

*/
#include <threemxl/platform/io/configuration/XMLConfiguration.h>
#include <threemxl/dxlassert.h>
#include <ros/ros.h>
#include <threemxl/C3mxlROS.h>
#include <geometry_msgs/Twist.h>
#include "drivingDriver.h"

void DrivingDriver::init(){
	ID = 436436436;
	sub = handle.subscribe<geometry_msgs::Twist>("/tawi/motors/drive", 1, &DrivingDriver::driveCallback, this);
	//Parameters set in launch file.
	ROS_ASSERT(handle.getParam("motor_port", motor_port_name));
	ROS_ASSERT(handle.getParam("motor_config", motor_config_name));
	ROS_ASSERT(handle.getParam("wheel_diameter", wheelDiameter));
	ROS_ASSERT(handle.getParam("wheel_base", wheelBase));

	ROS_ASSERT(motor_config_xml.loadFile(motor_config_name));

	initMotors();

	DXL_SAFE_CALL(left_motor->set3MxlMode(motor_config_left.m3mxlMode));
	DXL_SAFE_CALL(right_motor->set3MxlMode(motor_config_right.m3mxlMode));

	ROS_INFO("Driver initialized");
}

void DrivingDriver::driveCallback(const geometry_msgs::Twist::ConstPtr &msg){

	double v_x = msg->linear.x*0.1;//(wheelDiameter/2);
	double v_theta = msg->angular.z * 0.1; //(wheelBase/wheelDiameter);

	double leftMotorVelocity = v_x - v_theta;
	double rightMotorVelocity = v_x + v_theta;

	left_motor->setSpeed(fix_max_speed(leftMotorVelocity));
	right_motor->setSpeed(fix_max_speed(rightMotorVelocity));

}

int DrivingDriver::getID() {
	return ID;
}

double DrivingDriver::fix_max_speed(double value){
	if(value > 1.35){
		return 1.35;
	}
	if(value < -1.35){
		return -1.35;
	}
	return value;
}

int DrivingDriver::getState(){
	return state;
}

bool DrivingDriver::setPower(int level){
	currentPower = level;
}

int DrivingDriver::getPower(){
	return currentPower;
}

bool DrivingDriver::drive(){

	return true;
}

bool DrivingDriver::stop() {
	//dingen
	return false;
}

void DrivingDriver::initMotors(){

	ros::Rate init_rate(10);

	motor_config_left.readConfig(motor_config_xml.root().section("left"));
	left_motor = new C3mxlROS(motor_port_name.c_str());
	left_motor->setConfig(&motor_config_left);

	while (ros::ok() && left_motor->init() != DXL_SUCCESS) {
		ROS_WARN_ONCE("Couldn't initialize left wheel motor, will continue trying every second");
		init_rate.sleep();
	}

	motor_config_right.readConfig(motor_config_xml.root().section("right"));
	right_motor = new C3mxlROS(motor_port_name.c_str());
	right_motor->setConfig(&motor_config_right);

	while (ros::ok() && right_motor->init() != DXL_SUCCESS) {
		ROS_WARN_ONCE("Couldn't initialize right wheel motor, will continue trying every second");
		init_rate.sleep();
	}

	left_motor->set3MxlMode(SPEED_MODE);
	right_motor->set3MxlMode(SPEED_MODE);
}

void DrivingDriver::spin() {
	ROS_INFO("Spinning da spin");

	ros::Rate r(10);

	while(ros::ok()) {

		ros::spinOnce();
		r.sleep();
	}
}

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

	ros::init(argc, argv, "drivingDriver");
	DrivingDriver dd;
	dd.spin();

	return 0;
}
<|endoftext|>


<commit_before>void build(Solution &s)
{
    auto &tess = s.addProject("google.tesseract", "master");
    tess += Git("https://github.com/tesseract-ocr/tesseract", "", "{v}");

    auto &libtesseract = tess.addTarget<LibraryTarget>("libtesseract");
    {
        libtesseract.setChecks("libtesseract");

        libtesseract.ExportAllSymbols = true;
        libtesseract.PackageDefinitions = true;
        libtesseract +=
            "src/api/.*\\.cpp"_rr,
            "src/api/.*\\.h"_rr,
            "src/api/tess_version.h.in",
            "src/arch/.*\\.cpp"_rr,
            "src/arch/.*\\.h"_rr,
            "src/ccmain/.*\\.cpp"_rr,
            "src/ccmain/.*\\.h"_rr,
            "src/ccstruct/.*\\.cpp"_rr,
            "src/ccstruct/.*\\.h"_rr,
            "src/ccutil/.*\\.cpp"_rr,
            "src/ccutil/.*\\.h"_rr,
            "src/classify/.*\\.cpp"_rr,
            "src/classify/.*\\.h"_rr,
            "src/cutil/.*\\.cpp"_rr,
            "src/cutil/.*\\.h"_rr,
            "src/dict/.*\\.cpp"_rr,
            "src/dict/.*\\.h"_rr,
            "src/lstm/.*\\.cpp"_rr,
            "src/lstm/.*\\.h"_rr,
            "src/opencl/.*\\.cpp"_rr,
            "src/opencl/.*\\.h"_rr,
            "src/textord/.*\\.cpp"_rr,
            "src/textord/.*\\.h"_rr,
            "src/viewer/.*\\.cpp"_rr,
            "src/viewer/.*\\.h"_rr,
            "src/wordrec/.*\\.cpp"_rr,
            "src/wordrec/.*\\.h"_rr;

        libtesseract -=
            "src/api/tesseractmain.cpp",
            "src/viewer/svpaint.cpp";

        libtesseract.Public +=
            "src/opencl"_id,
            "src/ccmain"_id,
            "src/api"_id,
            "src/dict"_id,
            "src/viewer"_id,
            "src/wordrec"_id,
            "src/ccstruct"_id,
            "src/cutil"_id,
            "src/textord"_id,
            "src/ccutil"_id,
            "src/lstm"_id,
            "src/classify"_id,
            "src/arch"_id;

        if (libtesseract.getCompilerType() == CompilerType::MSVC ||
            libtesseract.getCompilerType() == CompilerType::ClangCl)
        {
            libtesseract += "__SSE4_1__"_def;
            libtesseract.CompileOptions.push_back("-arch:AVX2");

            libtesseract -=
                "src/arch/dotproductfma.cpp";
        }

        libtesseract.Public += "HAVE_CONFIG_H"_d;
        libtesseract.Public += "_SILENCE_STDEXT_HASH_DEPRECATION_WARNINGS=1"_d;
        libtesseract.Public += "HAVE_LIBARCHIVE"_d;
        libtesseract.Interface += sw::Shared, "TESS_IMPORTS"_d;
        libtesseract.Private += sw::Shared, "TESS_EXPORTS"_d;

        libtesseract.Public += "org.sw.demo.danbloomberg.leptonica-master"_dep;
        libtesseract.Public += "org.sw.demo.libarchive.libarchive"_dep;

        if (libtesseract.getSettings().TargetOS.Type == OSType::Windows)
        {
            libtesseract.Public += "ws2_32.lib"_l;
            libtesseract.Protected += "NOMINMAX"_def;
        }

        libtesseract.Variables["TESSERACT_MAJOR_VERSION"] = libtesseract.Variables["PACKAGE_MAJOR_VERSION"];
        libtesseract.Variables["TESSERACT_MINOR_VERSION"] = libtesseract.Variables["PACKAGE_MINOR_VERSION"];
        libtesseract.Variables["TESSERACT_MICRO_VERSION"] = libtesseract.Variables["PACKAGE_PATCH_VERSION"];
        libtesseract.Variables["TESSERACT_VERSION_STR"] = "master";
        libtesseract.configureFile("src/api/tess_version.h.in", "tess_version.h");

        // install
        if (!libtesseract.DryRun)
        {
            const Files files
            {
                // from api/makefile.am
                "src/api/apitypes.h",
                "src/api/baseapi.h",
                "src/api/capi.h",
                "src/api/renderer.h",
                "tess_version.h",

                //from arch/makefile.am
                "src/arch/dotproduct.h",
                "src/arch/intsimdmatrix.h",
                "src/arch/simddetect.h",

                //from ccmain/makefile.am
                "src/ccmain/thresholder.h",
                "src/ccmain/ltrresultiterator.h",
                "src/ccmain/pageiterator.h",
                "src/ccmain/resultiterator.h",
                "src/ccmain/osdetect.h",

                //from ccstruct/makefile.am
                "src/ccstruct/publictypes.h",

                //from ccutil/makefile.am
                "src/ccutil/basedir.h",
                "src/ccutil/errcode.h",
                "src/ccutil/fileerr.h",
                "src/ccutil/genericvector.h",
                "src/ccutil/helpers.h",
                "src/ccutil/params.h",
                "src/ccutil/ocrclass.h",
                "src/ccutil/platform.h",
                "src/ccutil/serialis.h",
                "src/ccutil/strngs.h",
                "src/ccutil/unichar.h",
                "src/ccutil/unicharcompress.h",
                "src/ccutil/unicharmap.h",
                "src/ccutil/unicharset.h",

                //from lstm/makefile.am
                "src/lstm/convolve.h",
                "src/lstm/ctc.h",
                "src/lstm/fullyconnected.h",
                "src/lstm/functions.h",
                "src/lstm/input.h",
                "src/lstm/lstm.h",
                "src/lstm/lstmrecognizer.h",
                "src/lstm/maxpool.h",
                "src/lstm/networkbuilder.h",
                "src/lstm/network.h",
                "src/lstm/networkio.h",
                "src/lstm/networkscratch.h",
                "src/lstm/parallel.h",
                "src/lstm/plumbing.h",
                "src/lstm/recodebeam.h",
                "src/lstm/reconfig.h",
                "src/lstm/reversed.h",
                "src/lstm/series.h",
                "src/lstm/static_shape.h",
                "src/lstm/stridemap.h",
                "src/lstm/tfnetwork.h",
                "src/lstm/weightmatrix.h",
            };

            auto d = libtesseract.BinaryDir / "tesseract";
            fs::create_directories(d);
            for (auto f : files)
            {
                libtesseract.check_absolute(f);
                fs::copy_file(f, d / f.filename(), fs::copy_options::overwrite_existing);
            }
        }
    }

    //
    auto &tesseract = tess.addExecutable("tesseract");
    tesseract += "src/api/tesseractmain.cpp";
    tesseract += libtesseract;

    //
    auto &tessopt = tess.addStaticLibrary("tessopt");
    tessopt += "src/training/tessopt.*"_rr;
    tessopt.Public += libtesseract;

    //
    auto &common_training = tess.addStaticLibrary("common_training");
    common_training +=
        "src/training/commandlineflags.cpp",
        "src/training/commandlineflags.h",
        "src/training/commontraining.cpp",
        "src/training/commontraining.h";
    common_training.Public += tessopt;

    //
    auto &unicharset_training = tess.addStaticLibrary("unicharset_training");
    unicharset_training +=
        "src/training/icuerrorcode.*"_rr,
        "src/training/icuerrorcode.h",
        "src/training/lang_model_helpers.*"_rr,
        "src/training/lstmtester.*"_rr,
        "src/training/lstmtrainer.*"_rr,
        "src/training/normstrngs.*"_rr,
        "src/training/unicharset_training_utils.*"_rr,
        "src/training/validat.*"_rr;
    unicharset_training.Public += common_training;
    unicharset_training.Public += "org.sw.demo.unicode.icu.i18n"_dep;

    //
#define ADD_EXE(n, ...)               \
    auto &n = tess.addExecutable(#n); \
    n += "src/training/" #n ".*"_rr;  \
    n.Public += __VA_ARGS__;          \
    n

    ADD_EXE(ambiguous_words, libtesseract);
    ADD_EXE(classifier_tester, common_training);
    ADD_EXE(combine_lang_model, unicharset_training);
    ADD_EXE(combine_tessdata, libtesseract);
    ADD_EXE(cntraining, common_training);
    ADD_EXE(dawg2wordlist, libtesseract);
    ADD_EXE(mftraining, common_training) += "src/training/mergenf.*"_rr;
    ADD_EXE(shapeclustering, common_training);
    ADD_EXE(unicharset_extractor, unicharset_training);
    ADD_EXE(wordlist2dawg, libtesseract);
    ADD_EXE(lstmeval, unicharset_training);
    ADD_EXE(lstmtraining, unicharset_training);
    ADD_EXE(set_unicharset_properties, unicharset_training);

    ADD_EXE(text2image, unicharset_training);
    text2image +=
        "src/training/boxchar.cpp",
        "src/training/boxchar.h",
        "src/training/degradeimage.cpp",
        "src/training/degradeimage.h",
        "src/training/icuerrorcode.h",
        "src/training/ligature_table.cpp",
        "src/training/ligature_table.h",
        "src/training/normstrngs.cpp",
        "src/training/normstrngs.h",
        "src/training/pango_font_info.cpp",
        "src/training/pango_font_info.h",
        "src/training/stringrenderer.cpp",
        "src/training/stringrenderer.h",
        "src/training/text2image.cpp",
        "src/training/tlog.cpp",
        "src/training/tlog.h",
        "src/training/util.h";
    text2image.Public += "org.sw.demo.gnome.pango.pangocairo-1.43"_dep;
}

void check(Checker &c)
{
    auto &s = c.addSet("libtesseract");
    s.checkFunctionExists("getline");
    s.checkIncludeExists("dlfcn.h");
    s.checkIncludeExists("inttypes.h");
    s.checkIncludeExists("limits.h");
    s.checkIncludeExists("malloc.h");
    s.checkIncludeExists("memory.h");
    s.checkIncludeExists("stdbool.h");
    s.checkIncludeExists("stdint.h");
    s.checkIncludeExists("stdlib.h");
    s.checkIncludeExists("string.h");
    s.checkIncludeExists("sys/ipc.h");
    s.checkIncludeExists("sys/shm.h");
    s.checkIncludeExists("sys/stat.h");
    s.checkIncludeExists("sys/types.h");
    s.checkIncludeExists("sys/wait.h");
    s.checkIncludeExists("tiffio.h");
    s.checkIncludeExists("unistd.h");
    s.checkTypeSize("long long int");
    s.checkTypeSize("mbstate_t");
    s.checkTypeSize("off_t");
    s.checkTypeSize("size_t");
    s.checkTypeSize("void *");
    s.checkTypeSize("wchar_t");
    s.checkTypeSize("_Bool");
    {
        auto &c = s.checkSymbolExists("snprintf");
        c.Parameters.Includes.push_back("stdio.h");
    }
}
<commit_msg>[sw] Use the latest pango again.<commit_after>void build(Solution &s)
{
    auto &tess = s.addProject("google.tesseract", "master");
    tess += Git("https://github.com/tesseract-ocr/tesseract", "", "{v}");

    auto &libtesseract = tess.addTarget<LibraryTarget>("libtesseract");
    {
        libtesseract.setChecks("libtesseract");

        libtesseract.ExportAllSymbols = true;
        libtesseract.PackageDefinitions = true;
        libtesseract +=
            "src/api/.*\\.cpp"_rr,
            "src/api/.*\\.h"_rr,
            "src/api/tess_version.h.in",
            "src/arch/.*\\.cpp"_rr,
            "src/arch/.*\\.h"_rr,
            "src/ccmain/.*\\.cpp"_rr,
            "src/ccmain/.*\\.h"_rr,
            "src/ccstruct/.*\\.cpp"_rr,
            "src/ccstruct/.*\\.h"_rr,
            "src/ccutil/.*\\.cpp"_rr,
            "src/ccutil/.*\\.h"_rr,
            "src/classify/.*\\.cpp"_rr,
            "src/classify/.*\\.h"_rr,
            "src/cutil/.*\\.cpp"_rr,
            "src/cutil/.*\\.h"_rr,
            "src/dict/.*\\.cpp"_rr,
            "src/dict/.*\\.h"_rr,
            "src/lstm/.*\\.cpp"_rr,
            "src/lstm/.*\\.h"_rr,
            "src/opencl/.*\\.cpp"_rr,
            "src/opencl/.*\\.h"_rr,
            "src/textord/.*\\.cpp"_rr,
            "src/textord/.*\\.h"_rr,
            "src/viewer/.*\\.cpp"_rr,
            "src/viewer/.*\\.h"_rr,
            "src/wordrec/.*\\.cpp"_rr,
            "src/wordrec/.*\\.h"_rr;

        libtesseract -=
            "src/api/tesseractmain.cpp",
            "src/viewer/svpaint.cpp";

        libtesseract.Public +=
            "src/opencl"_id,
            "src/ccmain"_id,
            "src/api"_id,
            "src/dict"_id,
            "src/viewer"_id,
            "src/wordrec"_id,
            "src/ccstruct"_id,
            "src/cutil"_id,
            "src/textord"_id,
            "src/ccutil"_id,
            "src/lstm"_id,
            "src/classify"_id,
            "src/arch"_id;

        if (libtesseract.getCompilerType() == CompilerType::MSVC ||
            libtesseract.getCompilerType() == CompilerType::ClangCl)
        {
            libtesseract += "__SSE4_1__"_def;
            libtesseract.CompileOptions.push_back("-arch:AVX2");

            libtesseract -=
                "src/arch/dotproductfma.cpp";
        }

        libtesseract.Public += "HAVE_CONFIG_H"_d;
        libtesseract.Public += "_SILENCE_STDEXT_HASH_DEPRECATION_WARNINGS=1"_d;
        libtesseract.Public += "HAVE_LIBARCHIVE"_d;
        libtesseract.Interface += sw::Shared, "TESS_IMPORTS"_d;
        libtesseract.Private += sw::Shared, "TESS_EXPORTS"_d;

        libtesseract.Public += "org.sw.demo.danbloomberg.leptonica-master"_dep;
        libtesseract.Public += "org.sw.demo.libarchive.libarchive"_dep;

        if (libtesseract.getSettings().TargetOS.Type == OSType::Windows)
        {
            libtesseract.Public += "ws2_32.lib"_l;
            libtesseract.Protected += "NOMINMAX"_def;
        }

        libtesseract.Variables["TESSERACT_MAJOR_VERSION"] = libtesseract.Variables["PACKAGE_MAJOR_VERSION"];
        libtesseract.Variables["TESSERACT_MINOR_VERSION"] = libtesseract.Variables["PACKAGE_MINOR_VERSION"];
        libtesseract.Variables["TESSERACT_MICRO_VERSION"] = libtesseract.Variables["PACKAGE_PATCH_VERSION"];
        libtesseract.Variables["TESSERACT_VERSION_STR"] = "master";
        libtesseract.configureFile("src/api/tess_version.h.in", "tess_version.h");

        // install
        if (!libtesseract.DryRun)
        {
            const Files files
            {
                // from api/makefile.am
                "src/api/apitypes.h",
                "src/api/baseapi.h",
                "src/api/capi.h",
                "src/api/renderer.h",
                "tess_version.h",

                //from arch/makefile.am
                "src/arch/dotproduct.h",
                "src/arch/intsimdmatrix.h",
                "src/arch/simddetect.h",

                //from ccmain/makefile.am
                "src/ccmain/thresholder.h",
                "src/ccmain/ltrresultiterator.h",
                "src/ccmain/pageiterator.h",
                "src/ccmain/resultiterator.h",
                "src/ccmain/osdetect.h",

                //from ccstruct/makefile.am
                "src/ccstruct/publictypes.h",

                //from ccutil/makefile.am
                "src/ccutil/basedir.h",
                "src/ccutil/errcode.h",
                "src/ccutil/fileerr.h",
                "src/ccutil/genericvector.h",
                "src/ccutil/helpers.h",
                "src/ccutil/params.h",
                "src/ccutil/ocrclass.h",
                "src/ccutil/platform.h",
                "src/ccutil/serialis.h",
                "src/ccutil/strngs.h",
                "src/ccutil/unichar.h",
                "src/ccutil/unicharcompress.h",
                "src/ccutil/unicharmap.h",
                "src/ccutil/unicharset.h",

                //from lstm/makefile.am
                "src/lstm/convolve.h",
                "src/lstm/ctc.h",
                "src/lstm/fullyconnected.h",
                "src/lstm/functions.h",
                "src/lstm/input.h",
                "src/lstm/lstm.h",
                "src/lstm/lstmrecognizer.h",
                "src/lstm/maxpool.h",
                "src/lstm/networkbuilder.h",
                "src/lstm/network.h",
                "src/lstm/networkio.h",
                "src/lstm/networkscratch.h",
                "src/lstm/parallel.h",
                "src/lstm/plumbing.h",
                "src/lstm/recodebeam.h",
                "src/lstm/reconfig.h",
                "src/lstm/reversed.h",
                "src/lstm/series.h",
                "src/lstm/static_shape.h",
                "src/lstm/stridemap.h",
                "src/lstm/tfnetwork.h",
                "src/lstm/weightmatrix.h",
            };

            auto d = libtesseract.BinaryDir / "tesseract";
            fs::create_directories(d);
            for (auto f : files)
            {
                libtesseract.check_absolute(f);
                fs::copy_file(f, d / f.filename(), fs::copy_options::overwrite_existing);
            }
        }
    }

    //
    auto &tesseract = tess.addExecutable("tesseract");
    tesseract += "src/api/tesseractmain.cpp";
    tesseract += libtesseract;

    //
    auto &tessopt = tess.addStaticLibrary("tessopt");
    tessopt += "src/training/tessopt.*"_rr;
    tessopt.Public += libtesseract;

    //
    auto &common_training = tess.addStaticLibrary("common_training");
    common_training +=
        "src/training/commandlineflags.cpp",
        "src/training/commandlineflags.h",
        "src/training/commontraining.cpp",
        "src/training/commontraining.h";
    common_training.Public += tessopt;

    //
    auto &unicharset_training = tess.addStaticLibrary("unicharset_training");
    unicharset_training +=
        "src/training/icuerrorcode.*"_rr,
        "src/training/icuerrorcode.h",
        "src/training/lang_model_helpers.*"_rr,
        "src/training/lstmtester.*"_rr,
        "src/training/lstmtrainer.*"_rr,
        "src/training/normstrngs.*"_rr,
        "src/training/unicharset_training_utils.*"_rr,
        "src/training/validat.*"_rr;
    unicharset_training.Public += common_training;
    unicharset_training.Public += "org.sw.demo.unicode.icu.i18n"_dep;

    //
#define ADD_EXE(n, ...)               \
    auto &n = tess.addExecutable(#n); \
    n += "src/training/" #n ".*"_rr;  \
    n.Public += __VA_ARGS__;          \
    n

    ADD_EXE(ambiguous_words, libtesseract);
    ADD_EXE(classifier_tester, common_training);
    ADD_EXE(combine_lang_model, unicharset_training);
    ADD_EXE(combine_tessdata, libtesseract);
    ADD_EXE(cntraining, common_training);
    ADD_EXE(dawg2wordlist, libtesseract);
    ADD_EXE(mftraining, common_training) += "src/training/mergenf.*"_rr;
    ADD_EXE(shapeclustering, common_training);
    ADD_EXE(unicharset_extractor, unicharset_training);
    ADD_EXE(wordlist2dawg, libtesseract);
    ADD_EXE(lstmeval, unicharset_training);
    ADD_EXE(lstmtraining, unicharset_training);
    ADD_EXE(set_unicharset_properties, unicharset_training);

    ADD_EXE(text2image, unicharset_training);
    text2image +=
        "src/training/boxchar.cpp",
        "src/training/boxchar.h",
        "src/training/degradeimage.cpp",
        "src/training/degradeimage.h",
        "src/training/icuerrorcode.h",
        "src/training/ligature_table.cpp",
        "src/training/ligature_table.h",
        "src/training/normstrngs.cpp",
        "src/training/normstrngs.h",
        "src/training/pango_font_info.cpp",
        "src/training/pango_font_info.h",
        "src/training/stringrenderer.cpp",
        "src/training/stringrenderer.h",
        "src/training/text2image.cpp",
        "src/training/tlog.cpp",
        "src/training/tlog.h",
        "src/training/util.h";
    text2image.Public += "org.sw.demo.gnome.pango.pangocairo"_dep;
}

void check(Checker &c)
{
    auto &s = c.addSet("libtesseract");
    s.checkFunctionExists("getline");
    s.checkIncludeExists("dlfcn.h");
    s.checkIncludeExists("inttypes.h");
    s.checkIncludeExists("limits.h");
    s.checkIncludeExists("malloc.h");
    s.checkIncludeExists("memory.h");
    s.checkIncludeExists("stdbool.h");
    s.checkIncludeExists("stdint.h");
    s.checkIncludeExists("stdlib.h");
    s.checkIncludeExists("string.h");
    s.checkIncludeExists("sys/ipc.h");
    s.checkIncludeExists("sys/shm.h");
    s.checkIncludeExists("sys/stat.h");
    s.checkIncludeExists("sys/types.h");
    s.checkIncludeExists("sys/wait.h");
    s.checkIncludeExists("tiffio.h");
    s.checkIncludeExists("unistd.h");
    s.checkTypeSize("long long int");
    s.checkTypeSize("mbstate_t");
    s.checkTypeSize("off_t");
    s.checkTypeSize("size_t");
    s.checkTypeSize("void *");
    s.checkTypeSize("wchar_t");
    s.checkTypeSize("_Bool");
    {
        auto &c = s.checkSymbolExists("snprintf");
        c.Parameters.Includes.push_back("stdio.h");
    }
}
<|endoftext|>


<commit_before>/* Copyright 2014-2015 Samsung Electronics Co., Ltd.
 *
 * 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 <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "jerry.h"
#include "jrt/jrt.h"

/**
 * Maximum command line arguments number
 */
#define JERRY_MAX_COMMAND_LINE_ARGS (64)

/**
 * Maximum size of source code buffer
 */
#define JERRY_SOURCE_BUFFER_SIZE (1048576)

/**
 * Standalone Jerry exit codes
 */
#define JERRY_STANDALONE_EXIT_CODE_OK   (0)
#define JERRY_STANDALONE_EXIT_CODE_FAIL (1)

static uint8_t source_buffer[ JERRY_SOURCE_BUFFER_SIZE ];

static const jerry_api_char_t *
read_sources (const char *script_file_names[],
              int files_count,
              size_t *out_source_size_p)
{
  int i;
  uint8_t *source_buffer_tail = source_buffer;

  for (i = 0; i < files_count; i++)
  {
    const char *script_file_name = script_file_names[i];

    FILE *file = fopen (script_file_name, "r");

    if (file == NULL)
    {
      break;
    }

    int fseek_status = fseek (file, 0, SEEK_END);

    if (fseek_status != 0)
    {
      break;
    }

    long script_len = ftell (file);

    if (script_len < 0)
    {
      break;
    }

    rewind (file);

    const size_t current_source_size = (size_t)script_len;

    if (source_buffer_tail + current_source_size >= source_buffer + sizeof (source_buffer))
    {
      break;
    }

    size_t bytes_read = fread (source_buffer_tail, 1, current_source_size, file);
    if (bytes_read < current_source_size)
    {
      break;
    }

    fclose (file);

    source_buffer_tail += current_source_size;
  }

  if (i < files_count)
  {
    JERRY_ERROR_MSG ("Failed to read script N%d\n", i + 1);

    return NULL;
  }
  else
  {
    const size_t source_size = (size_t) (source_buffer_tail - source_buffer);

    *out_source_size_p = source_size;

    return (const jerry_api_char_t *) source_buffer;
  }
}

/**
 * Provide the 'assert' implementation for the engine.
 *
 * @return true - if the argument was not a boolean value or it was boolean true.
 */
static bool
assert_handler (const jerry_api_object_t *function_obj_p __attr_unused___, /** < function object */
                const jerry_api_value_t *this_p __attr_unused___, /** < this arg */
                jerry_api_value_t *ret_val_p __attr_unused___, /** < return argument */
                const jerry_api_value_t args_p[], /** < function arguments */
                const jerry_api_length_t args_cnt) /** < number of function arguments */
{
  if (args_cnt > 0
      && args_p[0].type == JERRY_API_DATA_TYPE_BOOLEAN
      && args_p[0].v_bool != true)
  {
    JERRY_ERROR_MSG ("Script assertion failed\n");
    exit (JERRY_STANDALONE_EXIT_CODE_FAIL);
  }

  return true;
} /* assert_handler */

int
main (int argc,
      char **argv)
{
  if (argc >= JERRY_MAX_COMMAND_LINE_ARGS)
  {
    JERRY_ERROR_MSG ("Too many command line arguments. Current maximum is %d (JERRY_MAX_COMMAND_LINE_ARGS)\n", argc);

    return JERRY_STANDALONE_EXIT_CODE_FAIL;
  }

  const char *file_names[JERRY_MAX_COMMAND_LINE_ARGS];
  int i;
  int files_counter = 0;

  size_t max_data_bss_size, max_stack_size;
  jerry_get_memory_limits (&max_data_bss_size, &max_stack_size);

  // FIXME:
  //  jrt_set_mem_limits (max_data_bss_size, max_stack_size);

  jerry_flag_t flags = JERRY_FLAG_EMPTY;

#ifdef JERRY_ENABLE_LOG
  const char *log_file_name = NULL;
#endif /* JERRY_ENABLE_LOG */
  for (i = 1; i < argc; i++)
  {
    if (!strcmp ("-v", argv[i]))
    {
      printf ("Build date: \t%s\n", jerry_build_date);
      printf ("Commit hash:\t%s\n", jerry_commit_hash);
      printf ("Branch name:\t%s\n", jerry_branch_name);
      printf ("\n");
    }
    else if (!strcmp ("--mem-stats", argv[i]))
    {
      flags |= JERRY_FLAG_MEM_STATS;
    }
    else if (!strcmp ("--mem-stats-per-opcode", argv[i]))
    {
      flags |= JERRY_FLAG_MEM_STATS_PER_OPCODE;
    }
    else if (!strcmp ("--mem-stats-separate", argv[i]))
    {
      flags |= JERRY_FLAG_MEM_STATS_SEPARATE;
    }
    else if (!strcmp ("--parse-only", argv[i]))
    {
      flags |= JERRY_FLAG_PARSE_ONLY;
    }
    else if (!strcmp ("--show-opcodes", argv[i]))
    {
      flags |= JERRY_FLAG_SHOW_OPCODES;
    }
    else if (!strcmp ("--log-level", argv[i]))
    {
      flags |= JERRY_FLAG_ENABLE_LOG;
      if (++i < argc && strlen (argv[i]) == 1 && argv[i][0] >='0' && argv[i][0] <= '3')
      {
#ifdef JERRY_ENABLE_LOG
        jerry_debug_level = argv[i][0] - '0';
#endif /* JERRY_ENABLE_LOG */
      }
      else
      {
        JERRY_ERROR_MSG ("Error: wrong format or invalid argument\n");
        return JERRY_STANDALONE_EXIT_CODE_FAIL;
      }
    }
    else if (!strcmp ("--log-file", argv[i]))
    {
      flags |= JERRY_FLAG_ENABLE_LOG;
      if (++i < argc)
      {
#ifdef JERRY_ENABLE_LOG
        log_file_name = argv[i];
#endif /* JERRY_ENABLE_LOG */
      }
      else
      {
        JERRY_ERROR_MSG ("Error: wrong format of the arguments\n");
        return JERRY_STANDALONE_EXIT_CODE_FAIL;
      }
    }
    else if (!strcmp ("--abort-on-fail", argv[i]))
    {
      flags |= JERRY_FLAG_ABORT_ON_FAIL;
    }
    else
    {
      file_names[files_counter++] = argv[i];
    }
  }

  if (files_counter == 0)
  {
    return JERRY_STANDALONE_EXIT_CODE_OK;
  }
  else
  {
    size_t source_size;
    const jerry_api_char_t *source_p = read_sources (file_names, files_counter, &source_size);

    if (source_p == NULL)
    {
      return JERRY_STANDALONE_EXIT_CODE_FAIL;
    }
    else
    {
#ifdef JERRY_ENABLE_LOG
      if (log_file_name)
      {
        jerry_log_file = fopen (log_file_name, "w");
        if (jerry_log_file == NULL)
        {
          JERRY_ERROR_MSG ("Failed to open log file: %s\n", log_file_name);
          return JERRY_STANDALONE_EXIT_CODE_FAIL;
        }
      }
      else
      {
        jerry_log_file = stdout;
      }
#endif /* JERRY_ENABLE_LOG */

      jerry_init (flags);

      jerry_api_object_t *global_obj_p = jerry_api_get_global ();
      jerry_api_object_t *assert_func_p = jerry_api_create_external_function (assert_handler);
      jerry_api_value_t assert_value;
      assert_value.type = JERRY_API_DATA_TYPE_OBJECT;
      assert_value.v_object = assert_func_p;

      bool is_assert_added = jerry_api_set_object_field_value (global_obj_p,
                                                               (jerry_api_char_t *) "assert",
                                                               &assert_value);

      jerry_api_release_value (&assert_value);
      jerry_api_release_object (global_obj_p);

      if (!is_assert_added)
      {
        JERRY_ERROR_MSG ("Failed to register 'assert' method.");
      }

      jerry_completion_code_t ret_code = JERRY_COMPLETION_CODE_OK;

      if (!jerry_parse (source_p, source_size))
      {
        /* unhandled SyntaxError */
        ret_code = JERRY_COMPLETION_CODE_UNHANDLED_EXCEPTION;
      }
      else
      {
        if ((flags & JERRY_FLAG_PARSE_ONLY) == 0)
        {
          ret_code = jerry_run ();
        }
      }

      jerry_cleanup ();

#ifdef JERRY_ENABLE_LOG
      if (jerry_log_file && jerry_log_file != stdout)
      {
        fclose (jerry_log_file);
        jerry_log_file = NULL;
      }
#endif /* JERRY_ENABLE_LOG */

      if (ret_code == JERRY_COMPLETION_CODE_OK)
      {
        return JERRY_STANDALONE_EXIT_CODE_OK;
      }
      else
      {
        return JERRY_STANDALONE_EXIT_CODE_FAIL;
      }
    }
  }
}
<commit_msg>Fix resource leak at main-linux.cpp:read_sources.<commit_after>/* Copyright 2014-2015 Samsung Electronics Co., Ltd.
 *
 * 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 <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "jerry.h"
#include "jrt/jrt.h"

/**
 * Maximum command line arguments number
 */
#define JERRY_MAX_COMMAND_LINE_ARGS (64)

/**
 * Maximum size of source code buffer
 */
#define JERRY_SOURCE_BUFFER_SIZE (1048576)

/**
 * Standalone Jerry exit codes
 */
#define JERRY_STANDALONE_EXIT_CODE_OK   (0)
#define JERRY_STANDALONE_EXIT_CODE_FAIL (1)

static uint8_t source_buffer[ JERRY_SOURCE_BUFFER_SIZE ];

static const jerry_api_char_t *
read_sources (const char *script_file_names[],
              int files_count,
              size_t *out_source_size_p)
{
  int i;
  uint8_t *source_buffer_tail = source_buffer;

  for (i = 0; i < files_count; i++)
  {
    const char *script_file_name = script_file_names[i];

    FILE *file = fopen (script_file_name, "r");

    if (file == NULL)
    {
      break;
    }

    int fseek_status = fseek (file, 0, SEEK_END);

    if (fseek_status != 0)
    {
      break;
    }

    long script_len = ftell (file);

    if (script_len < 0)
    {
      fclose (file);
      break;
    }

    rewind (file);

    const size_t current_source_size = (size_t)script_len;

    if (source_buffer_tail + current_source_size >= source_buffer + sizeof (source_buffer))
    {
      fclose (file);
      break;
    }

    size_t bytes_read = fread (source_buffer_tail, 1, current_source_size, file);
    if (bytes_read < current_source_size)
    {
      fclose (file);
      break;
    }

    fclose (file);

    source_buffer_tail += current_source_size;
  }

  if (i < files_count)
  {
    JERRY_ERROR_MSG ("Failed to read script N%d\n", i + 1);

    return NULL;
  }
  else
  {
    const size_t source_size = (size_t) (source_buffer_tail - source_buffer);

    *out_source_size_p = source_size;

    return (const jerry_api_char_t *) source_buffer;
  }
}

/**
 * Provide the 'assert' implementation for the engine.
 *
 * @return true - if the argument was not a boolean value or it was boolean true.
 */
static bool
assert_handler (const jerry_api_object_t *function_obj_p __attr_unused___, /** < function object */
                const jerry_api_value_t *this_p __attr_unused___, /** < this arg */
                jerry_api_value_t *ret_val_p __attr_unused___, /** < return argument */
                const jerry_api_value_t args_p[], /** < function arguments */
                const jerry_api_length_t args_cnt) /** < number of function arguments */
{
  if (args_cnt > 0
      && args_p[0].type == JERRY_API_DATA_TYPE_BOOLEAN
      && args_p[0].v_bool != true)
  {
    JERRY_ERROR_MSG ("Script assertion failed\n");
    exit (JERRY_STANDALONE_EXIT_CODE_FAIL);
  }

  return true;
} /* assert_handler */

int
main (int argc,
      char **argv)
{
  if (argc >= JERRY_MAX_COMMAND_LINE_ARGS)
  {
    JERRY_ERROR_MSG ("Too many command line arguments. Current maximum is %d (JERRY_MAX_COMMAND_LINE_ARGS)\n", argc);

    return JERRY_STANDALONE_EXIT_CODE_FAIL;
  }

  const char *file_names[JERRY_MAX_COMMAND_LINE_ARGS];
  int i;
  int files_counter = 0;

  size_t max_data_bss_size, max_stack_size;
  jerry_get_memory_limits (&max_data_bss_size, &max_stack_size);

  // FIXME:
  //  jrt_set_mem_limits (max_data_bss_size, max_stack_size);

  jerry_flag_t flags = JERRY_FLAG_EMPTY;

#ifdef JERRY_ENABLE_LOG
  const char *log_file_name = NULL;
#endif /* JERRY_ENABLE_LOG */
  for (i = 1; i < argc; i++)
  {
    if (!strcmp ("-v", argv[i]))
    {
      printf ("Build date: \t%s\n", jerry_build_date);
      printf ("Commit hash:\t%s\n", jerry_commit_hash);
      printf ("Branch name:\t%s\n", jerry_branch_name);
      printf ("\n");
    }
    else if (!strcmp ("--mem-stats", argv[i]))
    {
      flags |= JERRY_FLAG_MEM_STATS;
    }
    else if (!strcmp ("--mem-stats-per-opcode", argv[i]))
    {
      flags |= JERRY_FLAG_MEM_STATS_PER_OPCODE;
    }
    else if (!strcmp ("--mem-stats-separate", argv[i]))
    {
      flags |= JERRY_FLAG_MEM_STATS_SEPARATE;
    }
    else if (!strcmp ("--parse-only", argv[i]))
    {
      flags |= JERRY_FLAG_PARSE_ONLY;
    }
    else if (!strcmp ("--show-opcodes", argv[i]))
    {
      flags |= JERRY_FLAG_SHOW_OPCODES;
    }
    else if (!strcmp ("--log-level", argv[i]))
    {
      flags |= JERRY_FLAG_ENABLE_LOG;
      if (++i < argc && strlen (argv[i]) == 1 && argv[i][0] >='0' && argv[i][0] <= '3')
      {
#ifdef JERRY_ENABLE_LOG
        jerry_debug_level = argv[i][0] - '0';
#endif /* JERRY_ENABLE_LOG */
      }
      else
      {
        JERRY_ERROR_MSG ("Error: wrong format or invalid argument\n");
        return JERRY_STANDALONE_EXIT_CODE_FAIL;
      }
    }
    else if (!strcmp ("--log-file", argv[i]))
    {
      flags |= JERRY_FLAG_ENABLE_LOG;
      if (++i < argc)
      {
#ifdef JERRY_ENABLE_LOG
        log_file_name = argv[i];
#endif /* JERRY_ENABLE_LOG */
      }
      else
      {
        JERRY_ERROR_MSG ("Error: wrong format of the arguments\n");
        return JERRY_STANDALONE_EXIT_CODE_FAIL;
      }
    }
    else if (!strcmp ("--abort-on-fail", argv[i]))
    {
      flags |= JERRY_FLAG_ABORT_ON_FAIL;
    }
    else
    {
      file_names[files_counter++] = argv[i];
    }
  }

  if (files_counter == 0)
  {
    return JERRY_STANDALONE_EXIT_CODE_OK;
  }
  else
  {
    size_t source_size;
    const jerry_api_char_t *source_p = read_sources (file_names, files_counter, &source_size);

    if (source_p == NULL)
    {
      return JERRY_STANDALONE_EXIT_CODE_FAIL;
    }
    else
    {
#ifdef JERRY_ENABLE_LOG
      if (log_file_name)
      {
        jerry_log_file = fopen (log_file_name, "w");
        if (jerry_log_file == NULL)
        {
          JERRY_ERROR_MSG ("Failed to open log file: %s\n", log_file_name);
          return JERRY_STANDALONE_EXIT_CODE_FAIL;
        }
      }
      else
      {
        jerry_log_file = stdout;
      }
#endif /* JERRY_ENABLE_LOG */

      jerry_init (flags);

      jerry_api_object_t *global_obj_p = jerry_api_get_global ();
      jerry_api_object_t *assert_func_p = jerry_api_create_external_function (assert_handler);
      jerry_api_value_t assert_value;
      assert_value.type = JERRY_API_DATA_TYPE_OBJECT;
      assert_value.v_object = assert_func_p;

      bool is_assert_added = jerry_api_set_object_field_value (global_obj_p,
                                                               (jerry_api_char_t *) "assert",
                                                               &assert_value);

      jerry_api_release_value (&assert_value);
      jerry_api_release_object (global_obj_p);

      if (!is_assert_added)
      {
        JERRY_ERROR_MSG ("Failed to register 'assert' method.");
      }

      jerry_completion_code_t ret_code = JERRY_COMPLETION_CODE_OK;

      if (!jerry_parse (source_p, source_size))
      {
        /* unhandled SyntaxError */
        ret_code = JERRY_COMPLETION_CODE_UNHANDLED_EXCEPTION;
      }
      else
      {
        if ((flags & JERRY_FLAG_PARSE_ONLY) == 0)
        {
          ret_code = jerry_run ();
        }
      }

      jerry_cleanup ();

#ifdef JERRY_ENABLE_LOG
      if (jerry_log_file && jerry_log_file != stdout)
      {
        fclose (jerry_log_file);
        jerry_log_file = NULL;
      }
#endif /* JERRY_ENABLE_LOG */

      if (ret_code == JERRY_COMPLETION_CODE_OK)
      {
        return JERRY_STANDALONE_EXIT_CODE_OK;
      }
      else
      {
        return JERRY_STANDALONE_EXIT_CODE_FAIL;
      }
    }
  }
}
<|endoftext|>


<commit_before>#ifndef SCHEDULER_TAG_HH
# define SCHEDULER_TAG_HH

# include <libport/symbol.hh>
# include <libport/weak-ptr.hh>

# include "scheduler/fwd.hh"

namespace scheduler
{

  class Tag
  {
  public:
    static rTag fresh (libport::Symbol name);
    static rTag fresh (rTag parent, libport::Symbol name);
    virtual ~Tag ();

    rTag self () const;

    bool frozen () const;
    bool blocked () const;

    void freeze (const Job&);
    void unfreeze (const Job&);
    void block (const Job&);
    void unblock (const Job&);
    void stop (const Job&);

    bool own_blocked () const;
    void set_blocked (bool);

    const libport::Symbol& name_get () const;

  private:
    Tag (libport::Symbol name);
    Tag (rTag parent, libport::Symbol name);
    libport::weak_ptr<Tag> self_;
    rTag            parent_;
    bool            blocked_;
    bool            frozen_;
    libport::Symbol name_;
  };

} // namespace scheduler

# include "scheduler/tag.hxx"

#endif // SCHEDULER_TAG_HH
<commit_msg>Add Tag comments<commit_after>#ifndef SCHEDULER_TAG_HH
# define SCHEDULER_TAG_HH

# include <libport/symbol.hh>
# include <libport/weak-ptr.hh>

# include "scheduler/fwd.hh"

namespace scheduler
{

  // A Tag is an entity attached to zero or more scheduler jobs. Each job
  // can have zero or more tags. When a new job is created, it usually
  // inherits the tags from its creator.
  //
  // The Tag state is represented by two parameters:
  //
  //   - frozen: jobs with this tag are not supposed to do any useful work;
  //
  //   - blocked: jobs with this tag are supposed to rewind their call
  //     stack until they die or until they are no longer affected by
  //     the tag.
  //
  // A tag is frozen when it has been explicitly frozen or when its parent
  // is frozen. Ditto for blocked.
  //
  // Stopping a tag is an immediate operation: all the jobs holding this
  // tag must act as if they were blocked, but only once. For example, they
  // must rewind their call stack in order not to be blocked anymore, but
  // when they resume execution, if they get the same tag again, they will
  // not act as if they were blocked again.

  class Tag
  {
  public:
    // Create a new tag, with or without a parent
    static rTag fresh (libport::Symbol name);
    static rTag fresh (rTag parent, libport::Symbol name);
    virtual ~Tag ();

    // Get a reference-counted pointer on the tag
    rTag self () const;

    // Is this tag directly or indirectly frozen or blocked?
    bool frozen () const;
    bool blocked () const;

    // Act on a tag and make the scheduler take it into account
    void freeze (const Job&);
    void unfreeze (const Job&);
    void block (const Job&);
    void unblock (const Job&);
    void stop (const Job&);

    // Return true if the tag has been directly blocked through a call
    // to "block". Return false if it is only indirectly blocked
    // through its parent.
    bool own_blocked () const;

    // Mark the tag as blocked. This is supposed to be used by the
    // scheduler to execute a "stop" command. It can also be used to
    // block a tag but without necessarily resuming its execution so that
    // it can rewind its call stack. For example, it can be used to stop
    // jobs if we know that the tag is permanently attached to the job:
    // if the job is currently sleeping, it may not be woken up just
    // so that it can die, it may die after it is done sleeping.
    void set_blocked (bool);

    const libport::Symbol& name_get () const;

  private:
    Tag (libport::Symbol name);
    Tag (rTag parent, libport::Symbol name);
    libport::weak_ptr<Tag> self_;
    rTag            parent_;
    bool            blocked_;
    bool            frozen_;
    libport::Symbol name_;
  };

} // namespace scheduler

# include "scheduler/tag.hxx"

#endif // SCHEDULER_TAG_HH
<|endoftext|>


<commit_before>#pragma once

//std
#include <ostream>
#include <array>
#include <vector>

//glm
#include <glm\glm.hpp>

template<typename T>
inline void read(std::istream& istream, T& t)
{
	istream.read(reinterpret_cast<char*>(&t), sizeof(T));
}

template<typename T>
inline void read(std::istream& istream, std::string& s)
{
    std::getline(istream, s, '\0');
}

template<typename T, size_t N>
inline void read(std::istream& istream, std::array<T, N>& data)
{
    istream.read(reinterpret_cast<char*>(data.data()), sizeof(T) * N);
}

//TODO: not the most efficient thing in the world, ask on SO how this might be done better
//drawbacks:
// T must have a default constructor
template<typename T>
inline void read(std::istream& istream, std::vector<T>& data, size_t count)
{
    data.reserve(count);

    std::vector<T> buffer;
    buffer.resize(count);

    istream.read(reinterpret_cast<char*>(buffer.data()), sizeof(T) * count);

    std::copy(buffer.begin(), buffer.end(), std::back_inserter(data));
}

template<typename T, size_t N>
inline void read(std::istream& istream, T data[N])
{
    istream.read(reinterpret_cast<char*>(data), _countof(data) * sizeof(T))
}

template<typename T>
inline void write(std::ostream& ostream, T& t)
{
    ostream.write(reinterpret_cast<char*>(&t), sizeof(T));
}

template<typename T>
std::ostream& operator<<(std::ostream& ostream, const glm::detail::tvec2<T>& v)
{
    return ostream << "[" << v.x << "," << v.y << "]";
}

template<typename T>
std::ostream& operator<<(std::ostream& ostream, const glm::detail::tvec3<T>& v)
{
    return ostream << "[" << v.x << "," << v.y << "," << v.z << "]";
}

template<typename T>
std::ostream& operator<<(std::ostream& ostream, const glm::detail::tvec4<T>& v)
{
    return ostream << "[" << v.x << "," << v.y << "," << v.z << "," << v.w << "]";
}
<commit_msg>added ability to extract texture data from GL into image struct added the ability to save PNGs from image structs f11 now takes "screenshots"<commit_after>#pragma once

//std
#include <ostream>
#include <array>
#include <vector>

//glm
#include <glm\glm.hpp>

template<typename T>
inline void read(std::istream& istream, T& t)
{
	istream.read(reinterpret_cast<char*>(&t), sizeof(T));
}

template<typename T>
inline void read(std::istream& istream, std::string& s)
{
    std::getline(istream, s, '\0');
}

template<typename T, size_t N>
inline void read(std::istream& istream, std::array<T, N>& data)
{
    istream.read(reinterpret_cast<char*>(data.data()), sizeof(T) * N);
}

//TODO: not the most efficient thing in the world, ask on SO how this might be done better
//drawbacks:
// T must have a default constructor
template<typename T>
inline void read(std::istream& istream, std::vector<T>& data, size_t count)
{
    data.reserve(count);

    std::vector<T> buffer;
    buffer.resize(count);

    istream.read(reinterpret_cast<char*>(buffer.data()), sizeof(T) * count);

    std::copy(buffer.begin(), buffer.end(), std::back_inserter(data));
}

template<typename T, size_t N>
inline void read(std::istream& istream, T data[N])
{
    istream.read(reinterpret_cast<char*>(data), _countof(data) * sizeof(T)) //TODO: same as sizeof(data)?
}

template<typename T>
inline void write(std::ostream& ostream, T& t)
{
    ostream.write(reinterpret_cast<char*>(&t), sizeof(T));
}

template<typename T>
std::ostream& operator<<(std::ostream& ostream, const glm::detail::tvec2<T>& v)
{
    return ostream << "[" << v.x << "," << v.y << "]";
}

template<typename T>
std::ostream& operator<<(std::ostream& ostream, const glm::detail::tvec3<T>& v)
{
    return ostream << "[" << v.x << "," << v.y << "," << v.z << "]";
}

template<typename T>
std::ostream& operator<<(std::ostream& ostream, const glm::detail::tvec4<T>& v)
{
    return ostream << "[" << v.x << "," << v.y << "," << v.z << "," << v.w << "]";
}
<|endoftext|>