<commit_before>/* This file is part of Strigi Desktop Search
 *
 * Copyright (C) 2006 Jos van den Oever <jos@vandenoever.info>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public License
 * along with this library; see the file COPYING.LIB.  If not, write to
 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
 * Boston, MA 02110-1301, USA.
 */
#include "interface.h"
#include "indexreader.h"
#include "combinedindexmanager.h"
#include "indexwriter.h"
#include "indexscheduler.h"
#include "eventlistener.h"
#include "streamanalyzer.h"
#include "analysisresult.h"
#include "analyzerconfiguration.h"
#include "stringstream.h"
#include "query.h"
#include "queryparser.h"
#include <sstream>
#include <iostream>
#include <vector>
#include <sys/types.h>
#include <signal.h>
#include <unistd.h>
using namespace std;
using namespace Strigi;

Interface::Interface(CombinedIndexManager& m, IndexScheduler& s)
        :ClientInterface(0), manager(m), scheduler(s), active(true) {
    eventListener = NULL;
}
void
Interface::setEventListener (EventListener* eListener) {
    eventListener = eListener;
}
int
Interface::countHits(const string& query) {
    QueryParser parser;
    Query q = parser.buildQuery(query);
    int count = manager.indexReader()->countHits(q);
    return count;
}
ClientInterface::Hits
Interface::getHits(const string& query, uint32_t max, uint32_t off) {
    QueryParser parser;
    Query q = parser.buildQuery(query);
    Hits hits;
    hits.hits = manager.indexReader()->query(q, off, max);
    // highlight the hits in the results
    // TODO fix highlighting
/*    vector<IndexedDocument>::iterator i;
    for (i = hits.hits.begin(); i != hits.hits.end(); ++i) {
        i->fragment = q.highlight(i->fragment);
    }*/
    return hits;
}
vector<string>
Interface::getBackEnds() {
    return manager.backEnds();
}
map<string, string>
Interface::getStatus() {
    map<string,string> status;
    status["Status"]=scheduler.getStateString();
    ostringstream out;
    out << scheduler.getQueueSize();
    status["Documents in queue"]= out.str();
    out.str("");
    IndexReader* reader = manager.indexReader();
    out << reader->countDocuments();
    status["Documents indexed"]= out.str();
    out.str("");
    out << reader->countWords();
    status["Unique words indexed"] = out.str();
    out.str("");
    out << reader->indexSize()/1024/1024;
    status["Index size"] = out.str()+" MB";
    return status;
}
string
Interface::stopDaemon() {
    cerr << "stopDaemon" << endl;
    active = false;
    // signal to all threads to quit. Do not use raise() here, because it will
    // cause a hang
    kill(getpid(), SIGINT);
    return "";
}
string
Interface::startIndexing() {
    scheduler.startIndexing();
    return "";
}
string
Interface::stopIndexing() {
    scheduler.stopIndexing();
    return "";
}
set<string>
Interface::getIndexedDirectories() {
    return scheduler.getIndexedDirectories();
}
string
Interface::setIndexedDirectories(set<string> dirs) {
    if (eventListener != NULL)
        eventListener->setIndexedDirectories( dirs);

    scheduler.setIndexedDirectories(dirs);
    return "";
}
void
Interface::setFilters(const vector<pair<bool,string> >& rules) {
    scheduler.getIndexerConfiguration().setFilters(rules);
}
vector<pair<bool,string> >
Interface::getFilters() {
    return scheduler.getIndexerConfiguration().filters();
}
void
Interface::indexFile(const string &path, uint64_t mtime,
        const vector<char>& content) {
    // TODO if the file is already there, remove it first
    IndexWriter* writer = manager.indexWriter();
    vector<string> paths;
    paths.push_back(path);
    writer->deleteEntries(paths);
    AnalyzerConfiguration ic;
    StreamAnalyzer streamindexer(ic);
    StringInputStream sr(&content[0], content.size(), false);
    AnalysisResult idx(path, mtime, *writer, streamindexer);
    idx.index(&sr);
}
vector<string>
Interface::getFieldNames() {
    return manager.indexReader()->fieldNames();
}
vector<pair<string, uint32_t> >
Interface::getHistogram(const string& query, const string& field,
        const string& labeltype) {
    return manager.indexReader()->histogram(query, field, labeltype);
}
int32_t
Interface::countKeywords(const string& keywordmatch,
        const vector<string>& fieldnames) {
    return 0;
}
vector<string>
Interface::getKeywords(const string& keywordmatch,
        const vector<string>& fieldnames,
        uint32_t max, uint32_t offset) {
    return vector<string>();
}
<commit_msg>Gracefully exit on dbus call "stopDaemon"<commit_after>/* This file is part of Strigi Desktop Search
 *
 * Copyright (C) 2006 Jos van den Oever <jos@vandenoever.info>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public License
 * along with this library; see the file COPYING.LIB.  If not, write to
 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
 * Boston, MA 02110-1301, USA.
 */
#include "interface.h"
#include "indexreader.h"
#include "combinedindexmanager.h"
#include "indexwriter.h"
#include "indexscheduler.h"
#include "eventlistener.h"
#include "streamanalyzer.h"
#include "analysisresult.h"
#include "analyzerconfiguration.h"
#include "stringstream.h"
#include "query.h"
#include "queryparser.h"
#include <sstream>
#include <iostream>
#include <vector>
#include <sys/types.h>
#include <signal.h>
#include <unistd.h>
using namespace std;
using namespace Strigi;

Interface::Interface(CombinedIndexManager& m, IndexScheduler& s)
        :ClientInterface(0), manager(m), scheduler(s), active(true) {
    eventListener = NULL;
}
void
Interface::setEventListener (EventListener* eListener) {
    eventListener = eListener;
}
int
Interface::countHits(const string& query) {
    QueryParser parser;
    Query q = parser.buildQuery(query);
    int count = manager.indexReader()->countHits(q);
    return count;
}
ClientInterface::Hits
Interface::getHits(const string& query, uint32_t max, uint32_t off) {
    QueryParser parser;
    Query q = parser.buildQuery(query);
    Hits hits;
    hits.hits = manager.indexReader()->query(q, off, max);
    // highlight the hits in the results
    // TODO fix highlighting
/*    vector<IndexedDocument>::iterator i;
    for (i = hits.hits.begin(); i != hits.hits.end(); ++i) {
        i->fragment = q.highlight(i->fragment);
    }*/
    return hits;
}
vector<string>
Interface::getBackEnds() {
    return manager.backEnds();
}
map<string, string>
Interface::getStatus() {
    map<string,string> status;
    status["Status"]=scheduler.getStateString();
    ostringstream out;
    out << scheduler.getQueueSize();
    status["Documents in queue"]= out.str();
    out.str("");
    IndexReader* reader = manager.indexReader();
    out << reader->countDocuments();
    status["Documents indexed"]= out.str();
    out.str("");
    out << reader->countWords();
    status["Unique words indexed"] = out.str();
    out.str("");
    out << reader->indexSize()/1024/1024;
    status["Index size"] = out.str()+" MB";
    return status;
}
string
Interface::stopDaemon() {
    cerr << "stopDaemon" << endl;
    StrigiThread::stopThreads();
    return "";
}
string
Interface::startIndexing() {
    scheduler.startIndexing();
    return "";
}
string
Interface::stopIndexing() {
    scheduler.stopIndexing();
    return "";
}
set<string>
Interface::getIndexedDirectories() {
    return scheduler.getIndexedDirectories();
}
string
Interface::setIndexedDirectories(set<string> dirs) {
    if (eventListener != NULL)
        eventListener->setIndexedDirectories( dirs);

    scheduler.setIndexedDirectories(dirs);
    return "";
}
void
Interface::setFilters(const vector<pair<bool,string> >& rules) {
    scheduler.getIndexerConfiguration().setFilters(rules);
}
vector<pair<bool,string> >
Interface::getFilters() {
    return scheduler.getIndexerConfiguration().filters();
}
void
Interface::indexFile(const string &path, uint64_t mtime,
        const vector<char>& content) {
    // TODO if the file is already there, remove it first
    IndexWriter* writer = manager.indexWriter();
    vector<string> paths;
    paths.push_back(path);
    writer->deleteEntries(paths);
    AnalyzerConfiguration ic;
    StreamAnalyzer streamindexer(ic);
    StringInputStream sr(&content[0], content.size(), false);
    AnalysisResult idx(path, mtime, *writer, streamindexer);
    idx.index(&sr);
}
vector<string>
Interface::getFieldNames() {
    return manager.indexReader()->fieldNames();
}
vector<pair<string, uint32_t> >
Interface::getHistogram(const string& query, const string& field,
        const string& labeltype) {
    return manager.indexReader()->histogram(query, field, labeltype);
}
int32_t
Interface::countKeywords(const string& keywordmatch,
        const vector<string>& fieldnames) {
    return 0;
}
vector<string>
Interface::getKeywords(const string& keywordmatch,
        const vector<string>& fieldnames,
        uint32_t max, uint32_t offset) {
    return vector<string>();
}
<|endoftext|>


<commit_before>/*
 *  Copyright (c) 2014 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "webrtc/modules/audio_processing/audio_processing_impl.h"

#include "webrtc/config.h"
#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "webrtc/modules/audio_processing/test/test_utils.h"
#include "webrtc/modules/interface/module_common_types.h"

using ::testing::Invoke;
using ::testing::Return;

namespace webrtc {

class MockInitialize : public AudioProcessingImpl {
 public:
  explicit MockInitialize(const Config& config) : AudioProcessingImpl(config) {
  }

  MOCK_METHOD0(InitializeLocked, int());
  int RealInitializeLocked() { return AudioProcessingImpl::InitializeLocked(); }
};

TEST(AudioProcessingImplTest, AudioParameterChangeTriggersInit) {
  Config config;
  MockInitialize mock(config);
  ON_CALL(mock, InitializeLocked())
      .WillByDefault(Invoke(&mock, &MockInitialize::RealInitializeLocked));

  EXPECT_CALL(mock, InitializeLocked()).Times(1);
  mock.Initialize();

  AudioFrame frame;
  // Call with the default parameters; there should be no init.
  frame.num_channels_ = 1;
  SetFrameSampleRate(&frame, 16000);
  EXPECT_CALL(mock, InitializeLocked())
      .Times(0);
  EXPECT_NOERR(mock.ProcessStream(&frame));
  EXPECT_NOERR(mock.AnalyzeReverseStream(&frame));

  // New sample rate. (Only impacts ProcessStream).
  SetFrameSampleRate(&frame, 32000);
  EXPECT_CALL(mock, InitializeLocked())
      .Times(1);
  EXPECT_NOERR(mock.ProcessStream(&frame));

  // New number of channels.
  frame.num_channels_ = 2;
  EXPECT_CALL(mock, InitializeLocked())
      .Times(2);
  EXPECT_NOERR(mock.ProcessStream(&frame));
  // ProcessStream sets num_channels_ == num_output_channels.
  frame.num_channels_ = 2;
  EXPECT_NOERR(mock.AnalyzeReverseStream(&frame));

  // A new sample rate passed to AnalyzeReverseStream should be an error and
  // not cause an init.
  SetFrameSampleRate(&frame, 16000);
  EXPECT_CALL(mock, InitializeLocked())
      .Times(0);
  EXPECT_EQ(mock.kBadSampleRateError, mock.AnalyzeReverseStream(&frame));
}

}  // namespace webrtc
<commit_msg>Reorder includes in audio_processing_impl_unittest.<commit_after>/*
 *  Copyright (c) 2014 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "webrtc/modules/audio_processing/audio_processing_impl.h"

#include "testing/gmock/include/gmock/gmock.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "webrtc/config.h"
#include "webrtc/modules/audio_processing/test/test_utils.h"
#include "webrtc/modules/interface/module_common_types.h"

using ::testing::Invoke;
using ::testing::Return;

namespace webrtc {

class MockInitialize : public AudioProcessingImpl {
 public:
  explicit MockInitialize(const Config& config) : AudioProcessingImpl(config) {
  }

  MOCK_METHOD0(InitializeLocked, int());
  int RealInitializeLocked() { return AudioProcessingImpl::InitializeLocked(); }
};

TEST(AudioProcessingImplTest, AudioParameterChangeTriggersInit) {
  Config config;
  MockInitialize mock(config);
  ON_CALL(mock, InitializeLocked())
      .WillByDefault(Invoke(&mock, &MockInitialize::RealInitializeLocked));

  EXPECT_CALL(mock, InitializeLocked()).Times(1);
  mock.Initialize();

  AudioFrame frame;
  // Call with the default parameters; there should be no init.
  frame.num_channels_ = 1;
  SetFrameSampleRate(&frame, 16000);
  EXPECT_CALL(mock, InitializeLocked())
      .Times(0);
  EXPECT_NOERR(mock.ProcessStream(&frame));
  EXPECT_NOERR(mock.AnalyzeReverseStream(&frame));

  // New sample rate. (Only impacts ProcessStream).
  SetFrameSampleRate(&frame, 32000);
  EXPECT_CALL(mock, InitializeLocked())
      .Times(1);
  EXPECT_NOERR(mock.ProcessStream(&frame));

  // New number of channels.
  frame.num_channels_ = 2;
  EXPECT_CALL(mock, InitializeLocked())
      .Times(2);
  EXPECT_NOERR(mock.ProcessStream(&frame));
  // ProcessStream sets num_channels_ == num_output_channels.
  frame.num_channels_ = 2;
  EXPECT_NOERR(mock.AnalyzeReverseStream(&frame));

  // A new sample rate passed to AnalyzeReverseStream should be an error and
  // not cause an init.
  SetFrameSampleRate(&frame, 16000);
  EXPECT_CALL(mock, InitializeLocked())
      .Times(0);
  EXPECT_EQ(mock.kBadSampleRateError, mock.AnalyzeReverseStream(&frame));
}

}  // namespace webrtc
<|endoftext|>


<commit_before>#include "AST/ast.h"
#include "Parse/parser.h"
#include "Sema/symbolcollector.h"
#include "Sema/symboltable.h"
#include "Sema/typechecker.h"
#include "Utils/astprinter.h"

// TODO: include codegen

#include <iostream>

static void Compile(const std::string& programFile)
{
    TosLang::FrontEnd::Parser parser;
    auto programAST = parser.ParseProgram(programFile);
    if (programAST == nullptr)
        return;

    auto symbolTable = std::make_shared<TosLang::FrontEnd::SymbolTable>();
    TosLang::FrontEnd::SymbolCollector sCollector{ symbolTable };
    size_t errorCount = sCollector.Run(programAST);
    if (errorCount != 0)
        return;

    TosLang::FrontEnd::TypeChecker tChecker{ symbolTable };
    errorCount = tChecker.Run(programAST);
    if (errorCount != 0)
        return;
}

static void DumpAST(const std::string& programFile)
{
    TosLang::FrontEnd::Parser parser;
    auto programAST = parser.ParseProgram(programFile);
    if (programAST == nullptr)
        return;

    std::ostream& stream = std::cout;
    TosLang::Utils::ASTPrinter<std::ostream> printer(std::move(stream));
}

int main(int argc, char** argv)
{
    if (argc < 2)
    {
        std::cout << "Correct usage: tc [options] <filename>"                               << std::endl
                  << "Options:"                                                             << std::endl
                  << "  -dump-ast                   Will output the program AST to stdout"  << std::endl;

    }
    else if (argc == 2)
    {
        Compile(argv[1]);
    }
    else
    {
        if (argv[1] == "-dump-ast")
        {
            DumpAST(argv[2]);
        }
    }
}<commit_msg>Finally fixing build break<commit_after>#include "AST/ast.h"
#include "Parse/parser.h"
#include "Sema/symbolcollector.h"
#include "Sema/symboltable.h"
#include "Sema/typechecker.h"
#include "Utils/astprinter.h"

// TODO: include codegen

#include <iostream>

static void Compile(const std::string& programFile)
{
    TosLang::FrontEnd::Parser parser;
    auto programAST = parser.ParseProgram(programFile);
    if (programAST == nullptr)
        return;

    auto symbolTable = std::make_shared<TosLang::FrontEnd::SymbolTable>();
    TosLang::FrontEnd::SymbolCollector sCollector{ symbolTable };
    size_t errorCount = sCollector.Run(programAST);
    if (errorCount != 0)
        return;

    TosLang::FrontEnd::TypeChecker tChecker{ symbolTable };
    errorCount = tChecker.Run(programAST);
    if (errorCount != 0)
        return;
}

static void DumpAST(const std::string& programFile)
{
    TosLang::FrontEnd::Parser parser;
    auto programAST = parser.ParseProgram(programFile);
    if (programAST == nullptr)
        return;

    std::ostream& stream = std::cout;
    TosLang::Utils::ASTPrinter<std::ostream> printer(stream);
}

int main(int argc, char** argv)
{
    if (argc < 2)
    {
        std::cout << "Correct usage: tc [options] <filename>"                               << std::endl
                  << "Options:"                                                             << std::endl
                  << "  -dump-ast                   Will output the program AST to stdout"  << std::endl;

    }
    else if (argc == 2)
    {
        Compile(argv[1]);
    }
    else
    {
        if (argv[1] == "-dump-ast")
        {
            DumpAST(argv[2]);
        }
    }
}<|endoftext|>


<commit_before>#ifndef _VINECPP_HEADER_HPP_
#define _VINECPP_HEADER_HPP_

// headers
#include <iostream>
#include <string>
#define _USE_MATH_DEFINES
#include <cmath>
#include <vector>
#include <nlopt.hpp>
#include <algorithm>
#include <utility>
#include <omp.h>

#include <stdlib.h>
#include <stdio.h>

#include<fstream>
#include<time.h>

// headers from the boost library
#include <boost/math/distributions/normal.hpp>
#include <boost/math/distributions/students_t.hpp>
//#include <boost/math/special_functions/detail/t_distribution_inv.hpp>
#include <boost/math/tools/roots.hpp>
#include <boost/random.hpp>

// gsl library
//#include <stdio.h>
//#include <gsl/gsl_cdf.h>

// User written headers
#include "VineCPP_helper.hpp"
#include "PC.hpp"
#include "PathToBoundsAndSeed.hpp"

#endif
<commit_msg>float.h included<commit_after>#ifndef _VINECPP_HEADER_HPP_
#define _VINECPP_HEADER_HPP_

// headers

#ifndef DBL_MAX
#define DBL_MAX 1.79769e+308
#endif

#include <iostream>
#include <string>
#define _USE_MATH_DEFINES
#include <cmath>
#include <vector>
#include <nlopt.hpp>
#include <algorithm>
#include <utility>
#include <omp.h>

#include <stdlib.h>
#include <stdio.h>

#include<fstream>
#include<time.h>

// headers from the boost library
#include <boost/math/distributions/normal.hpp>
#include <boost/math/distributions/students_t.hpp>
//#include <boost/math/special_functions/detail/t_distribution_inv.hpp>
#include <boost/math/tools/roots.hpp>
#include <boost/random.hpp>

// gsl library
//#include <stdio.h>
//#include <gsl/gsl_cdf.h>

// User written headers
#include "VineCPP_helper.hpp"
#include "PC.hpp"
#include "PathToBoundsAndSeed.hpp"

#endif
<|endoftext|>


<commit_before>/*
 *  Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "webrtc/modules/audio_coding/neteq/tools/input_audio_file.h"

#include "webrtc/base/checks.h"

namespace webrtc {
namespace test {

InputAudioFile::InputAudioFile(const std::string file_name) {
  fp_ = fopen(file_name.c_str(), "rb");
}

InputAudioFile::~InputAudioFile() { fclose(fp_); }

bool InputAudioFile::Read(size_t samples, int16_t* destination) {
  if (!fp_) {
    return false;
  }
  size_t samples_read = fread(destination, sizeof(int16_t), samples, fp_);
  if (samples_read < samples) {
    // Rewind and read the missing samples.
    rewind(fp_);
    size_t missing_samples = samples - samples_read;
    if (fread(destination, sizeof(int16_t), missing_samples, fp_) <
        missing_samples) {
      // Could not read enough even after rewinding the file.
      return false;
    }
  }
  return true;
}

bool InputAudioFile::Seek(int samples) {
  if (!fp_) {
    return false;
  }
  // Find file boundaries.
  const long current_pos = ftell(fp_);
  RTC_CHECK_NE(EOF, current_pos)
      << "Error returned when getting file position.";
  RTC_CHECK_EQ(0, fseek(fp_, 0, SEEK_END));  // Move to end of file.
  const long file_size = ftell(fp_);
  RTC_CHECK_NE(EOF, file_size) << "Error returned when getting file position.";
  // Find new position.
  long new_pos = current_pos + sizeof(int16_t) * samples;  // Samples to bytes.
  RTC_CHECK_GE(new_pos, 0)
      << "Trying to move to before the beginning of the file";
  new_pos = new_pos % file_size;  // Wrap around the end of the file.
  // Move to new position relative to the beginning of the file.
  RTC_CHECK_EQ(0, fseek(fp_, new_pos, SEEK_SET));
  return true;
}

void InputAudioFile::DuplicateInterleaved(const int16_t* source, size_t samples,
                                          size_t channels,
                                          int16_t* destination) {
  // Start from the end of |source| and |destination|, and work towards the
  // beginning. This is to allow in-place interleaving of the same array (i.e.,
  // |source| and |destination| are the same array).
  for (int i = static_cast<int>(samples - 1); i >= 0; --i) {
    for (int j = static_cast<int>(channels - 1); j >= 0; --j) {
      destination[i * channels + j] = source[i];
    }
  }
}

}  // namespace test
}  // namespace webrtc
<commit_msg>Fix a bug in InputAudioFile::Read<commit_after>/*
 *  Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#include "webrtc/modules/audio_coding/neteq/tools/input_audio_file.h"

#include "webrtc/base/checks.h"

namespace webrtc {
namespace test {

InputAudioFile::InputAudioFile(const std::string file_name) {
  fp_ = fopen(file_name.c_str(), "rb");
}

InputAudioFile::~InputAudioFile() { fclose(fp_); }

bool InputAudioFile::Read(size_t samples, int16_t* destination) {
  if (!fp_) {
    return false;
  }
  size_t samples_read = fread(destination, sizeof(int16_t), samples, fp_);
  if (samples_read < samples) {
    // Rewind and read the missing samples.
    rewind(fp_);
    size_t missing_samples = samples - samples_read;
    if (fread(destination + samples_read, sizeof(int16_t), missing_samples,
              fp_) < missing_samples) {
      // Could not read enough even after rewinding the file.
      return false;
    }
  }
  return true;
}

bool InputAudioFile::Seek(int samples) {
  if (!fp_) {
    return false;
  }
  // Find file boundaries.
  const long current_pos = ftell(fp_);
  RTC_CHECK_NE(EOF, current_pos)
      << "Error returned when getting file position.";
  RTC_CHECK_EQ(0, fseek(fp_, 0, SEEK_END));  // Move to end of file.
  const long file_size = ftell(fp_);
  RTC_CHECK_NE(EOF, file_size) << "Error returned when getting file position.";
  // Find new position.
  long new_pos = current_pos + sizeof(int16_t) * samples;  // Samples to bytes.
  RTC_CHECK_GE(new_pos, 0)
      << "Trying to move to before the beginning of the file";
  new_pos = new_pos % file_size;  // Wrap around the end of the file.
  // Move to new position relative to the beginning of the file.
  RTC_CHECK_EQ(0, fseek(fp_, new_pos, SEEK_SET));
  return true;
}

void InputAudioFile::DuplicateInterleaved(const int16_t* source, size_t samples,
                                          size_t channels,
                                          int16_t* destination) {
  // Start from the end of |source| and |destination|, and work towards the
  // beginning. This is to allow in-place interleaving of the same array (i.e.,
  // |source| and |destination| are the same array).
  for (int i = static_cast<int>(samples - 1); i >= 0; --i) {
    for (int j = static_cast<int>(channels - 1); j >= 0; --j) {
      destination[i * channels + j] = source[i];
    }
  }
}

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


<commit_before>/****************************************************************************
**
** Copyright (C) 2010 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:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file.  Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights.  These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/

// User includes
#include "qorganizeritemrequestqueue.h"

QOrganizerItemRequestQueue* QOrganizerItemRequestQueue::instance(
        QOrganizerItemSymbianEngine& aOrganizerItemManagerEngine)
{
    return new QOrganizerItemRequestQueue(aOrganizerItemManagerEngine);
}

QOrganizerItemRequestQueue::~QOrganizerItemRequestQueue()
{
    // Cleanup, delete all the pointers from the hash map
    QMapIterator<QOrganizerItemAbstractRequest*,
    COrganizerItemRequestsServiceProvider*> iter(m_abstractRequestMap);
    // Delete all the asynch requests one by one
    while (iter.hasNext()) {
        // Advance to next item
        iter.next();
        // It deletes the asynch request service provider
        delete iter.value();
    }
    // Clear the abstract request map
    m_abstractRequestMap.clear();
}

bool QOrganizerItemRequestQueue::startRequest(
        QOrganizerItemAbstractRequest* req)
{
    // Find m_abstractRequestMap if an asynchronous service provider for request
    // req already exists
    COrganizerItemRequestsServiceProvider* requestServiceProvider(
            m_abstractRequestMap[req]);
    // asynchronous service provider does not exist, create a new one
    if (!requestServiceProvider) {
            requestServiceProvider =
                    COrganizerItemRequestsServiceProvider::NewL(
                    iOrganizerItemManagerEngine);
            m_abstractRequestMap.insert(req, requestServiceProvider);
        }
    // Start the request
    return requestServiceProvider->StartRequest(req);
}

// To cancel aReq request
bool QOrganizerItemRequestQueue::cancelRequest(
        QOrganizerItemAbstractRequest* req)
{
    COrganizerItemRequestsServiceProvider* requestServiceProvider(
            m_abstractRequestMap[req]);
    //Cancel the request
    if (requestServiceProvider) {
            return requestServiceProvider->CancelRequest();
    }
    else {
        return false;
    }
}

// Wait for request to complete
bool QOrganizerItemRequestQueue::waitForRequestFinished(
        QOrganizerItemAbstractRequest* req, int msecs)
{
    Q_UNUSED(req)
    Q_UNUSED(msecs)
    // Not supported
    return false;
}

// Request is not more a valid request
void QOrganizerItemRequestQueue::requestDestroyed(
        QOrganizerItemAbstractRequest* req)
{
    // Get the pointer to the Asynchronous service provider for req request
    COrganizerItemRequestsServiceProvider* requestServiceProvider(
                m_abstractRequestMap[req]);
    if (requestServiceProvider) {
        // Delete the asynchronous service provider
        delete requestServiceProvider;
        // Remove req request & asynchronous service provider from the map
        // count is used only for the debugging purpose. Count should always be
        // 1, there is a serious programming mistake if not so.
        int count(m_abstractRequestMap.remove(req));
        }
}

QOrganizerItemRequestQueue::QOrganizerItemRequestQueue(
        QOrganizerItemSymbianEngine& aOrganizerItemManagerEngine) :
        iOrganizerItemManagerEngine(aOrganizerItemManagerEngine)
{
    // C++ constructor
}
<commit_msg>Rectified review comments in the Queue for asynch request<commit_after>/****************************************************************************
**
** Copyright (C) 2010 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:LGPL$
** No Commercial Usage
** This file contains pre-release code and may not be distributed.
** You may use this file in accordance with the terms and conditions
** contained in the Technology Preview License Agreement accompanying
** this package.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file.  Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights.  These rights are described in the Nokia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** If you have questions regarding the use of this file, please contact
** Nokia at qt-info@nokia.com.
**
**
**
**
**
**
**
**
** $QT_END_LICENSE$
**
****************************************************************************/

// User includes
#include "qorganizeritemrequestqueue.h"

QOrganizerItemRequestQueue* QOrganizerItemRequestQueue::instance(
        QOrganizerItemSymbianEngine& aOrganizerItemManagerEngine)
{
    return new QOrganizerItemRequestQueue(aOrganizerItemManagerEngine);
}

QOrganizerItemRequestQueue::~QOrganizerItemRequestQueue()
{
    // Cleanup, delete all the pointers from the hash map
    QMapIterator<QOrganizerItemAbstractRequest*,
    COrganizerItemRequestsServiceProvider*> iter(m_abstractRequestMap);
    // Delete all the asynch requests one by one
    while (iter.hasNext()) {
        // Advance to next item
        iter.next();
        // It deletes the asynch request service provider
        delete iter.value();
    }
    // Clear the abstract request map
    m_abstractRequestMap.clear();
}

bool QOrganizerItemRequestQueue::startRequest(
        QOrganizerItemAbstractRequest* req)
{
    // Find m_abstractRequestMap if an asynchronous service provider for request
    // req already exists
    COrganizerItemRequestsServiceProvider* requestServiceProvider(
            m_abstractRequestMap[req]);
    // asynchronous service provider does not exist, create a new one
    if (!requestServiceProvider) {
            requestServiceProvider =
                    COrganizerItemRequestsServiceProvider::NewL(
                    iOrganizerItemManagerEngine);
            m_abstractRequestMap.insert(req, requestServiceProvider);
        }
    // Start the request
    return requestServiceProvider->StartRequest(req);
}

// To cancel aReq request
bool QOrganizerItemRequestQueue::cancelRequest(
        QOrganizerItemAbstractRequest* req)
{
    COrganizerItemRequestsServiceProvider* requestServiceProvider(
            m_abstractRequestMap[req]);
    //Cancel the request
    if (requestServiceProvider) {
            return requestServiceProvider->CancelRequest();
    }
    else {
        return false;
    }
}

// Wait for request to complete
bool QOrganizerItemRequestQueue::waitForRequestFinished(
        QOrganizerItemAbstractRequest* req, int msecs)
{
    Q_UNUSED(req)
    Q_UNUSED(msecs)
    // Not supported
    return false;
}

// Request is not more a valid request
void QOrganizerItemRequestQueue::requestDestroyed(
        QOrganizerItemAbstractRequest* req)
{
    // Get the pointer to the Asynchronous service provider for req request
    COrganizerItemRequestsServiceProvider* requestServiceProvider(
                m_abstractRequestMap[req]);
    if (requestServiceProvider) {
        // Remove req request & asynchronous service provider from the map
        // count is used only for the debugging purpose. Count should always be
        // 1, there is a serious programming mistake if not so.
        int count(m_abstractRequestMap.remove(req));
		// Delete the asynchronous service provider
        delete requestServiceProvider;
        }
}

QOrganizerItemRequestQueue::QOrganizerItemRequestQueue(
        QOrganizerItemSymbianEngine& aOrganizerItemManagerEngine) :
        iOrganizerItemManagerEngine(aOrganizerItemManagerEngine)
{
    // C++ constructor
}
<|endoftext|>


<commit_before>/* Copyright (c) 2016 PaddlePaddle 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 "paddle/fluid/operators/fusion_seq_concat_fc_op.h"
#include <string>
#include "paddle/fluid/operators/math/blas.h"
#include "paddle/fluid/operators/math/cpu_vec.h"
#include "paddle/fluid/operators/math/fc_compute.h"
#include "paddle/fluid/platform/cpu_info.h"

namespace paddle {
namespace operators {

void FusionSeqConcatFCOp::InferShape(framework::InferShapeContext* ctx) const {
  PADDLE_ENFORCE(ctx->HasInput("X"),
                 "Input(X) of FusionSeqConcatFC should not be null.");
  PADDLE_ENFORCE(ctx->HasInput("FCWeight"),
                 "Input(FCWeight) of FusionSeqConcatFC should not be null.");

  PADDLE_ENFORCE(ctx->HasOutput("Out"),
                 "Output(Out) of FusionSeqConcatFC should not be null.");
  PADDLE_ENFORCE(ctx->HasOutput("FCOut"),
                 "Output(FCOut) of FusionSeqConcatFC should not be null.");

  // need check fc height = all inputs width sum

  auto x_dims = ctx->GetInputDim("X");
  const int M = x_dims[1];
  PADDLE_ENFORCE_EQ(x_dims.size(), 2, "Input(X)'s rank must be 2.");

  auto w_dims = ctx->GetInputDim("LSTMWeight");
  const int D = w_dims[1] / 4;
  PADDLE_ENFORCE_EQ(w_dims.size(), 2, "Input(LSTMWeight)'s rank must be 2.");
  PADDLE_ENFORCE_EQ(w_dims[0], D + M,
                    "LSTMWeight dims should be (%d + %d) * %d.", D + M, 4 * D);

  auto b_dims = ctx->GetInputDim("LSTMBias");
  PADDLE_ENFORCE_EQ(b_dims.size(), 2, "Input(LSTMBias)'s rank must be 2.");
  PADDLE_ENFORCE_EQ(b_dims[0], 1, "LSTMBias dims should be 1 x %d.", 4 * D);
  PADDLE_ENFORCE_EQ(b_dims[1], 4 * D, "LSTMBias dims should be 1 x %d.", 4 * D);

  auto c_dims = ctx->GetInputDim("C0");
  PADDLE_ENFORCE_EQ(c_dims.size(), 2, "Input(C0)'s rank must be 2.");
  PADDLE_ENFORCE_EQ(c_dims[1], D, "C0 dims should be N x %d.", D);
  if (ctx->HasInput("H0")) {
    auto h_dims = ctx->GetInputDim("H0");
    PADDLE_ENFORCE(h_dims == c_dims,
                   "The dimension of Input(H0) and Input(C0) "
                   "should be the same.");
  }

  auto atten_w_dims = ctx->GetInputDim("AttentionWeight");
  PADDLE_ENFORCE_EQ(atten_w_dims.size(), 2,
                    "Input(AttentionWeight)'s rank must be 2.");
  PADDLE_ENFORCE_EQ(atten_w_dims[0], M + D,
                    "AttentionWeight shapes must be (%d + %d) * 1.", M, D);
  PADDLE_ENFORCE_EQ(atten_w_dims[1], 1,
                    "AttentionWeight shapes must be (%d + %d) * 1.", M, D);
  if (ctx->HasInput("AttentionBias")) {
    auto atten_b_dims = ctx->GetInputDim("AttentionBias");
    PADDLE_ENFORCE_EQ(atten_b_dims.size(), 2,
                      "Input(AttentionBias)'s rank must be 2.");
    PADDLE_ENFORCE_EQ(atten_b_dims[0], 1,
                      "AttentionBias shapes must be 1 * 1.");
    PADDLE_ENFORCE_EQ(atten_b_dims[1], 1,
                      "AttentionBias shapes must be 1 * 1.");
  }

  if (ctx->HasInput("AttentionScalar")) {
    auto dims = ctx->GetInputDim("AttentionScalar");
    PADDLE_ENFORCE_EQ(dims.size(), 2,
                      "Input(AttentionScalar)'s rank must be 2.");
    PADDLE_ENFORCE_EQ(dims[0], 1, "AttentionScalar shapes must be 1 * 1.");
    PADDLE_ENFORCE_EQ(dims[1], 1, "AttentionScalar shapes must be 1 * 1.");
  }

  if (ctx->HasInput("AttentionScalarBias")) {
    auto dims = ctx->GetInputDim("AttentionScalarBias");
    PADDLE_ENFORCE(
        ctx->HasInput("AttentionScalar"),
        "AttentionScalar should not be null when have AttentionScalarBias.");
    PADDLE_ENFORCE_EQ(dims.size(), 2,
                      "Input(AttentionScalarBias)'s rank must be 2.");
    PADDLE_ENFORCE_EQ(dims[0], 1, "AttentionScalarBias shapes must be 1 * 1.");
    PADDLE_ENFORCE_EQ(dims[1], 1, "AttentionScalarBias shapes must be 1 * 1.");
  }

  framework::DDim out_dims({x_dims[0], D});
  ctx->SetOutputDim("Hidden", out_dims);
  ctx->SetOutputDim("Cell", out_dims);
  ctx->SetOutputDim("AttentionedX", {x_dims[0], 1});
  ctx->SetOutputDim("LSTMX", {1, M});
  ctx->SetOutputDim("LSTMOUT", {1, 4 * D});
  // AttentionFCOut should be reshape as (maxseqlen,1) in runtime
  ctx->ShareLoD("X", "Hidden");
  ctx->ShareLoD("X", "Cell");

  ctx->SetOutputDim("Out", out_dims);
  ctx->ShareLoD("X", /*->*/ "Out");
}

framework::OpKernelType FusionSeqConcatFCOp::GetExpectedKernelType(
    const framework::ExecutionContext& ctx) const {
  return framework::OpKernelType(
      framework::ToDataType(ctx.Input<framework::LoDTensor>("X")->type()),
      ctx.device_context());
}

void FusionSeqConcatFCOpMaker::Make() {
  AddInput("X",
           "(LoDTensor) input LodDTensors, the first one must be have ref lod "
           "for sequence expand, and the rest input should have same lod.")
      .AsDuplicable();
  AddInput("FCWeight", "(Tensor) the weights of fc.");
  AddInput("FCBias", "(Tensor, optional) the bias of fc.").AsDispensable();
  AddOutput("Out", "(LoDTensor) Output LodTensor.");
  AddOutput(
      "FCOut",
      "(Tensor) the intermediate tensor to keep the result of fc."
      "Shape is (N x D), where N is the batch size, D is the output dim of fc")
      .AsIntermediate();
  AddAttr<std::string>("fc_activation",
                       "(string, default: identity)"
                       "The activation for the result of fc."
                       "`identity` by default.")
      .SetDefault("identity")
      .InEnum({"sigmoid", "tanh", "relu", "identity"});
  AddComment(R"DOC(
Fusion Sequence expand + concat + fc Operator.

All below conditions should be meet:

The ref_level of seq_expand should be 0.

The ref lod of seq_expand level is the first input of concat.

The other inputs should have same lod and same batch size of ref lod.

The seq len of other inputs should be 1.

The concat axis should be 1.

)DOC");
}

// y[i] = (x[i] + bias[0]) > 0 ? (x[i] + bias[0]) : 0;
template <typename T>
inline void bias_relu(const int n, const T* x, const T* bias, T* y) {
  if (bias) {
    math::vec_add_bias<T, platform::jit::avx>(n, *bias, x, y);
    math::vec_relu<T, platform::jit::avx>(n, y, y);
  } else {
    math::vec_relu<T, platform::jit::avx>(n, x, y);
  }
}

template <typename T>
inline void vec_softmax(const int n, const T* x, T* y) {
  T scalar = x[0];
  // max
  for (int i = 1; i < n; ++i) {
    scalar = scalar < x[i] ? x[i] : scalar;
  }
  math::vec_add_bias<T, platform::jit::avx>(n, -scalar, x, y);  // sub
  math::vec_exp<T>(n, y, y);                                    // exp
  // sum
  scalar = T(0);
  for (int i = 0; i < n; ++i) {
    scalar += y[i];
  }
  math::vec_scal<T>(n, static_cast<T>(1) / scalar, y);  // scale
}

template <typename T>
class FusionSeqConcatFCKernel : public framework::OpKernel<T> {
 public:
  void Compute(const framework::ExecutionContext& ctx) const override {
    using DeviceContext = paddle::platform::CPUDeviceContext;
    auto* ins = ctx.Input<LoDTensor>("X");
    auto* w = ctx.Input<Tensor>("FCWeight");
    auto* b = ctx.Input<Tensor>("FCBias");

    auto* out = ctx.Output<LoDTensor>("Out");
    auto* fc_out = ctx.Output<Tensor>("FCOUT");

    std::function<void(const int, const T*, T*)> fc_act;
    auto& fc_act_str = ctx.Attr<std::string>("fc_activation");
    if (platform::jit::MayIUse(platform::jit::avx)) {
      math::VecActivations<T, platform::jit::avx> act_functor;
      fc_act = act_functor(fc_act_str);
    } else {
      math::VecActivations<T, platform::jit::isa_any> act_functor;
      fc_act = act_functor(fc_act_str);
    }

    PADDLE_ENFORCE_GT(ins.size(), 1, "Input(X)'s size must larger than 1.");
    auto* ref_in = ins[0];
    auto ref_in_lod = ref_in->lod();
    const int N = ref_in_lod[0].size() - 1;
    auto ref_in_dims = ref_in->dims();  // T x M0
    auto w_dims = w->dims();            // (M0+M1+M2+..) x D
    const int total_T = ref_in_dims[0];
    const int M0 = ref_in_dims[1];
    const int M1 = ins[1]->dims()[1];
    const int D = w_dims[1];

    const T* ref_in_data =
        ref_in->data<T>();  // size should be check at infershape
    const T* in1_data = ins[1]->data<T>();
    const T* w_data = w->data<T>();
    T* out_data = out->mutable_data<T>(ctx.GetPlace());
    T* fc_out_data = fc_out->mutable_data<T>(ctx.GetPlace());

    auto blas = math::GetBlas<DeviceContext, T>(ctx);
    math::FCCompute<DeviceContext, T>(blas, total_T, D, M0, ref_in_data, w_data,
                                      out_data, b ? b->data<T>() : NULL);
    w_data = w_data + M0 * D;

    // first one use write on
    blas.MatMul(N, D, M1, in1_data, w_data, fc_out_data);
    w_data = w_data + M1 * D;
    for (int i = 2; i < ins.size(); ++i) {
      // add on
      const T* in_data = ins[i]->data<T>();
      const int K = ins[i]->dims()[1];
      blas.GEMM(CblasNoTrans, CblasNoTrans, N, D, K, static_cast<T>(1), in_data,
                K, w_data, D, static_cast<T>(1), fc_out_data, D);
      w_data = w_data + K * D;
    }

    for (int i = 0; i < N; ++i) {
      int seq_len = ref_in_lod[0][i + 1] - ref_in_lod[0][i];
      T* src = fc_out_data + i * D;
      for (int step = 0; step < seq_len; ++step) {
        blas.VADD(D, out_data, src, out_data);
        out_data = out_data + D;
      }
    }

    fc_act(out_dims[0] * out_dims[1], out_data, out_data);
  }
};

}  // namespace operators
}  // namespace paddle

namespace ops = paddle::operators;
REGISTER_OPERATOR(fusion_seq_concat_fc, ops::FusionSeqConcatFCOp,
                  ops::FusionSeqConcatFCOpMaker,
                  paddle::framework::DefaultGradOpDescMaker<true>);

REGISTER_OP_CPU_KERNEL(fusion_seq_concat_fc,
                       ops::FusionSeqConcatFCKernel<float>,
                       ops::FusionSeqConcatFCKernel<double>);
<commit_msg>refine infershape and forward<commit_after>/* Copyright (c) 2016 PaddlePaddle 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 "paddle/fluid/operators/fusion_seq_concat_fc_op.h"
#include <string>
#include "paddle/fluid/operators/math/blas.h"
#include "paddle/fluid/operators/math/cpu_vec.h"
#include "paddle/fluid/operators/math/fc_compute.h"
#include "paddle/fluid/platform/cpu_info.h"

namespace paddle {
namespace operators {

void FusionSeqConcatFCOp::InferShape(framework::InferShapeContext* ctx) const {
  PADDLE_ENFORCE_GT(ctx->Inputs("X").size(), 1UL,
                    "Inputs(X) of FusionSeqConcatFCOp should larger than 1.");
  PADDLE_ENFORCE(ctx->HasInput("FCWeight"),
                 "Input(FCWeight) of FusionSeqConcatFC should not be null.");
  PADDLE_ENFORCE(ctx->HasOutput("Out"),
                 "Output(Out) of FusionSeqConcatFC should not be null.");
  PADDLE_ENFORCE(ctx->HasOutput("FCOut"),
                 "Output(FCOut) of FusionSeqConcatFC should not be null.");

  auto ins_dims = ctx->GetInputsDim("X");
  auto w_dims = ctx->GetInputDim("FCWeight");  // (M0+M1+M2+..) x D
  PADDLE_ENFORCE_EQ(w_dims.size(), 2UL, "Input(FCWeight)'s rank must be 2.");
  const int D = w_dims[1];
  int sum = ins_dims[0][1];
  for (size_t i = 1; i < ins_dims.size(); ++i) {
    sum += ins_dims[i][1];
  }
  PADDLE_ENFORCE_EQ(sum, w_dims[0],
                    "FC height should be sum of all inputs width.");
  if (ctx->HasInput("FCBias")) {
    auto b_dims = ctx->GetInputDim("FCBias");
    PADDLE_ENFORCE_EQ(b_dims.size(), 2, "Input(FCBias)'s rank must be 2.");
    PADDLE_ENFORCE_EQ(b_dims[0], 1, "FCBias shapes must be 1 * %d.", D);
    PADDLE_ENFORCE_EQ(b_dims[1], D, "FCBias shapes must be 1 * %d.", D);
  }

  ctx->SetOutputDim("Out", {ins_dims[0][0], D});
  // fcout should be reshape when run since can not get lod in infershape
  // explicit share the ref lod
  ctx->ShareLoD("X", "Out", 0);
}

framework::OpKernelType FusionSeqConcatFCOp::GetExpectedKernelType(
    const framework::ExecutionContext& ctx) const {
  return framework::OpKernelType(
      framework::ToDataType(ctx.Input<framework::LoDTensor>("X")->type()),
      ctx.device_context());
}

void FusionSeqConcatFCOpMaker::Make() {
  AddInput("X",
           "(LoDTensor) input LodDTensors, the first one must be have ref lod "
           "for sequence expand, and the rest input should have same lod.")
      .AsDuplicable();
  AddInput("FCWeight", "(Tensor) the weights of fc.");
  AddInput("FCBias", "(Tensor, optional) the bias of fc.").AsDispensable();
  AddOutput("Out", "(LoDTensor) Output LodTensor.");
  AddOutput(
      "FCOut",
      "(Tensor) the intermediate tensor to keep the result of fc."
      "Shape is (N x D), where N is the batch size, D is the output dim of fc")
      .AsIntermediate();
  AddAttr<std::string>("fc_activation",
                       "(string, default: identity)"
                       "The activation for the result of fc."
                       "`identity` by default.")
      .SetDefault("identity")
      .InEnum({"sigmoid", "tanh", "relu", "identity"});
  AddComment(R"DOC(
Fusion Sequence expand + concat + fc Operator.

All below conditions should be meet:

The ref_level of seq_expand should be 0.

The ref lod of seq_expand level is the first input of concat.

The other inputs should have same lod and same batch size of ref lod.

The seq len of other inputs should be 1.

The concat axis should be 1.

)DOC");
}

template <typename T>
class FusionSeqConcatFCKernel : public framework::OpKernel<T> {
 public:
  void Compute(const framework::ExecutionContext& ctx) const override {
    using DeviceContext = paddle::platform::CPUDeviceContext;
    auto ins = ctx.MultiInput<LoDTensor>("X");
    auto* w = ctx.Input<Tensor>("FCWeight");
    auto* b = ctx.Input<Tensor>("FCBias");
    auto* out = ctx.Output<LoDTensor>("Out");
    auto* fc_out = ctx.Output<Tensor>("FCOUT");

    auto* ref_in = ins[0];
    auto ref_lod = ref_in->lod();
    auto in1_lod = ins[1]->lod();
    auto ref_dims = ref_in->dims();  // T x M0
    auto in1_dims = ins[1]->dims();  // N x M1
    auto w_dims = w->dims();
    const int N = ref_lod[0].size() - 1;
    const int total_T = ref_dims[0];
    const int M0 = ref_dims[1];
    const int M1 = in1_dims[1];
    const int D = w_dims[1];

    // some check and fcout should be reshape here
    // since infershape can not get lod info
    PADDLE_ENFORCE_EQ(ref_lod.size(), 1UL, "Only support input lod size is 1.");
    PADDLE_ENFORCE_EQ(in1_lod.size(), 1UL, "Only support input lod size is 1.");
    PADDLE_ENFORCE_EQ(in1_lod[0].size() - 1, N,
                      "Batch size of all inputs should be equal.");
    PADDLE_ENFORCE_EQ(in1_lod[0][N], N,
                      "Seq_length of other inputs should be 1.");
    PADDLE_ENFORCE_EQ(in1_dims[0], N, "input height should be batch size.");
    for (size_t i = 2; i < ins.size(); ++i) {
      PADDLE_ENFORCE_EQ(ins[i]->dims()[0], N,
                        "All other inputs height should be equal");
      PADDLE_ENFORCE_EQ(ins[i]->lod(), in1_lod,
                        "All other inputs should have same lod");
    }
    fc_out->Resize({N, D});

    std::function<void(const int, const T*, T*)> fc_act;
    auto& fc_act_str = ctx.Attr<std::string>("fc_activation");
    if (platform::jit::MayIUse(platform::jit::avx)) {
      math::VecActivations<T, platform::jit::avx> act_functor;
      fc_act = act_functor(fc_act_str);
    } else {
      math::VecActivations<T, platform::jit::isa_any> act_functor;
      fc_act = act_functor(fc_act_str);
    }

    const T* ref_in_data = ref_in->data<T>();
    const T* in1_data = ins[1]->data<T>();
    const T* w_data = w->data<T>();
    T* out_data = out->mutable_data<T>(ctx.GetPlace());
    T* fc_out_data = fc_out->mutable_data<T>(ctx.GetPlace());

    auto blas = math::GetBlas<DeviceContext, T>(ctx);
    math::FCCompute<DeviceContext, T>(blas, total_T, D, M0, ref_in_data, w_data,
                                      out_data, b ? b->data<T>() : NULL);
    w_data = w_data + M0 * D;
    // first one use write on
    blas.MatMul(N, D, M1, in1_data, w_data, fc_out_data);
    w_data = w_data + M1 * D;
    for (size_t i = 2; i < ins.size(); ++i) {
      // add on
      const T* in_data = ins[i]->data<T>();
      const int K = ins[i]->dims()[1];
      blas.GEMM(CblasNoTrans, CblasNoTrans, N, D, K, static_cast<T>(1), in_data,
                K, w_data, D, static_cast<T>(1), fc_out_data, D);
      w_data = w_data + K * D;
    }

    for (int i = 0; i < N; ++i) {
      int seq_len = ref_lod[0][i + 1] - ref_lod[0][i];
      T* src = fc_out_data + i * D;
      for (int step = 0; step < seq_len; ++step) {
        blas.VADD(D, out_data, src, out_data);
        out_data = out_data + D;
      }
    }

    fc_act(total_T * D, out_data, out_data);
  }
};

}  // namespace operators
}  // namespace paddle

namespace ops = paddle::operators;
REGISTER_OPERATOR(fusion_seq_concat_fc, ops::FusionSeqConcatFCOp,
                  ops::FusionSeqConcatFCOpMaker,
                  paddle::framework::DefaultGradOpDescMaker<true>);

REGISTER_OP_CPU_KERNEL(fusion_seq_concat_fc,
                       ops::FusionSeqConcatFCKernel<float>,
                       ops::FusionSeqConcatFCKernel<double>);
<|endoftext|>


<commit_before>/*
 * Copyright 2016 Stoned Xander
 *
 * 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.
 */

/*
 * This example is not meant to simulate flocking, but only "almost"
 * straight line going agents and how it affects the search tree.
 */
#include <iostream>
#include <random>

#include <SFML/Window.hpp>
#include <SFML/Graphics.hpp>

#include <headless-logic/searchtree.hpp>
#include "../common.hpp"

int loadTexture(sf::Texture &texture, std::string path) {
    if(!texture.loadFromFile(path)) {
        std::cerr << "Can't load texture '"
            << path << "' !" << std::endl;
        return 0;
    }
    texture.setSmooth(true);
    return 1;
}

class DisplayerVisitor {
    private:
        sf::Sprite *_sprite;
        sf::RenderWindow *_window;
    public:
        DisplayerVisitor() : _sprite(nullptr), _window(nullptr) {}
        void set(sf::Sprite *sprite, sf::RenderWindow *window) {
            _sprite = sprite;
            _window = window;
        }
        void init() {}
        void enter(const Region& region) {
            glm::vec4 boundary = region.boundary();
#ifdef DISPLAY_CENTER
            _sprite->setPosition(boundary.x + (boundary.p / 2.0),
                    boundary.y + (boundary.q / 2.0));
            _window->draw(*_sprite);
#else
            _sprite->setPosition(boundary.x, boundary.y);
            _window->draw(*_sprite);
            _sprite->setPosition(boundary.x + boundary.p, boundary.y);
            _window->draw(*_sprite);
            _sprite->setPosition(boundary.x + boundary.p, boundary.y + boundary.q);
            _window->draw(*_sprite);
            _sprite->setPosition(boundary.x, boundary.y + boundary.q);
            _window->draw(*_sprite);
#endif
        }
        void exit(const Region&) {}
        void inspect(Element **, unsigned int count) {
            if(count == 0) {
               // std::cout << "Empty leaf !" << std::endl;
            }
            if(count > 3) {
                std::cout << "Node Overflow !" << std::endl;
            }
        }
};

#define AGENT_COUNT 256

/**
 * Main procedure.
 */
int main(void) {
    sf::Vector2f textureOffset(32, 32);

    sf::Texture agentTexture;
    if(!loadTexture(agentTexture, "resources/agent.png")) { return -1; }

    sf::Texture boundaryTexture;
    if(!loadTexture(boundaryTexture, "resources/cross.png")) { return -1; }

    sf::Sprite sprite;

    sf::RenderWindow window(sf::VideoMode(1024, 1024), "Crowd Control",
            sf::Style::Titlebar | sf::Style::Close);
    window.setFramerateLimit(60);

    DisplayerVisitor visitor;
    visitor.set(&sprite, &window);

    Region region(glm::vec4(0.0, 0.0, 1024.0, 1024.0));
    Headless::Logic::SearchTree::Node<glm::vec2, Region, Element> tree(&region, 3);

    Element **pool = new Element*[AGENT_COUNT];
    std::random_device randomDevice;
    std::mt19937 mt(randomDevice());
    std::uniform_real_distribution<double> posDist(0.0, 1024.0);
    std::uniform_real_distribution<double> velDist(-128.0, 128.0);

    for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
        pool[i] = new Element(glm::vec2(posDist(mt), posDist(mt)),
                std::string("Agent#").append(std::to_string(i)));
        pool[i]->velocity(glm::vec2(velDist(mt), velDist(mt)));
        tree.add(pool[i]);
    }

    sf::Clock clock;
    sf::Time elapsed;
    glm::vec2 target;
    glm::vec2 velocity;

    while (window.isOpen()) {
        // Logic update
        elapsed = clock.restart();
        float sec = elapsed.asSeconds();

        for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
            target = pool[i]->key();
            velocity = pool[i]->velocity();
            target.x += velocity.x * sec;
            target.y += velocity.y * sec;
            if(target.x < 0 || target.y < 0 || target.x > 1024.0 || target.y > 1024.0) {
                target.x = posDist(mt);
                target.y = posDist(mt);
                velocity.x = velDist(mt);
                velocity.y = velDist(mt);
                pool[i]->velocity(velocity);
            }
            tree.move(pool[i], target);
        }

        // Event handling.
        sf::Event event;
        while (window.pollEvent(event)) {
            if (event.type == sf::Event::Closed) {
                window.close();
            }
        }

        // Draw
        window.clear(sf::Color::Black);

        sf::Vector2i localPosition = sf::Mouse::getPosition(window);

        sprite.setTexture(agentTexture);
        sprite.setOrigin(textureOffset);
        sprite.setColor(sf::Color(0, 255, 0));
        sprite.setPosition(localPosition.x, localPosition.y);
        sprite.setScale(sf::Vector2f(.5f, .5f));
        window.draw(sprite);

        sprite.setColor(sf::Color(0, 128, 255));
        for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
            glm::vec2 pos = pool[i]->key();
            sprite.setPosition(pos.x, pos.y);
            window.draw(sprite);
        }

        sprite.setColor(sf::Color(255, 255, 255, 32));
        sprite.setTexture(boundaryTexture);
        tree.visit(visitor);

        window.display();

    }

    // Clean exit.
    return 0;
}
<commit_msg>Added crowd-ish behaviour. In fact, it is just a search result with mean vector.<commit_after>/*
 * Copyright 2016 Stoned Xander
 *
 * 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.
 */

/*
 * This example is not meant to simulate flocking, but only "almost"
 * straight line going agents and how it affects the search tree.
 */
#include <iostream>
#include <random>

#include <SFML/Window.hpp>
#include <SFML/Graphics.hpp>

#include <headless-logic/searchtree.hpp>
#include "../common.hpp"

int loadTexture(sf::Texture &texture, std::string path) {
    if(!texture.loadFromFile(path)) {
        std::cerr << "Can't load texture '"
            << path << "' !" << std::endl;
        return 0;
    }
    texture.setSmooth(true);
    return 1;
}

class DisplayerVisitor {
    private:
        sf::Sprite *_sprite;
        sf::RenderWindow *_window;
    public:
        DisplayerVisitor() : _sprite(nullptr), _window(nullptr) {}
        void set(sf::Sprite *sprite, sf::RenderWindow *window) {
            _sprite = sprite;
            _window = window;
        }
        void init() {}
        void enter(const Region& region) {
            glm::vec4 boundary = region.boundary();
#ifdef DISPLAY_CENTER
            _sprite->setPosition(boundary.x + (boundary.p / 2.0),
                    boundary.y + (boundary.q / 2.0));
            _window->draw(*_sprite);
#else
            _sprite->setPosition(boundary.x, boundary.y);
            _window->draw(*_sprite);
            _sprite->setPosition(boundary.x + boundary.p, boundary.y);
            _window->draw(*_sprite);
            _sprite->setPosition(boundary.x + boundary.p, boundary.y + boundary.q);
            _window->draw(*_sprite);
            _sprite->setPosition(boundary.x, boundary.y + boundary.q);
            _window->draw(*_sprite);
#endif
        }
        void exit(const Region&) {}
        void inspect(Element **, unsigned int count) {
            if(count == 0) {
               // std::cout << "Empty leaf !" << std::endl;
            }
            if(count > 3) {
                std::cout << "Node Overflow !" << std::endl;
            }
        }
};

#define AGENT_COUNT 256

/**
 * Main procedure.
 */
int main(void) {
    sf::Vector2f textureOffset(32, 32);

    sf::Texture agentTexture;
    if(!loadTexture(agentTexture, "resources/agent.png")) { return -1; }

    sf::Texture boundaryTexture;
    if(!loadTexture(boundaryTexture, "resources/cross.png")) { return -1; }

    sf::Sprite sprite;

    sf::RenderWindow window(sf::VideoMode(1024, 1024), "Crowd Control",
            sf::Style::Titlebar | sf::Style::Close);
    window.setFramerateLimit(60);

    DisplayerVisitor visitor;
    visitor.set(&sprite, &window);

    Region region(glm::vec4(0.0, 0.0, 1024.0, 1024.0));
    Headless::Logic::SearchTree::Node<glm::vec2, Region, Element> tree(&region, 3);

    Element **pool = new Element*[AGENT_COUNT];
    Element **searchResult = new Element*[AGENT_COUNT];
    std::random_device randomDevice;
    std::mt19937 mt(randomDevice());
    std::uniform_real_distribution<double> posDist(0.0, 1024.0);
    std::uniform_real_distribution<double> velDist(-128.0, 128.0);

    for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
        pool[i] = new Element(glm::vec2(posDist(mt), posDist(mt)),
                std::string("Agent#").append(std::to_string(i)));
        pool[i]->velocity(glm::vec2(velDist(mt), velDist(mt)));
        tree.add(pool[i]);
    }

    sf::Clock clock;
    sf::Time elapsed;
    glm::vec2 target;
    glm::vec2 velocity;

    Disc searchDisc;

    while (window.isOpen()) {
        // Logic update
        elapsed = clock.restart();
        float sec = elapsed.asSeconds();

        for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
            target = pool[i]->key();
            velocity = pool[i]->velocity();
            target.x += velocity.x * sec;
            target.y += velocity.y * sec;
            if(target.x < 0 || target.y < 0 || target.x > 1024.0 || target.y > 1024.0) {
                target.x = posDist(mt);
                target.y = posDist(mt);
                velocity.x = velDist(mt);
                velocity.y = velDist(mt);
                pool[i]->velocity(velocity);
            }
            tree.move(pool[i], target);

            // Search neighbor and take mean velocity.
            searchDisc.set(target, 32.0);
            unsigned int count = tree.retrieve(searchDisc, searchResult, AGENT_COUNT);
            glm::vec2 meanVelocity(0.0, 0.0);
            for(unsigned int j = 0; j < count; ++j) {
                meanVelocity += searchResult[j]->velocity();
            }
            if(count > 0) {
                meanVelocity.x /= (double) count;
                meanVelocity.y /= (double) count;
                pool[i]->velocity(meanVelocity);
            }
        }

        // Event handling.
        sf::Event event;
        while (window.pollEvent(event)) {
            if (event.type == sf::Event::Closed) {
                window.close();
            }
        }

        // Draw
        window.clear(sf::Color::Black);

        sf::Vector2i localPosition = sf::Mouse::getPosition(window);

        sprite.setTexture(agentTexture);
        sprite.setOrigin(textureOffset);
        sprite.setColor(sf::Color(0, 255, 0));
        sprite.setPosition(localPosition.x, localPosition.y);
        sprite.setScale(sf::Vector2f(.5f, .5f));
        window.draw(sprite);

        sprite.setColor(sf::Color(0, 128, 255));
        for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
            glm::vec2 pos = pool[i]->key();
            sprite.setPosition(pos.x, pos.y);
            window.draw(sprite);
        }

        sprite.setColor(sf::Color(255, 255, 255, 32));
        sprite.setTexture(boundaryTexture);
        tree.visit(visitor);

        window.display();

    }

    // Clean Exit.
    for(unsigned int i = 0; i < AGENT_COUNT; ++i) {
        delete pool[i];
    }
    delete []pool;
    delete []searchResult;
    return 0;
}
<|endoftext|>


<commit_before>/*
 * Copyright (C) 2008, 2009 Nokia Corporation.
 *
 * Contact: Marius Vollmer <marius.vollmer@nokia.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public License
 * version 2.1 as published by the Free Software Foundation.
 *
 * This library is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
 * 02110-1301 USA
 *
 */

#include <QtTest/QtTest>
#include <QtCore>
#include <stdlib.h>
#include "context.h"
#include "contextc.h"
#include "contextgroup.h"

QList<Context*> contextList;
QList<ContextGroup*> contextGroupList;

QString *lastBusName = NULL;
QStringList *lastKeysList = NULL;
QDBusConnection::BusType lastConnectionType;
QVariant *lastVariantSet = NULL;
int lastSubscribed = 0;
void *lastUserData = NULL;

/* Mocked implementation of ContextGroup */

ContextGroup::ContextGroup(QStringList propertiesToWatch, QObject *parent) : keyList(propertiesToWatch)
{
    contextGroupList.append(this);
}

ContextGroup::~ContextGroup()
{
    contextGroupList.removeAll(this);
}

void ContextGroup::fakeFirst()
{
    emit firstSubscriberAppeared();
}

void ContextGroup::fakeLast()
{
    emit lastSubscriberDisappeared();
}

/* Mocked implementation of Context */

void resetVariants()
{
    delete lastVariantSet;
    lastVariantSet = NULL;
}

void emitFirstOn(const QString &k)
{
    foreach (Context* c, contextList) {
        if (c->getKey() == k)
            c->fakeFirst();
    }

    foreach (ContextGroup* cg, contextGroupList) {
        if (cg->keyList.contains(k))
            cg->fakeFirst();
    }
}

void emitLastOn(const QString &k)
{
    foreach (Context* c, contextList) {
        if (c->getKey() == k)
            c->fakeLast();
    }

    foreach (ContextGroup* cg, contextGroupList) {
        if (cg->keyList.contains(k))
            cg->fakeLast();
    }
}

bool Context::initService(QDBusConnection::BusType busType, const QString &busName, const QStringList &keys)
{
    if (lastBusName && lastBusName == busName)
        return false;

    delete lastBusName;
    lastBusName = new QString(busName);

    delete lastKeysList;
    lastKeysList = new QStringList(keys);

    lastConnectionType = busType;
    return true;
}

void Context::stopService(const QString &name)
{
    if (lastBusName && name == lastBusName) {
        delete lastBusName;
        lastBusName = NULL;
        delete lastKeysList;
        lastKeysList = NULL;
    }
}

void Context::set(const QVariant &v)
{
    delete lastVariantSet;
    lastVariantSet = new QVariant(v);
}

void Context::unset()
{
    delete lastVariantSet;
    lastVariantSet = NULL;
}

Context::Context(const QString &name, QObject *obj) : QObject(obj), key(name)
{
    delete lastVariantSet;
    lastVariantSet = NULL;
    contextList.append(this);
}

Context::~Context()
{
    contextList.removeAll(this);
}

QString Context::getKey()
{
    return key;
}

void Context::fakeFirst()
{
    emit firstSubscriberAppeared(key);
}

void Context::fakeLast()
{
    emit lastSubscriberDisappeared(key);
}

class ContextCUnitTest : public QObject
{
    Q_OBJECT

private slots:
    void init();
    void startStopStart();
    void installKey();
    void installGroup();
    /*
    void isValid();
    void isSet();
    void unset();
    void getKey();
    void setGetInt();
    void setGetBool();
    void setGetString();
    void setGetDouble();
    */

};

void MagicCallback(int subscribed, void *user_data)
{
    lastSubscribed = subscribed;
    lastUserData = user_data;
}

// Before each test
void ContextCUnitTest::init()
{
    context_provider_stop();
    int res = context_provider_init(DBUS_BUS_SESSION, "com.test.provider");
    QCOMPARE(res, 1);
    QCOMPARE(*lastBusName, QString("com.test.provider"));
    QCOMPARE(lastKeysList->size(), 0);
    QCOMPARE(lastConnectionType, QDBusConnection::SessionBus);
}

void ContextCUnitTest::startStopStart()
{
    context_provider_stop();
    QCOMPARE(context_provider_init(DBUS_BUS_SESSION, "com.test.provider"), 1);
    QCOMPARE(context_provider_init(DBUS_BUS_SESSION, "com.test.provider"), 0);
    context_provider_stop();
    QCOMPARE(context_provider_init(DBUS_BUS_SESSION, "com.test.provider"), 1);
}

void ContextCUnitTest::installKey()
{
    context_provider_install_key("Battery.OnBattery", 0, MagicCallback, this);
    context_provider_install_key("Battery.Power", 0, MagicCallback, this);
    QVERIFY(lastKeysList->contains("Battery.OnBattery"));
    QVERIFY(lastKeysList->contains("Battery.Power"));
    QCOMPARE(lastKeysList->length(), 2);

    emitFirstOn("Battery.OnBattery");
    QCOMPARE(lastSubscribed, 1);
    QCOMPARE(lastUserData, this);

    emitLastOn("Battery.Power");
    QCOMPARE(lastSubscribed, 0);
    QCOMPARE(lastUserData, this);

    emitFirstOn("Battery.Something");
    QCOMPARE(lastSubscribed, 0);
    QCOMPARE(lastUserData, this);
}

void ContextCUnitTest::installGroup()
{
    const char *keys[3];
    keys[0] = "Location.Lat";
    keys[1] = "Location.Lon";
    keys[2] = NULL;

    context_provider_install_group(keys, 0, MagicCallback, this);
    QVERIFY(lastKeysList->contains("Location.Lat"));
    QVERIFY(lastKeysList->contains("Location.Lon"));
    QCOMPARE(lastKeysList->length(), 2);

    emitFirstOn("Location.Lat");
    QCOMPARE(lastSubscribed, 1);
    QCOMPARE(lastUserData, this);

    emitLastOn("Location.Lat");
    QCOMPARE(lastSubscribed, 0);
    QCOMPARE(lastUserData, this);
}

/*
void ContextCUnitTest::isValid({
    ContextPtr *c1 = context_new("Battery.OnBattery");
    QCOMPARE(context_is_valid(c1), 1);
    context_free(c1);

    ContextPtr *c2 = context_new("Battery.SomethingWeird");
    QCOMPARE(context_is_valid(c2), 0);
    context_free(c2);
}

void ContextCUnitTest::isSet()
{
    resetVariants();
    ContextPtr *c = context_new("Battery.OnBattery");
    QCOMPARE(context_is_set(c), 0);
    context_set_int(c, 999);
    QCOMPARE(context_is_set(c), 1);
    context_free(c);
}

void ContextCUnitTest::unset()
{
    resetVariants();
    ContextPtr *c = context_new("Battery.OnBattery");
    QCOMPARE(context_is_set(c), 0);
    context_set_int(c, 999);
    QCOMPARE(context_is_set(c), 1);
    context_unset(c);
    QCOMPARE(context_is_set(c), 0);
    context_free(c);
}

void ContextCUnitTest::getKey()
{
    ContextPtr *c = context_new("Battery.OnBattery");
    char *k = context_get_key(c);
    QVERIFY(strcmp(k, "Battery.OnBattery") == 0);
    context_free(c);
}

void ContextCUnitTest::setGetInt()
{
    int v;
    ContextPtr *c = context_new("Battery.OnBattery");
    QCOMPARE(context_get_int(c, &v), 0);
    QCOMPARE(v, 0);

    context_set_int(c, 666);
    QCOMPARE(*lastVariantSet, QVariant(666));

    QCOMPARE(context_get_int(c, &v), 1);
    QCOMPARE(v, 666);

    context_free(c);
}

void ContextCUnitTest::setGetDouble()
{
    double v;
    ContextPtr *c = context_new("Battery.OnBattery");
    QCOMPARE(context_get_double(c, &v), 0);
    QCOMPARE(v, 0.0);

    context_set_double(c, 0.666);
    QCOMPARE(*lastVariantSet, QVariant(0.666));

    QCOMPARE(context_get_double(c, &v), 1);
    QCOMPARE(v, 0.666);

    context_free(c);
}

void ContextCUnitTest::setGetString()
{
    char *v;
    ContextPtr *c = context_new("Battery.OnBattery");
    QCOMPARE(context_get_string(c, &v), 0);
    QVERIFY(v == NULL);

    context_set_string(c, "Hello!");
    QCOMPARE(*lastVariantSet, QVariant(QString("Hello!")));

    QCOMPARE(context_get_string(c, &v), 1);
    QVERIFY(v != NULL);
    QVERIFY(strcmp(v, "Hello!") == 0);

    free(v);
    context_free(c);
}

void ContextCUnitTest::setGetBool()
{
    int v;
    ContextPtr *c = context_new("Battery.OnBattery");
    QCOMPARE(context_get_bool(c, &v), 0);
    QCOMPARE(v, 0);

    context_set_bool(c, 1);
    QCOMPARE(*lastVariantSet, QVariant(true));

    QCOMPARE(context_get_bool(c, &v), 1);
    QCOMPARE(v, 1);

    context_free(c);
}
*/

#include "contextcunittest.moc"
QTEST_MAIN(ContextCUnitTest);
<commit_msg>Cleanups.<commit_after>/*
 * Copyright (C) 2008, 2009 Nokia Corporation.
 *
 * Contact: Marius Vollmer <marius.vollmer@nokia.com>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public License
 * version 2.1 as published by the Free Software Foundation.
 *
 * This library is distributed in the hope that it will be useful, but
 * WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
 * 02110-1301 USA
 *
 */

#include <QtTest/QtTest>
#include <QtCore>
#include <stdlib.h>
#include "context.h"
#include "contextc.h"
#include "contextgroup.h"

QList<Context*> contextList;
QList<ContextGroup*> contextGroupList;

QString *lastBusName = NULL;
QStringList *lastKeysList = NULL;
QDBusConnection::BusType lastConnectionType;
QVariant *lastVariantSet = NULL;
int lastSubscribed = 0;
void *lastUserData = NULL;

/* Mocked implementation of ContextGroup */

ContextGroup::ContextGroup(QStringList propertiesToWatch, QObject *parent) : keyList(propertiesToWatch)
{
    contextGroupList.append(this);
}

ContextGroup::~ContextGroup()
{
    contextGroupList.removeAll(this);
}

void ContextGroup::fakeFirst()
{
    emit firstSubscriberAppeared();
}

void ContextGroup::fakeLast()
{
    emit lastSubscriberDisappeared();
}

/* Mocked implementation of Context */

void resetVariants()
{
    delete lastVariantSet;
    lastVariantSet = NULL;
}

void emitFirstOn(const QString &k)
{
    foreach (Context* c, contextList) {
        if (c->getKey() == k)
            c->fakeFirst();
    }

    foreach (ContextGroup* cg, contextGroupList) {
        if (cg->keyList.contains(k))
            cg->fakeFirst();
    }
}

void emitLastOn(const QString &k)
{
    foreach (Context* c, contextList) {
        if (c->getKey() == k)
            c->fakeLast();
    }

    foreach (ContextGroup* cg, contextGroupList) {
        if (cg->keyList.contains(k))
            cg->fakeLast();
    }
}

bool Context::initService(QDBusConnection::BusType busType, const QString &busName, const QStringList &keys)
{
    if (lastBusName && lastBusName == busName)
        return false;

    delete lastBusName;
    lastBusName = new QString(busName);

    delete lastKeysList;
    lastKeysList = new QStringList(keys);

    lastConnectionType = busType;
    return true;
}

void Context::stopService(const QString &name)
{
    if (lastBusName && name == lastBusName) {
        delete lastBusName;
        lastBusName = NULL;
        delete lastKeysList;
        lastKeysList = NULL;
    }
}

void Context::set(const QVariant &v)
{
    delete lastVariantSet;
    lastVariantSet = new QVariant(v);
}

void Context::unset()
{
    delete lastVariantSet;
    lastVariantSet = NULL;
}

Context::Context(const QString &name, QObject *obj) : QObject(obj), key(name)
{
    delete lastVariantSet;
    lastVariantSet = NULL;
    contextList.append(this);
}

Context::~Context()
{
    contextList.removeAll(this);
}

QString Context::getKey()
{
    return key;
}

void Context::fakeFirst()
{
    emit firstSubscriberAppeared(key);
}

void Context::fakeLast()
{
    emit lastSubscriberDisappeared(key);
}

class ContextCUnitTest : public QObject
{
    Q_OBJECT

private slots:
    void init();
    void startStopStart();
    void installKey();
    void installGroup();
};

void MagicCallback(int subscribed, void *user_data)
{
    lastSubscribed = subscribed;
    lastUserData = user_data;
}

// Before each test
void ContextCUnitTest::init()
{
    context_provider_stop();
    int res = context_provider_init(DBUS_BUS_SESSION, "com.test.provider");
    QCOMPARE(res, 1);
    QCOMPARE(*lastBusName, QString("com.test.provider"));
    QCOMPARE(lastKeysList->size(), 0);
    QCOMPARE(lastConnectionType, QDBusConnection::SessionBus);
}

void ContextCUnitTest::startStopStart()
{
    context_provider_stop();
    QCOMPARE(context_provider_init(DBUS_BUS_SESSION, "com.test.provider"), 1);
    QCOMPARE(context_provider_init(DBUS_BUS_SESSION, "com.test.provider"), 0);
    context_provider_stop();
    QCOMPARE(context_provider_init(DBUS_BUS_SESSION, "com.test.provider"), 1);
}

void ContextCUnitTest::installKey()
{
    context_provider_install_key("Battery.OnBattery", 0, MagicCallback, this);
    context_provider_install_key("Battery.Power", 0, MagicCallback, this);
    QVERIFY(lastKeysList->contains("Battery.OnBattery"));
    QVERIFY(lastKeysList->contains("Battery.Power"));
    QCOMPARE(lastKeysList->length(), 2);

    emitFirstOn("Battery.OnBattery");
    QCOMPARE(lastSubscribed, 1);
    QCOMPARE(lastUserData, this);

    emitLastOn("Battery.Power");
    QCOMPARE(lastSubscribed, 0);
    QCOMPARE(lastUserData, this);

    emitFirstOn("Battery.Something");
    QCOMPARE(lastSubscribed, 0);
    QCOMPARE(lastUserData, this);
}

void ContextCUnitTest::installGroup()
{
    const char *keys[3];
    keys[0] = "Location.Lat";
    keys[1] = "Location.Lon";
    keys[2] = NULL;

    context_provider_install_group(keys, 0, MagicCallback, this);
    QVERIFY(lastKeysList->contains("Location.Lat"));
    QVERIFY(lastKeysList->contains("Location.Lon"));
    QCOMPARE(lastKeysList->length(), 2);

    emitFirstOn("Location.Lat");
    QCOMPARE(lastSubscribed, 1);
    QCOMPARE(lastUserData, this);

    emitLastOn("Location.Lat");
    QCOMPARE(lastSubscribed, 0);
    QCOMPARE(lastUserData, this);
}

#include "contextcunittest.moc"
QTEST_MAIN(ContextCUnitTest);
<|endoftext|>