<commit_before>/***
 * @file core.hpp
 *
 * Include all of the base components required to write MLPACK methods, and the
 * main MLPACK Doxygen documentation.
 */
#ifndef __MLPACK_CORE_HPP
#define __MLPACK_CORE_HPP

/**
 * @mainpage MLPACK Documentation
 *
 * @section intro_sec Introduction
 *
 * MLPACK is an intuitive, fast, scalable C++ machine learning library, meant to
 * be a machine learning analog to LAPACK.  It aims to implement a wide array of
 * machine learning methods and function as a "swiss army knife" for machine
 * learning researchers.  The MLPACK development website can be found at
 * http://mlpack.org.
 *
 * MLPACK uses the Armadillo C++ matrix library (http://arma.sourceforge.net)
 * for general matrix, vector, and linear algebra support.  MLPACK also uses the
 * program_options, math_c99, and unit_test_framework components of the Boost
 * library; in addition, LibXml2 is used.
 *
 * @section howto How To Use This Documentation
 *
 * This documentation is API documentation similar to Javadoc.  It isn't
 * necessarily a tutorial, but it does provide detailed documentation on every
 * namespace, method, and class.
 *
 * Each MLPACK namespace generally refers to one machine learning method, so
 * browsing the list of namespaces provides some insight as to the breadth of
 * the methods contained in the library.
 *
 * To generate this documentation in your own local copy of MLPACK, you can
 * simply use Doxygen, from the root directory (@c /mlpack/trunk/ ):
 *
 * @code
 * $ doxygen
 * @endcode
 *
 * @section executables Executables
 *
 * MLPACK provides several executables so that MLPACK methods can be used
 * without any need for knowledge of C++.  These executables are all
 * self-documented, and that documentation can be accessed by running the
 * executables with the '-h' or '--help' flag.
 *
 * A full list of executables is given below:
 *
 * allkfn, allknn, emst, gmm, hmm_train, hmm_loglik, hmm_viterbi, hmm_generate,
 * kernel_pca, kmeans, lars, linear_regression, local_coordinate_coding, mvu,
 * nbc, nca, pca, radical, sparse_coding
 *
 * @section tutorial Tutorials
 *
 * A few short tutorials on how to use MLPACK are given below.
 *
 *  - @ref build
 *  - @ref matrices
 *  - @ref iodoc
 *  - @ref timer
 *  - @ref sample
 *  - @ref verinfo
 *
 * Tutorials on specific methods are also available.
 *
 *  - @ref nstutorial
 *  - @ref lrtutorial
 *  - @ref rstutorial
 *  - @ref dettutorial
 *  - @ref emst_tutorial
 *  - @ref kmtutorial
 *  - @ref fmkstutorial
 *  - @ref amftutorial
 *
 * @section methods Methods in MLPACK
 *
 * The following methods are included in MLPACK:
 *
 *  - Density Estimation Trees - mlpack::det::DTree
 *  - Euclidean Minimum Spanning Trees - mlpack::emst::DualTreeBoruvka
 *  - Gaussian Mixture Models (GMMs) - mlpack::gmm::GMM
 *  - Hidden Markov Models (HMMs) - mlpack::hmm::HMM
 *  - Kernel PCA - mlpack::kpca::KernelPCA
 *  - K-Means Clustering - mlpack::kmeans::KMeans
 *  - Least-Angle Regression (LARS/LASSO) - mlpack::regression::LARS
 *  - Local Coordinate Coding - mlpack::lcc::LocalCoordinateCoding
 *  - Locality-Sensitive Hashing - mlpack::neighbor::LSHSearch
 *  - Naive Bayes Classifier - mlpack::naive_bayes::NaiveBayesClassifier
 *  - Neighborhood Components Analysis (NCA) - mlpack::nca::NCA
 *  - Principal Components Analysis (PCA) - mlpack::pca::PCA
 *  - RADICAL (ICA) - mlpack::radical::Radical
 *  - Simple Least-Squares Linear Regression -
 *        mlpack::regression::LinearRegression
 *  - Sparse Coding - mlpack::sparse_coding::SparseCoding
 *  - Tree-based neighbor search (AllkNN, AllkFN) -
 *        mlpack::neighbor::NeighborSearch
 *  - Tree-based range search - mlpack::range::RangeSearch
 *
 * @section remarks Final Remarks
 *
 * MLPACK contributors include:
 *
 *   - Ryan Curtin <gth671b@mail.gatech.edu>
 *   - James Cline <james.cline@gatech.edu>
 *   - Neil Slagle <nslagle3@gatech.edu>
 *   - Matthew Amidon <mamidon@gatech.edu>
 *   - Vlad Grantcharov <vlad321@gatech.edu>
 *   - Ajinkya Kale <kaleajinkya@gmail.com>
 *   - Bill March <march@gatech.edu>
 *   - Dongryeol Lee <dongryel@cc.gatech.edu>
 *   - Nishant Mehta <niche@cc.gatech.edu>
 *   - Parikshit Ram <p.ram@gatech.edu>
 *   - Rajendran Mohan <rmohan88@gatech.edu>
 *   - Trironk Kiatkungwanglai <trironk@gmail.com>
 *   - Patrick Mason <patrick.s.mason@gmail.com>
 *   - Chip Mappus <cmappus@gatech.edu>
 *   - Hua Ouyang <houyang@gatech.edu>
 *   - Long Quoc Tran <tqlong@gmail.com>
 *   - Noah Kauffman <notoriousnoah@gmail.com>
 *   - Guillermo Colon <gcolon7@mail.gatech.edu>
 *   - Wei Guan <wguan@cc.gatech.edu>
 *   - Ryan Riegel <rriegel@cc.gatech.edu>
 *   - Nikolaos Vasiloglou <nvasil@ieee.org>
 *   - Garry Boyer <garryb@gmail.com>
 *   - Andreas Löf <andreas.lof@cs.waikato.ac.nz>
 *   - Marcus Edel <marcus.edel@fu-berlin.de>
 *   - Mudit Raj Gupta <mudit.raaj.gupta@gmail.com>
 *   - Sumedh Ghaisas <sumedhghaisas@gmail.com>
 *   - Michael Fox <michaelfox99@gmail.com>
 *   - Ryan Birmingham <birm@gatech.edu>
 *   - Siddharth Agrawal <siddharth.950@gmail.com>
 *   - Saheb Motiani <saheb210692@gmail.com>
 *   - Yash Vadalia <yashdv@gmail.com>
 *   - Abhishek Laddha <laddhaabhishek11@gmail.com>
 *   - Vahab Akbarzadeh <v.akbarzadeh@gmail.com>
 *   - Andrew Wells <andrewmw94@gmail.com>
 *   - Zhihao Lou <lzh1984@gmail.com>
 *   - Udit Saxena <saxena.udit@gmail.com>
 */

// First, include all of the prerequisites.
#include <mlpack/prereqs.hpp>

// Now the core mlpack classes.
#include <mlpack/core/util/arma_traits.hpp>
#include <mlpack/core/util/log.hpp>
#include <mlpack/core/util/cli.hpp>
#include <mlpack/core/util/ostream_extra.hpp>
#include <mlpack/core/data/load.hpp>
#include <mlpack/core/data/save.hpp>
#include <mlpack/core/data/normalize_labels.hpp>
#include <mlpack/core/math/clamp.hpp>
#include <mlpack/core/math/random.hpp>
#include <mlpack/core/math/lin_alg.hpp>
#include <mlpack/core/math/range.hpp>
#include <mlpack/core/math/round.hpp>
#include <mlpack/core/util/save_restore_utility.hpp>
#include <mlpack/core/dists/discrete_distribution.hpp>
#include <mlpack/core/dists/gaussian_distribution.hpp>
#include <mlpack/core/dists/laplace_distribution.hpp>

// Include kernel traits.
#include <mlpack/core/kernels/kernel_traits.hpp>
#include <mlpack/core/kernels/linear_kernel.hpp>
#include <mlpack/core/kernels/polynomial_kernel.hpp>
#include <mlpack/core/kernels/cosine_distance.hpp>
#include <mlpack/core/kernels/gaussian_kernel.hpp>
#include <mlpack/core/kernels/epanechnikov_kernel.hpp>
#include <mlpack/core/kernels/hyperbolic_tangent_kernel.hpp>
#include <mlpack/core/kernels/laplacian_kernel.hpp>
#include <mlpack/core/kernels/pspectrum_string_kernel.hpp>
#include <mlpack/core/kernels/spherical_kernel.hpp>
#include <mlpack/core/kernels/triangular_kernel.hpp>

// Use armadillo's C++ version detection
#ifdef ARMA_USE_CXX11
  #define MLPACK_USE_CX11
#endif

#endif

// Clean up unfortunate Windows preprocessor definitions, even if this file was
// already included.  Use std::min and std::max!
#ifdef _WIN32
  #ifdef min
    #undef min
  #endif

  #ifdef max
    #undef max
  #endif
#endif
<commit_msg>Disable C4519 errors entirely.<commit_after>/***
 * @file core.hpp
 *
 * Include all of the base components required to write MLPACK methods, and the
 * main MLPACK Doxygen documentation.
 */
#ifndef __MLPACK_CORE_HPP
#define __MLPACK_CORE_HPP

/**
 * @mainpage MLPACK Documentation
 *
 * @section intro_sec Introduction
 *
 * MLPACK is an intuitive, fast, scalable C++ machine learning library, meant to
 * be a machine learning analog to LAPACK.  It aims to implement a wide array of
 * machine learning methods and function as a "swiss army knife" for machine
 * learning researchers.  The MLPACK development website can be found at
 * http://mlpack.org.
 *
 * MLPACK uses the Armadillo C++ matrix library (http://arma.sourceforge.net)
 * for general matrix, vector, and linear algebra support.  MLPACK also uses the
 * program_options, math_c99, and unit_test_framework components of the Boost
 * library; in addition, LibXml2 is used.
 *
 * @section howto How To Use This Documentation
 *
 * This documentation is API documentation similar to Javadoc.  It isn't
 * necessarily a tutorial, but it does provide detailed documentation on every
 * namespace, method, and class.
 *
 * Each MLPACK namespace generally refers to one machine learning method, so
 * browsing the list of namespaces provides some insight as to the breadth of
 * the methods contained in the library.
 *
 * To generate this documentation in your own local copy of MLPACK, you can
 * simply use Doxygen, from the root directory (@c /mlpack/trunk/ ):
 *
 * @code
 * $ doxygen
 * @endcode
 *
 * @section executables Executables
 *
 * MLPACK provides several executables so that MLPACK methods can be used
 * without any need for knowledge of C++.  These executables are all
 * self-documented, and that documentation can be accessed by running the
 * executables with the '-h' or '--help' flag.
 *
 * A full list of executables is given below:
 *
 * allkfn, allknn, emst, gmm, hmm_train, hmm_loglik, hmm_viterbi, hmm_generate,
 * kernel_pca, kmeans, lars, linear_regression, local_coordinate_coding, mvu,
 * nbc, nca, pca, radical, sparse_coding
 *
 * @section tutorial Tutorials
 *
 * A few short tutorials on how to use MLPACK are given below.
 *
 *  - @ref build
 *  - @ref matrices
 *  - @ref iodoc
 *  - @ref timer
 *  - @ref sample
 *  - @ref verinfo
 *
 * Tutorials on specific methods are also available.
 *
 *  - @ref nstutorial
 *  - @ref lrtutorial
 *  - @ref rstutorial
 *  - @ref dettutorial
 *  - @ref emst_tutorial
 *  - @ref kmtutorial
 *  - @ref fmkstutorial
 *  - @ref amftutorial
 *
 * @section methods Methods in MLPACK
 *
 * The following methods are included in MLPACK:
 *
 *  - Density Estimation Trees - mlpack::det::DTree
 *  - Euclidean Minimum Spanning Trees - mlpack::emst::DualTreeBoruvka
 *  - Gaussian Mixture Models (GMMs) - mlpack::gmm::GMM
 *  - Hidden Markov Models (HMMs) - mlpack::hmm::HMM
 *  - Kernel PCA - mlpack::kpca::KernelPCA
 *  - K-Means Clustering - mlpack::kmeans::KMeans
 *  - Least-Angle Regression (LARS/LASSO) - mlpack::regression::LARS
 *  - Local Coordinate Coding - mlpack::lcc::LocalCoordinateCoding
 *  - Locality-Sensitive Hashing - mlpack::neighbor::LSHSearch
 *  - Naive Bayes Classifier - mlpack::naive_bayes::NaiveBayesClassifier
 *  - Neighborhood Components Analysis (NCA) - mlpack::nca::NCA
 *  - Principal Components Analysis (PCA) - mlpack::pca::PCA
 *  - RADICAL (ICA) - mlpack::radical::Radical
 *  - Simple Least-Squares Linear Regression -
 *        mlpack::regression::LinearRegression
 *  - Sparse Coding - mlpack::sparse_coding::SparseCoding
 *  - Tree-based neighbor search (AllkNN, AllkFN) -
 *        mlpack::neighbor::NeighborSearch
 *  - Tree-based range search - mlpack::range::RangeSearch
 *
 * @section remarks Final Remarks
 *
 * MLPACK contributors include:
 *
 *   - Ryan Curtin <gth671b@mail.gatech.edu>
 *   - James Cline <james.cline@gatech.edu>
 *   - Neil Slagle <nslagle3@gatech.edu>
 *   - Matthew Amidon <mamidon@gatech.edu>
 *   - Vlad Grantcharov <vlad321@gatech.edu>
 *   - Ajinkya Kale <kaleajinkya@gmail.com>
 *   - Bill March <march@gatech.edu>
 *   - Dongryeol Lee <dongryel@cc.gatech.edu>
 *   - Nishant Mehta <niche@cc.gatech.edu>
 *   - Parikshit Ram <p.ram@gatech.edu>
 *   - Rajendran Mohan <rmohan88@gatech.edu>
 *   - Trironk Kiatkungwanglai <trironk@gmail.com>
 *   - Patrick Mason <patrick.s.mason@gmail.com>
 *   - Chip Mappus <cmappus@gatech.edu>
 *   - Hua Ouyang <houyang@gatech.edu>
 *   - Long Quoc Tran <tqlong@gmail.com>
 *   - Noah Kauffman <notoriousnoah@gmail.com>
 *   - Guillermo Colon <gcolon7@mail.gatech.edu>
 *   - Wei Guan <wguan@cc.gatech.edu>
 *   - Ryan Riegel <rriegel@cc.gatech.edu>
 *   - Nikolaos Vasiloglou <nvasil@ieee.org>
 *   - Garry Boyer <garryb@gmail.com>
 *   - Andreas Löf <andreas.lof@cs.waikato.ac.nz>
 *   - Marcus Edel <marcus.edel@fu-berlin.de>
 *   - Mudit Raj Gupta <mudit.raaj.gupta@gmail.com>
 *   - Sumedh Ghaisas <sumedhghaisas@gmail.com>
 *   - Michael Fox <michaelfox99@gmail.com>
 *   - Ryan Birmingham <birm@gatech.edu>
 *   - Siddharth Agrawal <siddharth.950@gmail.com>
 *   - Saheb Motiani <saheb210692@gmail.com>
 *   - Yash Vadalia <yashdv@gmail.com>
 *   - Abhishek Laddha <laddhaabhishek11@gmail.com>
 *   - Vahab Akbarzadeh <v.akbarzadeh@gmail.com>
 *   - Andrew Wells <andrewmw94@gmail.com>
 *   - Zhihao Lou <lzh1984@gmail.com>
 *   - Udit Saxena <saxena.udit@gmail.com>
 */

// First, include all of the prerequisites.
#include <mlpack/prereqs.hpp>

// Now the core mlpack classes.
#include <mlpack/core/util/arma_traits.hpp>
#include <mlpack/core/util/log.hpp>
#include <mlpack/core/util/cli.hpp>
#include <mlpack/core/util/ostream_extra.hpp>
#include <mlpack/core/data/load.hpp>
#include <mlpack/core/data/save.hpp>
#include <mlpack/core/data/normalize_labels.hpp>
#include <mlpack/core/math/clamp.hpp>
#include <mlpack/core/math/random.hpp>
#include <mlpack/core/math/lin_alg.hpp>
#include <mlpack/core/math/range.hpp>
#include <mlpack/core/math/round.hpp>
#include <mlpack/core/util/save_restore_utility.hpp>
#include <mlpack/core/dists/discrete_distribution.hpp>
#include <mlpack/core/dists/gaussian_distribution.hpp>
#include <mlpack/core/dists/laplace_distribution.hpp>

// Include kernel traits.
#include <mlpack/core/kernels/kernel_traits.hpp>
#include <mlpack/core/kernels/linear_kernel.hpp>
#include <mlpack/core/kernels/polynomial_kernel.hpp>
#include <mlpack/core/kernels/cosine_distance.hpp>
#include <mlpack/core/kernels/gaussian_kernel.hpp>
#include <mlpack/core/kernels/epanechnikov_kernel.hpp>
#include <mlpack/core/kernels/hyperbolic_tangent_kernel.hpp>
#include <mlpack/core/kernels/laplacian_kernel.hpp>
#include <mlpack/core/kernels/pspectrum_string_kernel.hpp>
#include <mlpack/core/kernels/spherical_kernel.hpp>
#include <mlpack/core/kernels/triangular_kernel.hpp>

// Use Armadillo's C++ version detection.
#ifdef ARMA_USE_CXX11
  #define MLPACK_USE_CX11
#endif

#endif

// Clean up unfortunate Windows preprocessor definitions, even if this file was
// already included.  Use std::min and std::max!
#ifdef _WIN32
  #ifdef min
    #undef min
  #endif

  #ifdef max
    #undef max
  #endif
#endif

// On Visual Studio, disable C4519 (default arguments for function templates)
// since it's by default an error, which doesn't even make any sense because
// it's part of the C++11 standard.
#ifdef _MSC_VER
  #pragma warning(disable : 4519)
#endif
<|endoftext|>


<commit_before>#include "BlobBinding.h"
#include "ClientRectBinding.h"
#include "ClientRectListBinding.h"
#include "DOMParserBinding.h"
#include "EventBinding.h"
#include "EventTargetBinding.h"
#include "FormDataBinding.h"
#include "HTMLCollectionBinding.h"
#include "nsScriptNameSpaceManager.h"

namespace mozilla {
namespace dom {
void
Register(nsScriptNameSpaceManager* aNameSpaceManager)
{

#define REGISTER_PROTO(_dom_class, _pref_check) \
  aNameSpaceManager->RegisterDefineDOMInterface(NS_LITERAL_STRING(#_dom_class), _dom_class##Binding::DefineDOMInterface, _pref_check);

REGISTER_PROTO(Blob, nullptr);
REGISTER_PROTO(ClientRect, nullptr);
REGISTER_PROTO(ClientRectList, nullptr);
REGISTER_PROTO(DOMParser, nullptr);
REGISTER_PROTO(Event, nullptr);
REGISTER_PROTO(EventTarget, nullptr);
REGISTER_PROTO(FormData, nullptr);
REGISTER_PROTO(HTMLCollection, nullptr);

#undef REGISTER_PROTO
}

} // namespace dom
} // namespace mozilla

<commit_msg>WebIDL codegen: Remove unneeded C++ goop.<commit_after><|endoftext|>


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

  Program:   Visualization Toolkit
  Module:    vtkExtractSelectedGraph.cxx

  Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
  All rights reserved.
  See Copyright.txt or http://www.kitware.com/Copyright.htm for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notice for more information.

=========================================================================*/
/*-------------------------------------------------------------------------
  Copyright 2008 Sandia Corporation.
  Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
  the U.S. Government retains certain rights in this software.
-------------------------------------------------------------------------*/

#include "vtkExtractSelectedGraph.h"

#include "vtkCellArray.h"
#include "vtkCellData.h"
#include "vtkCommand.h"
#include "vtkConvertSelection.h"
#include "vtkDataArray.h"
#include "vtkEdgeListIterator.h"
#include "vtkEventForwarderCommand.h"
#include "vtkExtractSelection.h"
#include "vtkGraph.h"
#include "vtkIdTypeArray.h"
#include "vtkInformation.h"
#include "vtkInformationVector.h"
#include "vtkMutableDirectedGraph.h"
#include "vtkMutableUndirectedGraph.h"
#include "vtkObjectFactory.h"
#include "vtkPointData.h"
#include "vtkPoints.h"
#include "vtkSelection.h"
#include "vtkSelectionNode.h"
#include "vtkSignedCharArray.h"
#include "vtkSmartPointer.h"
#include "vtkStringArray.h"
#include "vtkTree.h"
#include "vtkVertexListIterator.h"

#include <vtksys/stl/map>
#include <vtkstd/vector>

vtkCxxRevisionMacro(vtkExtractSelectedGraph, "1.30");
vtkStandardNewMacro(vtkExtractSelectedGraph);
//----------------------------------------------------------------------------
vtkExtractSelectedGraph::vtkExtractSelectedGraph()
{
  this->SetNumberOfInputPorts(2);
  this->RemoveIsolatedVertices = true;
}

//----------------------------------------------------------------------------
vtkExtractSelectedGraph::~vtkExtractSelectedGraph()
{
}

//----------------------------------------------------------------------------
int vtkExtractSelectedGraph::FillInputPortInformation(int port, vtkInformation* info)
{
  if (port == 0)
    {
    info->Set(vtkAlgorithm::INPUT_REQUIRED_DATA_TYPE(), "vtkGraph");
    return 1;
    }
  else if (port == 1)
    {
    info->Set(vtkAlgorithm::INPUT_REQUIRED_DATA_TYPE(), "vtkSelection");
    return 1;
    }
  return 0;
}

//----------------------------------------------------------------------------
void vtkExtractSelectedGraph::SetSelectionConnection(vtkAlgorithmOutput* in)
{
  this->SetInputConnection(1, in);
}

//----------------------------------------------------------------------------
int vtkExtractSelectedGraph::RequestDataObject(
  vtkInformation*,
  vtkInformationVector** inputVector ,
  vtkInformationVector* outputVector)
{
  vtkInformation* inInfo = inputVector[0]->GetInformationObject(0);
  if (!inInfo)
    {
    return 0;
    }
  vtkGraph *input = vtkGraph::SafeDownCast(
    inInfo->Get(vtkDataObject::DATA_OBJECT()));

  if (input)
    {
    vtkInformation* info = outputVector->GetInformationObject(0);
    vtkGraph *output = vtkGraph::SafeDownCast(
      info->Get(vtkDataObject::DATA_OBJECT()));

    // Output a vtkDirectedGraph if the input is a tree.
    if (!output
        || (vtkTree::SafeDownCast(input) && !vtkDirectedGraph::SafeDownCast(output))
        || (!vtkTree::SafeDownCast(input) && !output->IsA(input->GetClassName())))
      {
      if (vtkTree::SafeDownCast(input))
        {
        output = vtkDirectedGraph::New();
        }
      else
        {
        output = input->NewInstance();
        }
      output->SetPipelineInformation(info);
      output->Delete();
      this->GetOutputPortInformation(0)->Set(
        vtkDataObject::DATA_EXTENT_TYPE(), output->GetExtentType());
      }
    return 1;
    }
  return 0;
}

//----------------------------------------------------------------------------
int vtkExtractSelectedGraph::RequestData(
  vtkInformation* vtkNotUsed(request),
  vtkInformationVector** inputVector,
  vtkInformationVector* outputVector)
{
  vtkGraph* input = vtkGraph::GetData(inputVector[0]);
  vtkSelection* selection = vtkSelection::GetData(inputVector[1]);

  // Convert the selection to an INDICES selection
  vtkSmartPointer<vtkSelection> converted;
  converted.TakeReference(vtkConvertSelection::ToIndexSelection(selection, input));
  if (!converted.GetPointer())
    {
    vtkErrorMacro("Selection conversion to INDICES failed.");
    return 0;
    }

  // Collect vertex and edge selections.
  vtkSmartPointer<vtkIdTypeArray> edgeList = vtkSmartPointer<vtkIdTypeArray>::New();
  bool hasEdges = false;
  vtkSmartPointer<vtkIdTypeArray> vertexList = vtkSmartPointer<vtkIdTypeArray>::New();
  bool hasVertices = false;
  for (unsigned int i = 0; i < converted->GetNumberOfNodes(); ++i)
    {
    vtkSelectionNode* node = converted->GetNode(i);
    vtkIdTypeArray* list = 0;
    if (node->GetFieldType() == vtkSelectionNode::VERTEX)
      {
      list = vertexList;
      hasVertices = true;
      }
    else if (node->GetFieldType() == vtkSelectionNode::EDGE)
      {
      list = edgeList;
      hasEdges = true;
      }

    if (list)
      {
      // Append the selection list to the selection
      vtkIdTypeArray* curList = vtkIdTypeArray::SafeDownCast(node->GetSelectionList());
      if (curList)
        {
        int inverse = node->GetProperties()->Get(vtkSelectionNode::INVERSE());
        if (inverse)
          {
          vtkIdType num =
            (node->GetFieldType() == vtkSelectionNode::VERTEX) ?
            input->GetNumberOfVertices() : input->GetNumberOfEdges();
          for (vtkIdType j = 0; i < num; ++j)
            {
            if (curList->LookupValue(j) < 0 && list->LookupValue(j) < 0)
              {
              list->InsertNextValue(j);
              }
            }
          }
        else
          {
          vtkIdType numTuples = curList->GetNumberOfTuples();
          for (vtkIdType j = 0; j < numTuples; ++j)
            {
            vtkIdType curValue = curList->GetValue(j);
            if (list->LookupValue(curValue) < 0)
              {
              list->InsertNextValue(curValue);
              }
            }
          }
        } // end if (curList)
      } // end if (list)
    } // end for each child

  // If there is no selection list, return an empty graph
  if (vertexList->GetNumberOfTuples() == 0 && edgeList->GetNumberOfTuples() == 0)
    {
    return 1;
    }

  vtkSmartPointer<vtkMutableDirectedGraph> dirBuilder =
    vtkSmartPointer<vtkMutableDirectedGraph>::New();
  vtkSmartPointer<vtkMutableUndirectedGraph> undirBuilder =
    vtkSmartPointer<vtkMutableUndirectedGraph>::New();
  bool directed;
  vtkGraph* builder = 0;
  if (vtkDirectedGraph::SafeDownCast(input))
    {
    directed = true;
    builder = dirBuilder;
    }
  else
    {
    directed = false;
    builder = undirBuilder;
    }

  // There are three cases to handle:
  // 1. Selecting vertices only: Select the vertices along with any edges
  //    connecting two selected vertices.
  // 2. Selecting edges only: Select the edges along with all vertices
  //    adjacent to a selected edge.
  // 3. Selecting vertices and edges: Select the edges along with all vertices
  //    adjacent to a selected edge, plus any additional vertex specified
  //    in the vertex selection.

  vtkDataSetAttributes* vdIn = input->GetVertexData();
  vtkDataSetAttributes* edIn = input->GetEdgeData();
  vtkDataSetAttributes* vdOut = builder->GetVertexData();
  vtkDataSetAttributes* edOut = builder->GetEdgeData();
  vtkPoints* ptsIn = input->GetPoints();
  vtkPoints* ptsOut = builder->GetPoints();
  vdOut->CopyAllocate(vdIn);
  edOut->CopyAllocate(edIn);
  vtksys_stl::map<vtkIdType, vtkIdType> vertexMap;

  // Step 1: Add the vertices.
  // If the user has specified a vertex selection, add them.
  // Else if only an edge selection and RemoveIsolatedVertices is off,
  //   add all vertices to the output.
  // Otherwise, let the edge selection determine the vertices to add.
  if (hasVertices)
    {
    // Add selected vertices
    vtkIdType numSelectedVerts = vertexList->GetNumberOfTuples();
    for (vtkIdType i = 0; i < numSelectedVerts; ++i)
      {
      vtkIdType inVert = vertexList->GetValue(i);
      vtkIdType outVert = 0;
      if (directed)
        {
        outVert = dirBuilder->AddVertex();
        }
      else
        {
        outVert = undirBuilder->AddVertex();
        }
      vdOut->CopyData(vdIn, inVert, outVert);
      ptsOut->InsertNextPoint(ptsIn->GetPoint(inVert));
      vertexMap[inVert] = outVert;
      }
    }
  else if (!this->RemoveIsolatedVertices)
    {
    // In the special case where there is only an edge selection, the user may
    // specify that they want all vertices in the output.
    vtkIdType numVert = input->GetNumberOfVertices();
    for (vtkIdType inVert = 0; inVert < numVert; ++inVert)
      {
      vtkIdType outVert = 0;
      if (directed)
        {
        outVert = dirBuilder->AddVertex();
        }
      else
        {
        outVert = undirBuilder->AddVertex();
        }
      vdOut->CopyData(vdIn, inVert, outVert);
      ptsOut->InsertNextPoint(ptsIn->GetPoint(inVert));
      vertexMap[inVert] = outVert;
      }
    }

  // Step 2: Add the edges
  // If there is an edge selection, add those edges.
  // Otherwise, add all edges connecting selected vertices.
  if (hasEdges)
    {
    // Add selected edges
    vtkIdType numSelectedEdges = edgeList->GetNumberOfTuples();
    for (vtkIdType i = 0; i < numSelectedEdges; ++i)
      {
      vtkEdgeType e;
      e.Id = edgeList->GetValue(i);
      e.Source = input->GetSourceVertex(e.Id);
      e.Target = input->GetTargetVertex(e.Id);

      // Add source and target vertices if they are not yet in output
      vtkIdType addVert[2];
      int numAddVert = 0;
      if (vertexMap.find(e.Source) == vertexMap.end())
        {
        addVert[numAddVert] = e.Source;
        ++numAddVert;
        }
      if (vertexMap.find(e.Target) == vertexMap.end())
        {
        addVert[numAddVert] = e.Target;
        ++numAddVert;
        }
      for (int j = 0; j < numAddVert; ++j)
        {
        vtkIdType outVert = 0;
        if (directed)
          {
          outVert = dirBuilder->AddVertex();
          }
        else
          {
          outVert = undirBuilder->AddVertex();
          }
        vdOut->CopyData(vdIn, addVert[j], outVert);
        ptsOut->InsertNextPoint(ptsIn->GetPoint(addVert[j]));
        vertexMap[addVert[j]] = outVert;
        }

      // Add the selected edge
      vtkIdType source = vertexMap[e.Source];
      vtkIdType target = vertexMap[e.Target];
      vtkEdgeType f;
      if (directed)
        {
        f = dirBuilder->AddEdge(source, target);
        }
      else
        {
        f = undirBuilder->AddEdge(source, target);
        }
      edOut->CopyData(edIn, e.Id, f.Id);
      // Copy edge layout to the output.
      vtkIdType npts;
      double* pts;
      input->GetEdgePoints(e.Id, npts, pts);
      builder->SetEdgePoints(f.Id, npts, pts);
      }
    }
  else
    {
    // Add edges between selected vertices
    vtkSmartPointer<vtkEdgeListIterator> edges = vtkSmartPointer<vtkEdgeListIterator>::New();
    input->GetEdges(edges);
    while (edges->HasNext())
      {
      vtkEdgeType e = edges->Next();
      if (vertexMap.find(e.Source) != vertexMap.end() &&
          vertexMap.find(e.Target) != vertexMap.end())
        {
        vtkIdType source = vertexMap[e.Source];
        vtkIdType target = vertexMap[e.Target];
        vtkEdgeType f;
        if (directed)
          {
          f = dirBuilder->AddEdge(source, target);
          }
        else
          {
          f = undirBuilder->AddEdge(source, target);
          }
        edOut->CopyData(edIn, e.Id, f.Id);
        // Copy edge layout to the output.
        vtkIdType npts;
        double* pts;
        input->GetEdgePoints(e.Id, npts, pts);
        builder->SetEdgePoints(f.Id, npts, pts);
        }
      }
    }

  // Pass constructed graph to output.
  vtkGraph* output = vtkGraph::GetData(outputVector);
  if (directed)
    {
    if (!output->CheckedShallowCopy(dirBuilder))
      {
      vtkErrorMacro(<<"Invalid graph structure.");
      return 0;
      }
    }
  else
    {
    if (!output->CheckedShallowCopy(undirBuilder))
      {
      vtkErrorMacro(<<"Invalid graph structure.");
      return 0;
      }
    }
  output->GetFieldData()->PassData(input->GetFieldData());

  // Clean up
  output->Squeeze();

  return 1;
}

//----------------------------------------------------------------------------
void vtkExtractSelectedGraph::PrintSelf(ostream& os, vtkIndent indent)
{
  this->Superclass::PrintSelf(os, indent);
  os << indent << "RemoveIsolatedVertices: "
     << (this->RemoveIsolatedVertices ? "on" : "off") << endl;
}
<commit_msg>COMP: Removing warnings.<commit_after>/*=========================================================================

  Program:   Visualization Toolkit
  Module:    vtkExtractSelectedGraph.cxx

  Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
  All rights reserved.
  See Copyright.txt or http://www.kitware.com/Copyright.htm for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notice for more information.

=========================================================================*/
/*-------------------------------------------------------------------------
  Copyright 2008 Sandia Corporation.
  Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,
  the U.S. Government retains certain rights in this software.
-------------------------------------------------------------------------*/

#include "vtkExtractSelectedGraph.h"

#include "vtkCellArray.h"
#include "vtkCellData.h"
#include "vtkCommand.h"
#include "vtkConvertSelection.h"
#include "vtkDataArray.h"
#include "vtkEdgeListIterator.h"
#include "vtkEventForwarderCommand.h"
#include "vtkExtractSelection.h"
#include "vtkGraph.h"
#include "vtkIdTypeArray.h"
#include "vtkInformation.h"
#include "vtkInformationVector.h"
#include "vtkMutableDirectedGraph.h"
#include "vtkMutableUndirectedGraph.h"
#include "vtkObjectFactory.h"
#include "vtkPointData.h"
#include "vtkPoints.h"
#include "vtkSelection.h"
#include "vtkSelectionNode.h"
#include "vtkSignedCharArray.h"
#include "vtkSmartPointer.h"
#include "vtkStringArray.h"
#include "vtkTree.h"
#include "vtkVertexListIterator.h"

#include <vtksys/stl/map>
#include <vtkstd/vector>

vtkCxxRevisionMacro(vtkExtractSelectedGraph, "1.31");
vtkStandardNewMacro(vtkExtractSelectedGraph);
//----------------------------------------------------------------------------
vtkExtractSelectedGraph::vtkExtractSelectedGraph()
{
  this->SetNumberOfInputPorts(2);
  this->RemoveIsolatedVertices = true;
}

//----------------------------------------------------------------------------
vtkExtractSelectedGraph::~vtkExtractSelectedGraph()
{
}

//----------------------------------------------------------------------------
int vtkExtractSelectedGraph::FillInputPortInformation(int port, vtkInformation* info)
{
  if (port == 0)
    {
    info->Set(vtkAlgorithm::INPUT_REQUIRED_DATA_TYPE(), "vtkGraph");
    return 1;
    }
  else if (port == 1)
    {
    info->Set(vtkAlgorithm::INPUT_REQUIRED_DATA_TYPE(), "vtkSelection");
    return 1;
    }
  return 0;
}

//----------------------------------------------------------------------------
void vtkExtractSelectedGraph::SetSelectionConnection(vtkAlgorithmOutput* in)
{
  this->SetInputConnection(1, in);
}

//----------------------------------------------------------------------------
int vtkExtractSelectedGraph::RequestDataObject(
  vtkInformation*,
  vtkInformationVector** inputVector ,
  vtkInformationVector* outputVector)
{
  vtkInformation* inInfo = inputVector[0]->GetInformationObject(0);
  if (!inInfo)
    {
    return 0;
    }
  vtkGraph *input = vtkGraph::SafeDownCast(
    inInfo->Get(vtkDataObject::DATA_OBJECT()));

  if (input)
    {
    vtkInformation* info = outputVector->GetInformationObject(0);
    vtkGraph *output = vtkGraph::SafeDownCast(
      info->Get(vtkDataObject::DATA_OBJECT()));

    // Output a vtkDirectedGraph if the input is a tree.
    if (!output
        || (vtkTree::SafeDownCast(input) && !vtkDirectedGraph::SafeDownCast(output))
        || (!vtkTree::SafeDownCast(input) && !output->IsA(input->GetClassName())))
      {
      if (vtkTree::SafeDownCast(input))
        {
        output = vtkDirectedGraph::New();
        }
      else
        {
        output = input->NewInstance();
        }
      output->SetPipelineInformation(info);
      output->Delete();
      this->GetOutputPortInformation(0)->Set(
        vtkDataObject::DATA_EXTENT_TYPE(), output->GetExtentType());
      }
    return 1;
    }
  return 0;
}

//----------------------------------------------------------------------------
int vtkExtractSelectedGraph::RequestData(
  vtkInformation* vtkNotUsed(request),
  vtkInformationVector** inputVector,
  vtkInformationVector* outputVector)
{
  vtkGraph* input = vtkGraph::GetData(inputVector[0]);
  vtkSelection* selection = vtkSelection::GetData(inputVector[1]);

  // Convert the selection to an INDICES selection
  vtkSmartPointer<vtkSelection> converted;
  converted.TakeReference(vtkConvertSelection::ToIndexSelection(selection, input));
  if (!converted.GetPointer())
    {
    vtkErrorMacro("Selection conversion to INDICES failed.");
    return 0;
    }

  // Collect vertex and edge selections.
  vtkSmartPointer<vtkIdTypeArray> edgeList = vtkSmartPointer<vtkIdTypeArray>::New();
  bool hasEdges = false;
  vtkSmartPointer<vtkIdTypeArray> vertexList = vtkSmartPointer<vtkIdTypeArray>::New();
  bool hasVertices = false;
  for (unsigned int i = 0; i < converted->GetNumberOfNodes(); ++i)
    {
    vtkSelectionNode* node = converted->GetNode(i);
    vtkIdTypeArray* list = 0;
    if (node->GetFieldType() == vtkSelectionNode::VERTEX)
      {
      list = vertexList;
      hasVertices = true;
      }
    else if (node->GetFieldType() == vtkSelectionNode::EDGE)
      {
      list = edgeList;
      hasEdges = true;
      }

    if (list)
      {
      // Append the selection list to the selection
      vtkIdTypeArray* curList = vtkIdTypeArray::SafeDownCast(node->GetSelectionList());
      if (curList)
        {
        int inverse = node->GetProperties()->Get(vtkSelectionNode::INVERSE());
        if (inverse)
          {
          vtkIdType num =
            (node->GetFieldType() == vtkSelectionNode::VERTEX) ?
            input->GetNumberOfVertices() : input->GetNumberOfEdges();
          for (vtkIdType j = 0; j < num; ++j)
            {
            if (curList->LookupValue(j) < 0 && list->LookupValue(j) < 0)
              {
              list->InsertNextValue(j);
              }
            }
          }
        else
          {
          vtkIdType numTuples = curList->GetNumberOfTuples();
          for (vtkIdType j = 0; j < numTuples; ++j)
            {
            vtkIdType curValue = curList->GetValue(j);
            if (list->LookupValue(curValue) < 0)
              {
              list->InsertNextValue(curValue);
              }
            }
          }
        } // end if (curList)
      } // end if (list)
    } // end for each child

  // If there is no selection list, return an empty graph
  if (vertexList->GetNumberOfTuples() == 0 && edgeList->GetNumberOfTuples() == 0)
    {
    return 1;
    }

  vtkSmartPointer<vtkMutableDirectedGraph> dirBuilder =
    vtkSmartPointer<vtkMutableDirectedGraph>::New();
  vtkSmartPointer<vtkMutableUndirectedGraph> undirBuilder =
    vtkSmartPointer<vtkMutableUndirectedGraph>::New();
  bool directed;
  vtkGraph* builder = 0;
  if (vtkDirectedGraph::SafeDownCast(input))
    {
    directed = true;
    builder = dirBuilder;
    }
  else
    {
    directed = false;
    builder = undirBuilder;
    }

  // There are three cases to handle:
  // 1. Selecting vertices only: Select the vertices along with any edges
  //    connecting two selected vertices.
  // 2. Selecting edges only: Select the edges along with all vertices
  //    adjacent to a selected edge.
  // 3. Selecting vertices and edges: Select the edges along with all vertices
  //    adjacent to a selected edge, plus any additional vertex specified
  //    in the vertex selection.

  vtkDataSetAttributes* vdIn = input->GetVertexData();
  vtkDataSetAttributes* edIn = input->GetEdgeData();
  vtkDataSetAttributes* vdOut = builder->GetVertexData();
  vtkDataSetAttributes* edOut = builder->GetEdgeData();
  vtkPoints* ptsIn = input->GetPoints();
  vtkPoints* ptsOut = builder->GetPoints();
  vdOut->CopyAllocate(vdIn);
  edOut->CopyAllocate(edIn);
  vtksys_stl::map<vtkIdType, vtkIdType> vertexMap;

  // Step 1: Add the vertices.
  // If the user has specified a vertex selection, add them.
  // Else if only an edge selection and RemoveIsolatedVertices is off,
  //   add all vertices to the output.
  // Otherwise, let the edge selection determine the vertices to add.
  if (hasVertices)
    {
    // Add selected vertices
    vtkIdType numSelectedVerts = vertexList->GetNumberOfTuples();
    for (vtkIdType i = 0; i < numSelectedVerts; ++i)
      {
      vtkIdType inVert = vertexList->GetValue(i);
      vtkIdType outVert = 0;
      if (directed)
        {
        outVert = dirBuilder->AddVertex();
        }
      else
        {
        outVert = undirBuilder->AddVertex();
        }
      vdOut->CopyData(vdIn, inVert, outVert);
      ptsOut->InsertNextPoint(ptsIn->GetPoint(inVert));
      vertexMap[inVert] = outVert;
      }
    }
  else if (!this->RemoveIsolatedVertices)
    {
    // In the special case where there is only an edge selection, the user may
    // specify that they want all vertices in the output.
    vtkIdType numVert = input->GetNumberOfVertices();
    for (vtkIdType inVert = 0; inVert < numVert; ++inVert)
      {
      vtkIdType outVert = 0;
      if (directed)
        {
        outVert = dirBuilder->AddVertex();
        }
      else
        {
        outVert = undirBuilder->AddVertex();
        }
      vdOut->CopyData(vdIn, inVert, outVert);
      ptsOut->InsertNextPoint(ptsIn->GetPoint(inVert));
      vertexMap[inVert] = outVert;
      }
    }

  // Step 2: Add the edges
  // If there is an edge selection, add those edges.
  // Otherwise, add all edges connecting selected vertices.
  if (hasEdges)
    {
    // Add selected edges
    vtkIdType numSelectedEdges = edgeList->GetNumberOfTuples();
    for (vtkIdType i = 0; i < numSelectedEdges; ++i)
      {
      vtkEdgeType e;
      e.Id = edgeList->GetValue(i);
      e.Source = input->GetSourceVertex(e.Id);
      e.Target = input->GetTargetVertex(e.Id);

      // Add source and target vertices if they are not yet in output
      vtkIdType addVert[2];
      int numAddVert = 0;
      if (vertexMap.find(e.Source) == vertexMap.end())
        {
        addVert[numAddVert] = e.Source;
        ++numAddVert;
        }
      if (vertexMap.find(e.Target) == vertexMap.end())
        {
        addVert[numAddVert] = e.Target;
        ++numAddVert;
        }
      for (int j = 0; j < numAddVert; ++j)
        {
        vtkIdType outVert = 0;
        if (directed)
          {
          outVert = dirBuilder->AddVertex();
          }
        else
          {
          outVert = undirBuilder->AddVertex();
          }
        vdOut->CopyData(vdIn, addVert[j], outVert);
        ptsOut->InsertNextPoint(ptsIn->GetPoint(addVert[j]));
        vertexMap[addVert[j]] = outVert;
        }

      // Add the selected edge
      vtkIdType source = vertexMap[e.Source];
      vtkIdType target = vertexMap[e.Target];
      vtkEdgeType f;
      if (directed)
        {
        f = dirBuilder->AddEdge(source, target);
        }
      else
        {
        f = undirBuilder->AddEdge(source, target);
        }
      edOut->CopyData(edIn, e.Id, f.Id);
      // Copy edge layout to the output.
      vtkIdType npts;
      double* pts;
      input->GetEdgePoints(e.Id, npts, pts);
      builder->SetEdgePoints(f.Id, npts, pts);
      }
    }
  else
    {
    // Add edges between selected vertices
    vtkSmartPointer<vtkEdgeListIterator> edges = vtkSmartPointer<vtkEdgeListIterator>::New();
    input->GetEdges(edges);
    while (edges->HasNext())
      {
      vtkEdgeType e = edges->Next();
      if (vertexMap.find(e.Source) != vertexMap.end() &&
          vertexMap.find(e.Target) != vertexMap.end())
        {
        vtkIdType source = vertexMap[e.Source];
        vtkIdType target = vertexMap[e.Target];
        vtkEdgeType f;
        if (directed)
          {
          f = dirBuilder->AddEdge(source, target);
          }
        else
          {
          f = undirBuilder->AddEdge(source, target);
          }
        edOut->CopyData(edIn, e.Id, f.Id);
        // Copy edge layout to the output.
        vtkIdType npts;
        double* pts;
        input->GetEdgePoints(e.Id, npts, pts);
        builder->SetEdgePoints(f.Id, npts, pts);
        }
      }
    }

  // Pass constructed graph to output.
  vtkGraph* output = vtkGraph::GetData(outputVector);
  if (directed)
    {
    if (!output->CheckedShallowCopy(dirBuilder))
      {
      vtkErrorMacro(<<"Invalid graph structure.");
      return 0;
      }
    }
  else
    {
    if (!output->CheckedShallowCopy(undirBuilder))
      {
      vtkErrorMacro(<<"Invalid graph structure.");
      return 0;
      }
    }
  output->GetFieldData()->PassData(input->GetFieldData());

  // Clean up
  output->Squeeze();

  return 1;
}

//----------------------------------------------------------------------------
void vtkExtractSelectedGraph::PrintSelf(ostream& os, vtkIndent indent)
{
  this->Superclass::PrintSelf(os, indent);
  os << indent << "RemoveIsolatedVertices: "
     << (this->RemoveIsolatedVertices ? "on" : "off") << endl;
}
<|endoftext|>


<commit_before>//===--- StmtDumper.cpp - Dumping implementation for Stmt ASTs ------------===//
//
//                     The LLVM Compiler Infrastructure
//
// This file was developed by Chris Lattner and is distributed under
// the University of Illinois Open Source License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This file implements the Stmt::dump/Stmt::print methods, which dump out the
// AST in a form that exposes type details and other fields.
//
//===----------------------------------------------------------------------===//

#include "clang/AST/StmtVisitor.h"
#include "clang/AST/Decl.h"
#include "clang/AST/ExprCXX.h"
#include "clang/Lex/IdentifierTable.h"
#include "llvm/Support/Compiler.h"
#include <cstdio>
using namespace clang;

//===----------------------------------------------------------------------===//
// StmtDumper Visitor
//===----------------------------------------------------------------------===//

namespace  {
  class VISIBILITY_HIDDEN StmtDumper : public StmtVisitor<StmtDumper> {
    const SourceManager *SM;
    FILE *F;
    unsigned IndentLevel;

    /// MaxDepth - When doing a normal dump (not dumpAll) we only want to dump
    /// the first few levels of an AST.  This keeps track of how many ast levels
    /// are left.
    unsigned MaxDepth;
  public:
    StmtDumper(const SourceManager *sm, FILE *f, unsigned maxDepth)
      : SM(sm), F(f), IndentLevel(0-1), MaxDepth(maxDepth) {}

    void DumpSubTree(Stmt *S) {
      // Prune the recursion if not using dump all.
      if (MaxDepth == 0) return;

      ++IndentLevel;
      if (S) {
        Visit(S);

        // Print out children.
        Stmt::child_iterator CI = S->child_begin(), CE = S->child_end();
        if (CI != CE) {
          while (CI != CE) {
            fprintf(F, "\n");
            DumpSubTree(*CI++);
          }
        }
        fprintf(F, ")");
      } else {
        Indent();
        fprintf(F, "<<<NULL>>>");
      }
      --IndentLevel;
    }

    void DumpDeclarator(Decl *D);

    void Indent() const {
      for (int i = 0, e = IndentLevel; i < e; ++i)
        fprintf(F, "  ");
    }

    void DumpType(QualType T) const {
      fprintf(F, "'%s'", T.getAsString().c_str());

      // If the type is directly a typedef, strip off typedefness to give at
      // least one level of concreteness.
      if (TypedefType *TDT = dyn_cast<TypedefType>(T))
        fprintf(F, ":'%s'", TDT->LookThroughTypedefs().getAsString().c_str());
    }

    void DumpStmt(const Stmt *Node) const {
      Indent();
      fprintf(F, "(%s %p", Node->getStmtClassName(), (void*)Node);
    }

    void DumpExpr(Expr *Node) const {
      DumpStmt(Node);
      fprintf(F, " ");
      DumpType(Node->getType());
    }

    void VisitStmt(Stmt *Node);
#define STMT(N, CLASS, PARENT) \
    void Visit##CLASS(CLASS *Node);
#include "clang/AST/StmtNodes.def"
  };
}

//===----------------------------------------------------------------------===//
//  Stmt printing methods.
//===----------------------------------------------------------------------===//

void StmtDumper::VisitStmt(Stmt *Node) {
  Indent();
  fprintf(F, "<<unknown stmt type>>\n");
}

void StmtDumper::DumpDeclarator(Decl *D) {
  // FIXME: Need to complete/beautify this... this code simply shows the
  // nodes are where they need to be.
  if (TypedefDecl *localType = dyn_cast<TypedefDecl>(D)) {
    fprintf(F, "\"typedef %s %s\"",
            localType->getUnderlyingType().getAsString().c_str(),
            localType->getName());
  } else if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) {
    fprintf(F, "\"");
    // Emit storage class for vardecls.
    if (VarDecl *V = dyn_cast<VarDecl>(VD)) {
      switch (V->getStorageClass()) {
      default: assert(0 && "Unknown storage class!");
      case VarDecl::None:     break;
      case VarDecl::Extern:   fprintf(F, "extern "); break;
      case VarDecl::Static:   fprintf(F, "static "); break;
      case VarDecl::Auto:     fprintf(F, "auto "); break;
      case VarDecl::Register: fprintf(F, "register "); break;
      }
    }

    std::string Name = VD->getName();
    VD->getType().getAsStringInternal(Name);
    fprintf(F, "%s", Name.c_str());

    // If this is a vardecl with an initializer, emit it.
    if (VarDecl *V = dyn_cast<VarDecl>(VD)) {
      if (V->getInit()) {
        fprintf(F, " =\n");
        DumpSubTree(V->getInit());
      }
    }
    fprintf(F, "\"");
  } else {
    // FIXME: "struct x;"
    assert(0 && "Unexpected decl");
  }
}

void StmtDumper::VisitNullStmt(NullStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitDeclStmt(DeclStmt *Node) {
  DumpStmt(Node);
  fprintf(F, "\n");
  for (Decl *D = Node->getDecl(); D; D = D->getNextDeclarator()) {
    ++IndentLevel;
    Indent();
    fprintf(F, "%p ", (void*)D);
    DumpDeclarator(D);
    if (D->getNextDeclarator())
      fprintf(F, "\n");
    --IndentLevel;
  }
}

void StmtDumper::VisitCompoundStmt(CompoundStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitCaseStmt(CaseStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitDefaultStmt(DefaultStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitLabelStmt(LabelStmt *Node) {
  DumpStmt(Node);
  fprintf(F, " '%s'\n", Node->getName());
}

void StmtDumper::VisitIfStmt(IfStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitSwitchStmt(SwitchStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitSwitchCase(SwitchCase*) {
  assert(0 && "SwitchCase is an abstract class");
}

void StmtDumper::VisitWhileStmt(WhileStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitDoStmt(DoStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitForStmt(ForStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitGotoStmt(GotoStmt *Node) {
  DumpStmt(Node);
  fprintf(F, " '%s':%p", Node->getLabel()->getName(), (void*)Node->getLabel());
}

void StmtDumper::VisitIndirectGotoStmt(IndirectGotoStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitContinueStmt(ContinueStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitBreakStmt(BreakStmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::VisitReturnStmt(ReturnStmt *Node) {
  DumpStmt(Node);
}

//===----------------------------------------------------------------------===//
//  Expr printing methods.
//===----------------------------------------------------------------------===//

void StmtDumper::VisitExpr(Expr *Node) {
  DumpExpr(Node);
  fprintf(F, ": UNKNOWN EXPR to StmtDumper)");
}

void StmtDumper::VisitDeclRefExpr(DeclRefExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " Decl='%s' %p", Node->getDecl()->getName(),
          (void*)Node->getDecl());
}

void StmtDumper::VisitPreDefinedExpr(PreDefinedExpr *Node) {
  DumpExpr(Node);
  switch (Node->getIdentType()) {
  default:
    assert(0 && "unknown case");
  case PreDefinedExpr::Func:
    fprintf(F, " __func__");
    break;
  case PreDefinedExpr::Function:
    fprintf(F, " __FUNCTION__");
    break;
  case PreDefinedExpr::PrettyFunction:
    fprintf(F, " __PRETTY_FUNCTION__");
    break;
  }
}

void StmtDumper::VisitCharacterLiteral(CharacterLiteral *Node) {
  DumpExpr(Node);
  fprintf(F, " %d", Node->getValue());
}

void StmtDumper::VisitIntegerLiteral(IntegerLiteral *Node) {
  DumpExpr(Node);

  bool isSigned = Node->getType()->isSignedIntegerType();
  fprintf(F, " %s", Node->getValue().toString(10, isSigned).c_str());
}
void StmtDumper::VisitFloatingLiteral(FloatingLiteral *Node) {
  DumpExpr(Node);
  fprintf(F, " %f", Node->getValue());
}

void StmtDumper::VisitImaginaryLiteral(ImaginaryLiteral *Node) {
  DumpExpr(Node);
}

void StmtDumper::VisitStringLiteral(StringLiteral *Str) {
  DumpExpr(Str);
  // FIXME: this doesn't print wstrings right.
  fprintf(F, " %s\"", Str->isWide() ? "L" : "");

  for (unsigned i = 0, e = Str->getByteLength(); i != e; ++i) {
    switch (char C = Str->getStrData()[i]) {
    default:
      if (isprint(C))
        fputc(C, F);
      else
        fprintf(F, "\\%03o", C);
      break;
    // Handle some common ones to make dumps prettier.
    case '\\': fprintf(F, "\\\\"); break;
    case '"':  fprintf(F, "\\\""); break;
    case '\n': fprintf(F, "\\n"); break;
    case '\t': fprintf(F, "\\t"); break;
    case '\a': fprintf(F, "\\a"); break;
    case '\b': fprintf(F, "\\b"); break;
    }
  }
  fprintf(F, "\"");
}
void StmtDumper::VisitParenExpr(ParenExpr *Node) {
  DumpExpr(Node);
}
void StmtDumper::VisitUnaryOperator(UnaryOperator *Node) {
  DumpExpr(Node);
  fprintf(F, " %s '%s'", Node->isPostfix() ? "postfix" : "prefix",
          UnaryOperator::getOpcodeStr(Node->getOpcode()));
}
void StmtDumper::VisitSizeOfAlignOfTypeExpr(SizeOfAlignOfTypeExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s ", Node->isSizeOf() ? "sizeof" : "alignof");
  DumpType(Node->getArgumentType());
}
void StmtDumper::VisitArraySubscriptExpr(ArraySubscriptExpr *Node) {
  DumpExpr(Node);
}

void StmtDumper::VisitCallExpr(CallExpr *Node) {
  DumpExpr(Node);
}

void StmtDumper::VisitMemberExpr(MemberExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s%s %p", Node->isArrow() ? "->" : ".",
          Node->getMemberDecl()->getName(), (void*)Node->getMemberDecl());
}
void StmtDumper::VisitOCUVectorElementExpr(OCUVectorElementExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s", Node->getAccessor().getName());
}
void StmtDumper::VisitCastExpr(CastExpr *Node) {
  DumpExpr(Node);
}
void StmtDumper::VisitCompoundLiteralExpr(CompoundLiteralExpr *Node) {
  DumpExpr(Node);
}
void StmtDumper::VisitImplicitCastExpr(ImplicitCastExpr *Node) {
  DumpExpr(Node);
}
void StmtDumper::VisitBinaryOperator(BinaryOperator *Node) {
  DumpExpr(Node);
  fprintf(F, " '%s'", BinaryOperator::getOpcodeStr(Node->getOpcode()));
}
void StmtDumper::VisitCompoundAssignOperator(CompoundAssignOperator *Node) {
  DumpExpr(Node);
  fprintf(F, " '%s' ComputeTy=",
          BinaryOperator::getOpcodeStr(Node->getOpcode()));
  DumpType(Node->getComputationType());
}
void StmtDumper::VisitConditionalOperator(ConditionalOperator *Node) {
  DumpExpr(Node);
}

// GNU extensions.

void StmtDumper::VisitAddrLabelExpr(AddrLabelExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s %p", Node->getLabel()->getName(), (void*)Node->getLabel());
}

void StmtDumper::VisitStmtExpr(StmtExpr *Node) {
  DumpExpr(Node);
}

void StmtDumper::VisitTypesCompatibleExpr(TypesCompatibleExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " ");
  DumpType(Node->getArgType1());
  fprintf(F, " ");
  DumpType(Node->getArgType2());
}

void StmtDumper::VisitChooseExpr(ChooseExpr *Node) {
  DumpExpr(Node);
}

//===----------------------------------------------------------------------===//
// C++ Expressions
//===----------------------------------------------------------------------===//

void StmtDumper::VisitCXXCastExpr(CXXCastExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s", CXXCastExpr::getOpcodeStr(Node->getOpcode()));
}

void StmtDumper::VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s", Node->getValue() ? "true" : "false");
}

//===----------------------------------------------------------------------===//
// Obj-C Expressions
//===----------------------------------------------------------------------===//

void StmtDumper::VisitObjCStringLiteral(ObjCStringLiteral *Node) {
  DumpExpr(Node);
}

void StmtDumper::VisitObjCEncodeExpr(ObjCEncodeExpr *Node) {
  DumpExpr(Node);

  fprintf(F, " ");
  DumpType(Node->getEncodedType());
}

//===----------------------------------------------------------------------===//
// Stmt method implementations
//===----------------------------------------------------------------------===//

/// dump - This does a local dump of the specified AST fragment.  It dumps the
/// specified node and a few nodes underneath it, but not the whole subtree.
/// This is useful in a debugger.
void Stmt::dump(const SourceManager &SM) const {
  StmtDumper P(&SM, stderr, 4);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}

/// dump - This does a local dump of the specified AST fragment.  It dumps the
/// specified node and a few nodes underneath it, but not the whole subtree.
/// This is useful in a debugger.
void Stmt::dump() const {
  StmtDumper P(0, stderr, 4);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}

/// dumpAll - This does a dump of the specified AST fragment and all subtrees.
void Stmt::dumpAll(const SourceManager &SM) const {
  StmtDumper P(&SM, stderr, ~0U);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}

/// dumpAll - This does a dump of the specified AST fragment and all subtrees.
void Stmt::dumpAll() const {
  StmtDumper P(0, stderr, ~0U);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}
<commit_msg>Previous commit should have been:   Use Ted's child walking interface to allow the dumper to walk the tree    in one place and only have node-specific callbacks worry about    formatting the nodes (instead of formatting the nodes plus walking the   tree).<commit_after>//===--- StmtDumper.cpp - Dumping implementation for Stmt ASTs ------------===//
//
//                     The LLVM Compiler Infrastructure
//
// This file was developed by Chris Lattner and is distributed under
// the University of Illinois Open Source License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This file implements the Stmt::dump/Stmt::print methods, which dump out the
// AST in a form that exposes type details and other fields.
//
//===----------------------------------------------------------------------===//

#include "clang/AST/StmtVisitor.h"
#include "clang/AST/Decl.h"
#include "clang/AST/ExprCXX.h"
#include "clang/Lex/IdentifierTable.h"
#include "llvm/Support/Compiler.h"
#include <cstdio>
using namespace clang;

//===----------------------------------------------------------------------===//
// StmtDumper Visitor
//===----------------------------------------------------------------------===//

namespace  {
  class VISIBILITY_HIDDEN StmtDumper : public StmtVisitor<StmtDumper> {
    const SourceManager *SM;
    FILE *F;
    unsigned IndentLevel;

    /// MaxDepth - When doing a normal dump (not dumpAll) we only want to dump
    /// the first few levels of an AST.  This keeps track of how many ast levels
    /// are left.
    unsigned MaxDepth;
  public:
    StmtDumper(const SourceManager *sm, FILE *f, unsigned maxDepth)
      : SM(sm), F(f), IndentLevel(0-1), MaxDepth(maxDepth) {}

    void DumpSubTree(Stmt *S) {
      // Prune the recursion if not using dump all.
      if (MaxDepth == 0) return;

      ++IndentLevel;
      if (S) {
        Visit(S);

        // Print out children.
        Stmt::child_iterator CI = S->child_begin(), CE = S->child_end();
        if (CI != CE) {
          while (CI != CE) {
            fprintf(F, "\n");
            DumpSubTree(*CI++);
          }
        }
        fprintf(F, ")");
      } else {
        Indent();
        fprintf(F, "<<<NULL>>>");
      }
      --IndentLevel;
    }

    void DumpDeclarator(Decl *D);

    void Indent() const {
      for (int i = 0, e = IndentLevel; i < e; ++i)
        fprintf(F, "  ");
    }

    void DumpType(QualType T) const {
      fprintf(F, "'%s'", T.getAsString().c_str());

      // If the type is directly a typedef, strip off typedefness to give at
      // least one level of concreteness.
      if (TypedefType *TDT = dyn_cast<TypedefType>(T))
        fprintf(F, ":'%s'", TDT->LookThroughTypedefs().getAsString().c_str());
    }

    void DumpStmt(const Stmt *Node) const {
      Indent();
      fprintf(F, "(%s %p", Node->getStmtClassName(), (void*)Node);
    }

    void DumpExpr(Expr *Node) const {
      DumpStmt(Node);
      fprintf(F, " ");
      DumpType(Node->getType());
    }

    // Stmts.
    void VisitStmt(Stmt *Node);
    void VisitDeclStmt(DeclStmt *Node);
    void VisitLabelStmt(LabelStmt *Node);
    void VisitGotoStmt(GotoStmt *Node);

    // Exprs
    void VisitExpr(Expr *Node);
    void VisitDeclRefExpr(DeclRefExpr *Node);
    void VisitPreDefinedExpr(PreDefinedExpr *Node);
    void VisitCharacterLiteral(CharacterLiteral *Node);
    void VisitIntegerLiteral(IntegerLiteral *Node);
    void VisitFloatingLiteral(FloatingLiteral *Node);
    void VisitStringLiteral(StringLiteral *Str);
    void VisitUnaryOperator(UnaryOperator *Node);
    void VisitSizeOfAlignOfTypeExpr(SizeOfAlignOfTypeExpr *Node);
    void VisitMemberExpr(MemberExpr *Node);
    void VisitOCUVectorElementExpr(OCUVectorElementExpr *Node);
    void VisitBinaryOperator(BinaryOperator *Node);
    void VisitCompoundAssignOperator(CompoundAssignOperator *Node);
    void VisitAddrLabelExpr(AddrLabelExpr *Node);
    void VisitTypesCompatibleExpr(TypesCompatibleExpr *Node);

    // C++
    void VisitCXXCastExpr(CXXCastExpr *Node);
    void VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *Node);

    // ObjC
    void VisitObjCEncodeExpr(ObjCEncodeExpr *Node);
  };
}

//===----------------------------------------------------------------------===//
//  Stmt printing methods.
//===----------------------------------------------------------------------===//

void StmtDumper::VisitStmt(Stmt *Node) {
  DumpStmt(Node);
}

void StmtDumper::DumpDeclarator(Decl *D) {
  // FIXME: Need to complete/beautify this... this code simply shows the
  // nodes are where they need to be.
  if (TypedefDecl *localType = dyn_cast<TypedefDecl>(D)) {
    fprintf(F, "\"typedef %s %s\"",
            localType->getUnderlyingType().getAsString().c_str(),
            localType->getName());
  } else if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) {
    fprintf(F, "\"");
    // Emit storage class for vardecls.
    if (VarDecl *V = dyn_cast<VarDecl>(VD)) {
      switch (V->getStorageClass()) {
      default: assert(0 && "Unknown storage class!");
      case VarDecl::None:     break;
      case VarDecl::Extern:   fprintf(F, "extern "); break;
      case VarDecl::Static:   fprintf(F, "static "); break;
      case VarDecl::Auto:     fprintf(F, "auto "); break;
      case VarDecl::Register: fprintf(F, "register "); break;
      }
    }

    std::string Name = VD->getName();
    VD->getType().getAsStringInternal(Name);
    fprintf(F, "%s", Name.c_str());

    // If this is a vardecl with an initializer, emit it.
    if (VarDecl *V = dyn_cast<VarDecl>(VD)) {
      if (V->getInit()) {
        fprintf(F, " =\n");
        DumpSubTree(V->getInit());
      }
    }
    fprintf(F, "\"");
  } else {
    // FIXME: "struct x;"
    assert(0 && "Unexpected decl");
  }
}

void StmtDumper::VisitDeclStmt(DeclStmt *Node) {
  DumpStmt(Node);
  fprintf(F, "\n");
  for (Decl *D = Node->getDecl(); D; D = D->getNextDeclarator()) {
    ++IndentLevel;
    Indent();
    fprintf(F, "%p ", (void*)D);
    DumpDeclarator(D);
    if (D->getNextDeclarator())
      fprintf(F, "\n");
    --IndentLevel;
  }
}

void StmtDumper::VisitLabelStmt(LabelStmt *Node) {
  DumpStmt(Node);
  fprintf(F, " '%s'\n", Node->getName());
}

void StmtDumper::VisitGotoStmt(GotoStmt *Node) {
  DumpStmt(Node);
  fprintf(F, " '%s':%p", Node->getLabel()->getName(), (void*)Node->getLabel());
}

//===----------------------------------------------------------------------===//
//  Expr printing methods.
//===----------------------------------------------------------------------===//

void StmtDumper::VisitExpr(Expr *Node) {
  DumpExpr(Node);
}

void StmtDumper::VisitDeclRefExpr(DeclRefExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " Decl='%s' %p", Node->getDecl()->getName(),
          (void*)Node->getDecl());
}

void StmtDumper::VisitPreDefinedExpr(PreDefinedExpr *Node) {
  DumpExpr(Node);
  switch (Node->getIdentType()) {
  default:
    assert(0 && "unknown case");
  case PreDefinedExpr::Func:
    fprintf(F, " __func__");
    break;
  case PreDefinedExpr::Function:
    fprintf(F, " __FUNCTION__");
    break;
  case PreDefinedExpr::PrettyFunction:
    fprintf(F, " __PRETTY_FUNCTION__");
    break;
  }
}

void StmtDumper::VisitCharacterLiteral(CharacterLiteral *Node) {
  DumpExpr(Node);
  fprintf(F, " %d", Node->getValue());
}

void StmtDumper::VisitIntegerLiteral(IntegerLiteral *Node) {
  DumpExpr(Node);

  bool isSigned = Node->getType()->isSignedIntegerType();
  fprintf(F, " %s", Node->getValue().toString(10, isSigned).c_str());
}
void StmtDumper::VisitFloatingLiteral(FloatingLiteral *Node) {
  DumpExpr(Node);
  fprintf(F, " %f", Node->getValue());
}

void StmtDumper::VisitStringLiteral(StringLiteral *Str) {
  DumpExpr(Str);
  // FIXME: this doesn't print wstrings right.
  fprintf(F, " %s\"", Str->isWide() ? "L" : "");

  for (unsigned i = 0, e = Str->getByteLength(); i != e; ++i) {
    switch (char C = Str->getStrData()[i]) {
    default:
      if (isprint(C))
        fputc(C, F);
      else
        fprintf(F, "\\%03o", C);
      break;
    // Handle some common ones to make dumps prettier.
    case '\\': fprintf(F, "\\\\"); break;
    case '"':  fprintf(F, "\\\""); break;
    case '\n': fprintf(F, "\\n"); break;
    case '\t': fprintf(F, "\\t"); break;
    case '\a': fprintf(F, "\\a"); break;
    case '\b': fprintf(F, "\\b"); break;
    }
  }
  fprintf(F, "\"");
}

void StmtDumper::VisitUnaryOperator(UnaryOperator *Node) {
  DumpExpr(Node);
  fprintf(F, " %s '%s'", Node->isPostfix() ? "postfix" : "prefix",
          UnaryOperator::getOpcodeStr(Node->getOpcode()));
}
void StmtDumper::VisitSizeOfAlignOfTypeExpr(SizeOfAlignOfTypeExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s ", Node->isSizeOf() ? "sizeof" : "alignof");
  DumpType(Node->getArgumentType());
}

void StmtDumper::VisitMemberExpr(MemberExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s%s %p", Node->isArrow() ? "->" : ".",
          Node->getMemberDecl()->getName(), (void*)Node->getMemberDecl());
}
void StmtDumper::VisitOCUVectorElementExpr(OCUVectorElementExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s", Node->getAccessor().getName());
}
void StmtDumper::VisitBinaryOperator(BinaryOperator *Node) {
  DumpExpr(Node);
  fprintf(F, " '%s'", BinaryOperator::getOpcodeStr(Node->getOpcode()));
}
void StmtDumper::VisitCompoundAssignOperator(CompoundAssignOperator *Node) {
  DumpExpr(Node);
  fprintf(F, " '%s' ComputeTy=",
          BinaryOperator::getOpcodeStr(Node->getOpcode()));
  DumpType(Node->getComputationType());
}

// GNU extensions.

void StmtDumper::VisitAddrLabelExpr(AddrLabelExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s %p", Node->getLabel()->getName(), (void*)Node->getLabel());
}

void StmtDumper::VisitTypesCompatibleExpr(TypesCompatibleExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " ");
  DumpType(Node->getArgType1());
  fprintf(F, " ");
  DumpType(Node->getArgType2());
}

//===----------------------------------------------------------------------===//
// C++ Expressions
//===----------------------------------------------------------------------===//

void StmtDumper::VisitCXXCastExpr(CXXCastExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s", CXXCastExpr::getOpcodeStr(Node->getOpcode()));
}

void StmtDumper::VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *Node) {
  DumpExpr(Node);
  fprintf(F, " %s", Node->getValue() ? "true" : "false");
}

//===----------------------------------------------------------------------===//
// Obj-C Expressions
//===----------------------------------------------------------------------===//

void StmtDumper::VisitObjCEncodeExpr(ObjCEncodeExpr *Node) {
  DumpExpr(Node);

  fprintf(F, " ");
  DumpType(Node->getEncodedType());
}

//===----------------------------------------------------------------------===//
// Stmt method implementations
//===----------------------------------------------------------------------===//

/// dump - This does a local dump of the specified AST fragment.  It dumps the
/// specified node and a few nodes underneath it, but not the whole subtree.
/// This is useful in a debugger.
void Stmt::dump(const SourceManager &SM) const {
  StmtDumper P(&SM, stderr, 4);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}

/// dump - This does a local dump of the specified AST fragment.  It dumps the
/// specified node and a few nodes underneath it, but not the whole subtree.
/// This is useful in a debugger.
void Stmt::dump() const {
  StmtDumper P(0, stderr, 4);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}

/// dumpAll - This does a dump of the specified AST fragment and all subtrees.
void Stmt::dumpAll(const SourceManager &SM) const {
  StmtDumper P(&SM, stderr, ~0U);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}

/// dumpAll - This does a dump of the specified AST fragment and all subtrees.
void Stmt::dumpAll() const {
  StmtDumper P(0, stderr, ~0U);
  P.DumpSubTree(const_cast<Stmt*>(this));
  fprintf(stderr, "\n");
}
<|endoftext|>


<commit_before>#ifndef ALEPH_DISTANCES_DETAIL_MATRIX_HH__
#define ALEPH_DISTANCES_DETAIL_MATRIX_HH__

#include <algorithm>
#include <iosfwd>
#include <utility>

#include <cassert>
#include <cstddef>

namespace aleph
{

namespace distances
{

namespace detail
{

template <class T> class Matrix
{
public:

  Matrix( std::size_t n )
    : _n( n )
    , _data( new T*[_n] )
  {
    for( std::size_t row = 0; row < _n; row ++ )
    {
      _data[row] = new T[_n];

      std::fill( _data[row], _data[row] + _n, T() );
    }
  }

  ~Matrix()
  {
    for( std::size_t row = 0; row < _n; row++ )
      delete[] _data[row];

    delete[] _data;
  }

  Matrix( const Matrix& other )
    : _n( other._n )
    , _data( new T*[_n] )
  {
    for( std::size_t row = 0; row < _n; row ++ )
    {
      _data[row] = new T[_n];

      std::copy( other._data[row], other._data[row] + _n, _data[row] );
    }
  }

  Matrix( Matrix&& other )
    : Matrix( 0 )
  {
    swap( *this, other );
  }

  Matrix& operator=( Matrix other )
  {
    swap( *this, other );
    return *this;
  }

  friend void swap( Matrix& m1, Matrix& m2 ) noexcept
  {
    using std::swap;

    swap( m1._n,    m2._n );
    swap( m1._data, m2._data );
  }

  std::size_t n() const
  {
    return _n;
  }

  T& operator()( std::size_t row, std::size_t column )
  {
    return const_cast<T&>( static_cast<const Matrix&>( *this ).operator()( row, column ) );
  }

  const T& operator()( std::size_t row, std::size_t column ) const
  {
    assert( row    < _n );
    assert( column < _n );

    return _data[row][column];
  }

private:

  std::size_t _n = 0;
  T** _data      = nullptr;
};

template <class T> std::ostream& operator<<( std::ostream& o, const Matrix<T>& m )
{
  auto n = m.n();

  for( decltype(n) row = 0; row < n; row++ )
  {
    for( decltype(n) col = 0; col < n; col++ )
    {
      if( col > 0 )
        o << " ";

      o << m(row,col);
    }

    o << "\n";
  }

  return o;
}

}

}

}

#endif
<commit_msg>Fixed incorrect include<commit_after>#ifndef ALEPH_DISTANCES_DETAIL_MATRIX_HH__
#define ALEPH_DISTANCES_DETAIL_MATRIX_HH__

#include <algorithm>
#include <ostream>
#include <utility>

#include <cassert>
#include <cstddef>

namespace aleph
{

namespace distances
{

namespace detail
{

template <class T> class Matrix
{
public:

  Matrix( std::size_t n )
    : _n( n )
    , _data( new T*[_n] )
  {
    for( std::size_t row = 0; row < _n; row ++ )
    {
      _data[row] = new T[_n];

      std::fill( _data[row], _data[row] + _n, T() );
    }
  }

  ~Matrix()
  {
    for( std::size_t row = 0; row < _n; row++ )
      delete[] _data[row];

    delete[] _data;
  }

  Matrix( const Matrix& other )
    : _n( other._n )
    , _data( new T*[_n] )
  {
    for( std::size_t row = 0; row < _n; row ++ )
    {
      _data[row] = new T[_n];

      std::copy( other._data[row], other._data[row] + _n, _data[row] );
    }
  }

  Matrix( Matrix&& other )
    : Matrix( 0 )
  {
    swap( *this, other );
  }

  Matrix& operator=( Matrix other )
  {
    swap( *this, other );
    return *this;
  }

  friend void swap( Matrix& m1, Matrix& m2 ) noexcept
  {
    using std::swap;

    swap( m1._n,    m2._n );
    swap( m1._data, m2._data );
  }

  std::size_t n() const
  {
    return _n;
  }

  T& operator()( std::size_t row, std::size_t column )
  {
    return const_cast<T&>( static_cast<const Matrix&>( *this ).operator()( row, column ) );
  }

  const T& operator()( std::size_t row, std::size_t column ) const
  {
    assert( row    < _n );
    assert( column < _n );

    return _data[row][column];
  }

private:

  std::size_t _n = 0;
  T** _data      = nullptr;
};

template <class T> std::ostream& operator<<( std::ostream& o, const Matrix<T>& m )
{
  auto n = m.n();

  for( decltype(n) row = 0; row < n; row++ )
  {
    for( decltype(n) col = 0; col < n; col++ )
    {
      if( col > 0 )
        o << " ";

      o << m(row,col);
    }

    o << "\n";
  }

  return o;
}

}

}

}

#endif
<|endoftext|>


<commit_before>/*************************************************************************
 *
 *  OpenOffice.org - a multi-platform office productivity suite
 *
 *  $RCSfile: swcont.hxx,v $
 *
 *  $Revision: 1.4 $
 *
 *  last change: $Author: hr $ $Date: 2007-09-27 12:10:25 $
 *
 *  The Contents of this file are made available subject to
 *  the terms of GNU Lesser General Public License Version 2.1.
 *
 *
 *    GNU Lesser General Public License Version 2.1
 *    =============================================
 *    Copyright 2005 by Sun Microsystems, Inc.
 *    901 San Antonio Road, Palo Alto, CA 94303, USA
 *
 *    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., 59 Temple Place, Suite 330, Boston,
 *    MA  02111-1307  USA
 *
 ************************************************************************/

#ifndef _SWCONT_HXX
#define _SWCONT_HXX

#ifndef _STRING_HXX //autogen
#include <tools/string.hxx>
#endif

class SwContentType;

//Reihenfolge und Anzahl mit ResIds abgleichen!!
#define CONTENT_TYPE_OUTLINE        0
#define CONTENT_TYPE_TABLE          1
#define CONTENT_TYPE_FRAME          2
#define CONTENT_TYPE_GRAPHIC        3
#define CONTENT_TYPE_OLE            4
#define CONTENT_TYPE_BOOKMARK       5
#define CONTENT_TYPE_REGION         6
#define CONTENT_TYPE_URLFIELD       7
#define CONTENT_TYPE_REFERENCE      8
#define CONTENT_TYPE_INDEX          9
#define CONTENT_TYPE_POSTIT         10
#define CONTENT_TYPE_DRAWOBJECT     11
#define CONTENT_TYPE_MAX            CONTENT_TYPE_DRAWOBJECT +1

// Typen fuer das Globaldokument
#define GLOBAL_CONTENT_REGION       100
#define GLOBAL_CONTENT_INDEX        101
#define GLOBAL_CONTENT_TEXT         102
#define GLOBAL_CONTENT_MAX          3

// Strings fuer Kontextmenue
#define CONTEXT_COUNT   12
#define GLOBAL_CONTEXT_COUNT 14

// Modi fuer Drag 'n Drop
#define REGION_MODE_NONE        0
#define REGION_MODE_LINK        1
#define REGION_MODE_EMBEDDED    2

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

//mini rtti
class SwTypeNumber
{
    BYTE nTypeId;

    public:
        SwTypeNumber(BYTE nId) :nTypeId(nId){}
        virtual ~SwTypeNumber();

        virtual BYTE    GetTypeId();
};
//----------------------------------------------------------------------------

class SwContent : public SwTypeNumber
{
    const SwContentType*    pParent;
    String                  sContentName;
    long                    nYPosition;
    BOOL                    bInvisible;
public:
        SwContent(const SwContentType* pCnt, const String& rName, long nYPos );

    virtual BOOL            IsProtect() const;
    const SwContentType*    GetParent() const {return pParent;}
    const String&           GetName()   const {return sContentName;}
    int                     operator==(const SwContent& /*rCont*/) const
                                {
                                    //gleich sind sie nie, sonst fallen sie aus dem Array
                                    return FALSE;
                                }
    int                     operator<(const SwContent& rCont) const
                                {
                                    //zuerst nach Position dann nach Name sortieren
                                    return nYPosition != rCont.nYPosition ?
                                        nYPosition < rCont.nYPosition :
                                            sContentName < rCont.sContentName;;
                                }

    long        GetYPos() const {return nYPosition;}

    BOOL        IsInvisible() const {return bInvisible;}
    void        SetInvisible(){ bInvisible = TRUE;}
};

#endif
<commit_msg>INTEGRATION: CWS changefileheader (1.4.242); FILE MERGED 2008/04/01 15:59:20 thb 1.4.242.2: #i85898# Stripping all external header guards 2008/03/31 16:58:39 rt 1.4.242.1: #i87441# Change license header to LPGL v3.<commit_after>/*************************************************************************
 *
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * Copyright 2008 by Sun Microsystems, Inc.
 *
 * OpenOffice.org - a multi-platform office productivity suite
 *
 * $RCSfile: swcont.hxx,v $
 * $Revision: 1.5 $
 *
 * This file is part of OpenOffice.org.
 *
 * OpenOffice.org is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Lesser General Public License version 3
 * only, as published by the Free Software Foundation.
 *
 * OpenOffice.org 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 version 3 for more details
 * (a copy is included in the LICENSE file that accompanied this code).
 *
 * You should have received a copy of the GNU Lesser General Public License
 * version 3 along with OpenOffice.org.  If not, see
 * <http://www.openoffice.org/license.html>
 * for a copy of the LGPLv3 License.
 *
 ************************************************************************/

#ifndef _SWCONT_HXX
#define _SWCONT_HXX

#include <tools/string.hxx>

class SwContentType;

//Reihenfolge und Anzahl mit ResIds abgleichen!!
#define CONTENT_TYPE_OUTLINE        0
#define CONTENT_TYPE_TABLE          1
#define CONTENT_TYPE_FRAME          2
#define CONTENT_TYPE_GRAPHIC        3
#define CONTENT_TYPE_OLE            4
#define CONTENT_TYPE_BOOKMARK       5
#define CONTENT_TYPE_REGION         6
#define CONTENT_TYPE_URLFIELD       7
#define CONTENT_TYPE_REFERENCE      8
#define CONTENT_TYPE_INDEX          9
#define CONTENT_TYPE_POSTIT         10
#define CONTENT_TYPE_DRAWOBJECT     11
#define CONTENT_TYPE_MAX            CONTENT_TYPE_DRAWOBJECT +1

// Typen fuer das Globaldokument
#define GLOBAL_CONTENT_REGION       100
#define GLOBAL_CONTENT_INDEX        101
#define GLOBAL_CONTENT_TEXT         102
#define GLOBAL_CONTENT_MAX          3

// Strings fuer Kontextmenue
#define CONTEXT_COUNT   12
#define GLOBAL_CONTEXT_COUNT 14

// Modi fuer Drag 'n Drop
#define REGION_MODE_NONE        0
#define REGION_MODE_LINK        1
#define REGION_MODE_EMBEDDED    2

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

//mini rtti
class SwTypeNumber
{
    BYTE nTypeId;

    public:
        SwTypeNumber(BYTE nId) :nTypeId(nId){}
        virtual ~SwTypeNumber();

        virtual BYTE    GetTypeId();
};
//----------------------------------------------------------------------------

class SwContent : public SwTypeNumber
{
    const SwContentType*    pParent;
    String                  sContentName;
    long                    nYPosition;
    BOOL                    bInvisible;
public:
        SwContent(const SwContentType* pCnt, const String& rName, long nYPos );

    virtual BOOL            IsProtect() const;
    const SwContentType*    GetParent() const {return pParent;}
    const String&           GetName()   const {return sContentName;}
    int                     operator==(const SwContent& /*rCont*/) const
                                {
                                    //gleich sind sie nie, sonst fallen sie aus dem Array
                                    return FALSE;
                                }
    int                     operator<(const SwContent& rCont) const
                                {
                                    //zuerst nach Position dann nach Name sortieren
                                    return nYPosition != rCont.nYPosition ?
                                        nYPosition < rCont.nYPosition :
                                            sContentName < rCont.sContentName;;
                                }

    long        GetYPos() const {return nYPosition;}

    BOOL        IsInvisible() const {return bInvisible;}
    void        SetInvisible(){ bInvisible = TRUE;}
};

#endif
<|endoftext|>


<commit_before>#include <eeros/logger/Logger.hpp>
#include <eeros/logger/StreamLogWriter.hpp>
#include <eeros/safety/SafetySystem.hpp>
#include <eeros/control/TimeDomain.hpp>
#include <eeros/core/Executor.hpp>
#include <eeros/control/Constant.hpp>
#include <eeros/control/I.hpp>
#include <eeros/control/Trace.hpp>
#include <eeros/task/Lambda.hpp>
#include <eeros/math/Matrix.hpp>
#include <eeros/core/System.hpp>
#include <signal.h>
#include <iostream>
#include <fstream>

using namespace eeros;
using namespace eeros::safety;
using namespace eeros::logger;
using namespace eeros::control;
using namespace eeros::task;
using namespace eeros::math;

double period = 0.1;
double traceLen = 64;

class ControlSystem {
public:
	ControlSystem() : c(0.1), trace1(traceLen), trace2(traceLen) {
		i.getIn().connect(c.getOut());
		i.setInitCondition(Vector3{0, 1.0, 2.0});
		i.enable();
		trace1.getIn().connect(c.getOut());
		trace2.getIn().connect(i.getOut());
	}

	Constant<Vector3> c;
	I<Vector3> i;
	Trace<Vector3> trace1, trace2;
};

class SafetyPropertiesTest : public SafetyProperties {
public:
	SafetyPropertiesTest(ControlSystem& cs) :
		slOff("off"), slRunning("running"), seShutDown("switching off") {
		// Add levels
		addLevel(slOff);
		addLevel(slRunning);
		// Add events to the levels
		slRunning.addEvent(seShutDown, slOff, kPrivateEvent);
		// Define and add level functions
		slOff.setLevelAction([&](SafetyContext* privateContext) {Executor::stop();});
		slRunning.setLevelAction([&](SafetyContext* privateContext) {
			if (slRunning.getNofActivations() == 30) {// start after 3s
				cs.trace1.enable();
				cs.trace2.enable();
			}
			if (slRunning.getNofActivations() == 300) {// write to log file after 30s
				new TraceWriter<Vector3>(cs.trace2, "/tmp/ctrlData.txt");
			}
		});
		// Define action when exiting application with Ctrl-C
		exitFunction = [&](SafetyContext* privateContext) {privateContext->triggerEvent(seShutDown);};
		// Define entry level
		setEntryLevel(slRunning);
	};
	SafetyLevel slOff, slRunning;
	SafetyEvent seShutDown;
};

void signalHandler(int signum) {
	SafetySystem::exitHandler();
}

int main() {
	signal(SIGINT, signalHandler);

	StreamLogWriter w(std::cout);
	w.show(LogLevel::TRACE);
	Logger::setDefaultWriter(&w);
	Logger log;

	log.info() << "Trace test started...";

	ControlSystem controlSystem;

	// Create and initialize safety system
	SafetyPropertiesTest ssProperties(controlSystem);
	SafetySystem safetySys(ssProperties, period);

	// create time domain and add blocks of control system
	TimeDomain td("td1", period, true);
	td.addBlock(controlSystem.c);
	td.addBlock(controlSystem.i);
	td.addBlock(controlSystem.trace1);
	td.addBlock(controlSystem.trace2);

	// create periodic function for logging
	Lambda l1 ([&] () { });
	Periodic periodic("per1", 0.5, l1);
	periodic.monitors.push_back([&](PeriodicCounter &pc, Logger &log){
		log.info() << controlSystem.i.getOut().getSignal();
	});

	// Create and run executor
	auto& executor = eeros::Executor::instance();
	executor.setMainTask(safetySys);
	executor.add(td);
	executor.add(periodic);
	executor.run();

	log.info() << "start writing file";
	uint64_t start = eeros::System::getTimeNs();
	std::ofstream file;
	file.open("/mnt/ramdisk/ctrlData.txt", std::ios::trunc);
	timestamp_t* timeStampBuf = controlSystem.trace1.getTimestampTrace();
	Vector3* buf1 = controlSystem.trace1.getTrace();
	Vector3* buf2 = controlSystem.trace2.getTrace();
	for (int i = 0; i < controlSystem.trace1.getSize(); i++) file << timeStampBuf[i] << " " << buf1[i] << " " << buf2[i].getRow(0) << std::endl;
	file.close();
	uint64_t stop = eeros::System::getTimeNs();
	log.error() << stop - start;

	log.info() << "file written";

	log.info() << "Test finished...";
}
<commit_msg>improve example<commit_after>#include <eeros/logger/Logger.hpp>
#include <eeros/logger/StreamLogWriter.hpp>
#include <eeros/safety/SafetySystem.hpp>
#include <eeros/control/TimeDomain.hpp>
#include <eeros/core/Executor.hpp>
#include <eeros/control/Constant.hpp>
#include <eeros/control/I.hpp>
#include <eeros/control/Trace.hpp>
#include <eeros/task/Lambda.hpp>
#include <eeros/math/Matrix.hpp>
#include <eeros/core/System.hpp>
#include <signal.h>
#include <iostream>
#include <fstream>

using namespace eeros;
using namespace eeros::safety;
using namespace eeros::logger;
using namespace eeros::control;
using namespace eeros::task;
using namespace eeros::math;

double period = 0.1;
double traceLen = 64;

class ControlSystem {
public:
	ControlSystem() : c(0.1), trace1(traceLen), trace2(traceLen) {
		i.getIn().connect(c.getOut());
		i.setInitCondition(Vector3{0, 1.0, 2.0});
		i.enable();
		trace1.getIn().connect(c.getOut());
		trace2.getIn().connect(i.getOut());
	}

	Constant<Vector3> c;
	I<Vector3> i;
	Trace<Vector3> trace1, trace2;
};

class SafetyPropertiesTest : public SafetyProperties {
public:
	SafetyPropertiesTest(ControlSystem& cs) :
		slOff("off"), slRunning("running"), seShutDown("switching off") {
		// Add levels
		addLevel(slOff);
		addLevel(slRunning);
		// Add events to the levels
		slRunning.addEvent(seShutDown, slOff, kPrivateEvent);
		// Define and add level functions
		slOff.setLevelAction([&](SafetyContext* privateContext) {Executor::stop();});
		slRunning.setLevelAction([&](SafetyContext* privateContext) {
			if (slRunning.getNofActivations() == (int)(3 / period)) {// start after 3s
				cs.trace1.enable();
				cs.trace2.enable();
			}
			if (slRunning.getNofActivations() % (int)(30 / period) == 0) {// write to log file every 30s
				new TraceWriter<Vector3>(cs.trace2, "/tmp/ctrlData.txt");
			}
		});
		// Define action when exiting application with Ctrl-C
		exitFunction = [&](SafetyContext* privateContext) {privateContext->triggerEvent(seShutDown);};
		// Define entry level
		setEntryLevel(slRunning);
	};
	SafetyLevel slOff, slRunning;
	SafetyEvent seShutDown;
};

void signalHandler(int signum) {
	SafetySystem::exitHandler();
}

int main() {
	signal(SIGINT, signalHandler);

	StreamLogWriter w(std::cout);
	w.show(LogLevel::TRACE);
	Logger::setDefaultWriter(&w);
	Logger log;

	log.info() << "Trace test started...";

	ControlSystem controlSystem;

	// Create and initialize safety system
	SafetyPropertiesTest ssProperties(controlSystem);
	SafetySystem safetySys(ssProperties, period);

	// create time domain and add blocks of control system
	TimeDomain td("td1", period, true);
	td.addBlock(controlSystem.c);
	td.addBlock(controlSystem.i);
	td.addBlock(controlSystem.trace1);
	td.addBlock(controlSystem.trace2);

	// create periodic function for logging
	Lambda l1 ([&] () { });
	Periodic periodic("per1", 0.5, l1);
	periodic.monitors.push_back([&](PeriodicCounter &pc, Logger &log){
		log.info() << controlSystem.i.getOut().getSignal();
	});

	// Create and run executor
	auto& executor = eeros::Executor::instance();
	executor.setMainTask(safetySys);
	executor.add(td);
	executor.add(periodic);
	executor.run();

	log.info() << "start writing file";
	uint64_t start = eeros::System::getTimeNs();
	std::ofstream file;
	file.open("/mnt/ramdisk/ctrlData.txt", std::ios::trunc);
	timestamp_t* timeStampBuf = controlSystem.trace1.getTimestampTrace();
	Vector3* buf1 = controlSystem.trace1.getTrace();
	Vector3* buf2 = controlSystem.trace2.getTrace();
	for (int i = 0; i < controlSystem.trace1.getSize(); i++) file << timeStampBuf[i] << " " << buf1[i] << " " << buf2[i] << std::endl;
	file.close();
	uint64_t stop = eeros::System::getTimeNs();
	log.error() << stop - start;

	log.info() << "file written";

	log.info() << "Test finished...";
}
<|endoftext|>


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

#include "content/renderer/p2p/host_address_request.h"

#include "base/bind.h"
#include "base/message_loop_proxy.h"
#include "content/common/p2p_messages.h"
#include "content/renderer/p2p/socket_dispatcher.h"

namespace content {

P2PHostAddressRequest::P2PHostAddressRequest(P2PSocketDispatcher* dispatcher)
    : dispatcher_(dispatcher),
      ipc_message_loop_(dispatcher->message_loop()),
      delegate_message_loop_(base::MessageLoopProxy::current()),
      state_(STATE_CREATED),
      request_id_(0),
      registered_(false) {
}

P2PHostAddressRequest::~P2PHostAddressRequest() {
  DCHECK(state_ == STATE_CREATED || state_ == STATE_FINISHED);
}

void P2PHostAddressRequest::Request(const std::string& host_name,
                                    const DoneCallback& done_callback) {
  DCHECK(delegate_message_loop_->BelongsToCurrentThread());

  state_ = STATE_SENT;
  ipc_message_loop_->PostTask(FROM_HERE, base::Bind(
      &P2PHostAddressRequest::DoSendRequest, this, host_name, done_callback));
}

void P2PHostAddressRequest::Cancel() {
  DCHECK(delegate_message_loop_->BelongsToCurrentThread());

  if (state_ != STATE_FINISHED) {
    state_ = STATE_FINISHED;
    ipc_message_loop_->PostTask(FROM_HERE, base::Bind(
        &P2PHostAddressRequest::DoUnregister, this));
  }
}

void P2PHostAddressRequest::DoSendRequest(const std::string& host_name,
                                          const DoneCallback& done_callback) {
  DCHECK(ipc_message_loop_->BelongsToCurrentThread());

  done_callback_ = done_callback;
  request_id_ = dispatcher_->RegisterHostAddressRequest(this);
  registered_ = true;
  dispatcher_->SendP2PMessage(
      new P2PHostMsg_GetHostAddress(0, host_name, request_id_));
}

void P2PHostAddressRequest::DoUnregister() {
  DCHECK(ipc_message_loop_->BelongsToCurrentThread());
  if (registered_) {
    dispatcher_->UnregisterHostAddressRequest(request_id_);
    registered_ = false;
  }
}

void P2PHostAddressRequest::OnResponse(const net::IPAddressNumber& address) {
  DCHECK(ipc_message_loop_->BelongsToCurrentThread());
  delegate_message_loop_->PostTask(FROM_HERE, base::Bind(
      &P2PHostAddressRequest::DeliverResponse, this, address));
  dispatcher_->UnregisterHostAddressRequest(request_id_);
  registered_ = false;
}

void P2PHostAddressRequest::DeliverResponse(
    const net::IPAddressNumber& address) {
  DCHECK(delegate_message_loop_->BelongsToCurrentThread());
  if (state_ == STATE_SENT) {
    done_callback_.Run(address);
    state_ = STATE_FINISHED;
  }
}

}  // namespace content
<commit_msg>Fix crash when resolving stun address<commit_after>// Copyright (c) 2011 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "content/renderer/p2p/host_address_request.h"

#include "base/bind.h"
#include "base/message_loop_proxy.h"
#include "content/common/p2p_messages.h"
#include "content/renderer/p2p/socket_dispatcher.h"

namespace content {

P2PHostAddressRequest::P2PHostAddressRequest(P2PSocketDispatcher* dispatcher)
    : dispatcher_(dispatcher),
      ipc_message_loop_(dispatcher->message_loop()),
      delegate_message_loop_(base::MessageLoopProxy::current()),
      state_(STATE_CREATED),
      request_id_(0),
      registered_(false) {
}

P2PHostAddressRequest::~P2PHostAddressRequest() {
  DCHECK(state_ == STATE_CREATED || state_ == STATE_FINISHED);
  DCHECK(!registered_);
}

void P2PHostAddressRequest::Request(const std::string& host_name,
                                    const DoneCallback& done_callback) {
  DCHECK(delegate_message_loop_->BelongsToCurrentThread());

  state_ = STATE_SENT;
  ipc_message_loop_->PostTask(FROM_HERE, base::Bind(
      &P2PHostAddressRequest::DoSendRequest, this, host_name, done_callback));
}

void P2PHostAddressRequest::Cancel() {
  DCHECK(delegate_message_loop_->BelongsToCurrentThread());

  if (state_ != STATE_FINISHED) {
    state_ = STATE_FINISHED;
    ipc_message_loop_->PostTask(FROM_HERE, base::Bind(
        &P2PHostAddressRequest::DoUnregister, this));
  }
}

void P2PHostAddressRequest::DoSendRequest(const std::string& host_name,
                                          const DoneCallback& done_callback) {
  DCHECK(ipc_message_loop_->BelongsToCurrentThread());

  done_callback_ = done_callback;
  request_id_ = dispatcher_->RegisterHostAddressRequest(this);
  registered_ = true;
  dispatcher_->SendP2PMessage(
      new P2PHostMsg_GetHostAddress(0, host_name, request_id_));
}

void P2PHostAddressRequest::DoUnregister() {
  DCHECK(ipc_message_loop_->BelongsToCurrentThread());
  if (registered_) {
    dispatcher_->UnregisterHostAddressRequest(request_id_);
    registered_ = false;
  }
}

void P2PHostAddressRequest::OnResponse(const net::IPAddressNumber& address) {
  DCHECK(ipc_message_loop_->BelongsToCurrentThread());
  DCHECK(registered_);

  dispatcher_->UnregisterHostAddressRequest(request_id_);
  registered_ = false;

  delegate_message_loop_->PostTask(FROM_HERE, base::Bind(
      &P2PHostAddressRequest::DeliverResponse, this, address));
}

void P2PHostAddressRequest::DeliverResponse(
    const net::IPAddressNumber& address) {
  DCHECK(delegate_message_loop_->BelongsToCurrentThread());
  if (state_ == STATE_SENT) {
    done_callback_.Run(address);
    state_ = STATE_FINISHED;
  }
}

}  // namespace content
<|endoftext|>