<commit_before>//===--- PrintPreprocessedOutput.cpp - Implement the -E mode --------------===//
//
//                     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 code simply runs the preprocessor on the input file and prints out the
// result.  This is the traditional behavior of the -E option.
//
//===----------------------------------------------------------------------===//

#include "clang.h"
#include "clang/Lex/PPCallbacks.h"
#include "clang/Lex/Preprocessor.h"
#include "clang/Lex/Pragma.h"
#include "clang/Basic/SourceManager.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/Config/config.h"
#include <cstdio>
using namespace clang;

//===----------------------------------------------------------------------===//
// Simple buffered I/O
//===----------------------------------------------------------------------===//
//
// Empirically, iostream is over 30% slower than stdio for this workload, and
// stdio itself isn't very well suited.  The problem with stdio is use of
// putchar_unlocked.  We have many newline characters that need to be emitted,
// but stdio needs to do extra checks to handle line buffering mode.  These
// extra checks make putchar_unlocked fall off its inlined code path, hitting
// slow system code.  In practice, using 'write' directly makes 'clang -E -P'
// about 10% faster than using the stdio path on darwin.

#ifdef HAVE_UNISTD_H
#include <unistd.h>
#else
#define USE_STDIO 1
#endif

static char *OutBufStart = 0, *OutBufEnd, *OutBufCur;

/// InitOutputBuffer - Initialize our output buffer.
///
static void InitOutputBuffer() {
#ifndef USE_STDIO
  OutBufStart = new char[64*1024];
  OutBufEnd = OutBufStart+64*1024;
  OutBufCur = OutBufStart;
#endif
}

/// FlushBuffer - Write the accumulated bytes to the output stream.
///
static void FlushBuffer() {
#ifndef USE_STDIO
  write(STDOUT_FILENO, OutBufStart, OutBufCur-OutBufStart);
  OutBufCur = OutBufStart;
#endif
}

/// CleanupOutputBuffer - Finish up output.
///
static void CleanupOutputBuffer() {
#ifndef USE_STDIO
  FlushBuffer();
  delete [] OutBufStart;
#endif
}

static void OutputChar(char c) {
#ifdef USE_STDIO
  putchar_unlocked(c);
#else
  if (OutBufCur >= OutBufEnd)
    FlushBuffer();
  *OutBufCur++ = c;
#endif
}

static void OutputString(const char *Ptr, unsigned Size) {
#ifdef USE_STDIO
  fwrite(Ptr, Size, 1, stdout);
#else
  if (OutBufCur+Size >= OutBufEnd)
    FlushBuffer();
  memcpy(OutBufCur, Ptr, Size);
  OutBufCur += Size;
#endif
}

//===----------------------------------------------------------------------===//
// Preprocessed token printer
//===----------------------------------------------------------------------===//

static llvm::cl::opt<bool>
DisableLineMarkers("P", llvm::cl::desc("Disable linemarker output in -E mode"));
static llvm::cl::opt<bool>
EnableCommentOutput("C", llvm::cl::desc("Enable comment output in -E mode"));
static llvm::cl::opt<bool>
EnableMacroCommentOutput("CC",
                         llvm::cl::desc("Enable comment output in -E mode, "
                                        "even from macro expansions"));

namespace {
class PrintPPOutputPPCallbacks : public PPCallbacks {
  Preprocessor &PP;
  unsigned CurLine;
  std::string CurFilename;
  bool EmittedTokensOnThisLine;
  DirectoryLookup::DirType FileType;
public:
  PrintPPOutputPPCallbacks(Preprocessor &pp) : PP(pp) {
    CurLine = 0;
    CurFilename = "<uninit>";
    EmittedTokensOnThisLine = false;
    FileType = DirectoryLookup::NormalHeaderDir;
  }

  void SetEmittedTokensOnThisLine() { EmittedTokensOnThisLine = true; }

  virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason,
                           DirectoryLookup::DirType FileType);
  virtual void Ident(SourceLocation Loc, const std::string &str);

  void HandleFirstTokOnLine(Token &Tok);
  void MoveToLine(SourceLocation Loc);
  bool AvoidConcat(const Token &PrevTok, const Token &Tok);
};
}

/// MoveToLine - Move the output to the source line specified by the location
/// object.  We can do this by emitting some number of \n's, or be emitting a
/// #line directive.
void PrintPPOutputPPCallbacks::MoveToLine(SourceLocation Loc) {
  if (DisableLineMarkers) {
    if (EmittedTokensOnThisLine) {
      OutputChar('\n');
      EmittedTokensOnThisLine = false;
    }
    return;
  }

  unsigned LineNo = PP.getSourceManager().getLogicalLineNumber(Loc);

  // If this line is "close enough" to the original line, just print newlines,
  // otherwise print a #line directive.
  if (LineNo-CurLine < 8) {
    unsigned Line = CurLine;
    for (; Line != LineNo; ++Line)
      OutputChar('\n');
    CurLine = Line;
  } else {
    if (EmittedTokensOnThisLine) {
      OutputChar('\n');
      EmittedTokensOnThisLine = false;
    }

    CurLine = LineNo;

    OutputChar('#');
    OutputChar(' ');
    std::string Num = llvm::utostr_32(LineNo);
    OutputString(&Num[0], Num.size());
    OutputChar(' ');
    OutputChar('"');
    OutputString(&CurFilename[0], CurFilename.size());
    OutputChar('"');

    if (FileType == DirectoryLookup::SystemHeaderDir)
      OutputString(" 3", 2);
    else if (FileType == DirectoryLookup::ExternCSystemHeaderDir)
      OutputString(" 3 4", 4);
    OutputChar('\n');
  }
}

/// FileChanged - Whenever the preprocessor enters or exits a #include file
/// it invokes this handler.  Update our conception of the current source
/// position.
void PrintPPOutputPPCallbacks::FileChanged(SourceLocation Loc,
                                           FileChangeReason Reason,
                                           DirectoryLookup::DirType FileType) {
  if (DisableLineMarkers) return;

  // Unless we are exiting a #include, make sure to skip ahead to the line the
  // #include directive was at.
  SourceManager &SourceMgr = PP.getSourceManager();
  if (Reason == PPCallbacks::EnterFile) {
    MoveToLine(SourceMgr.getIncludeLoc(Loc));
  } else if (Reason == PPCallbacks::SystemHeaderPragma) {
    MoveToLine(Loc);

    // TODO GCC emits the # directive for this directive on the line AFTER the
    // directive and emits a bunch of spaces that aren't needed.  Emulate this
    // strange behavior.
  }

  Loc = SourceMgr.getLogicalLoc(Loc);
  CurLine = SourceMgr.getLineNumber(Loc);
  CurFilename = Lexer::Stringify(SourceMgr.getSourceName(Loc));
  FileType = FileType;

  if (EmittedTokensOnThisLine) {
    OutputChar('\n');
    EmittedTokensOnThisLine = false;
  }

  OutputChar('#');
  OutputChar(' ');
  std::string Num = llvm::utostr_32(CurLine);
  OutputString(&Num[0], Num.size());
  OutputChar(' ');
  OutputChar('"');
  OutputString(&CurFilename[0], CurFilename.size());
  OutputChar('"');

  switch (Reason) {
  case PPCallbacks::EnterFile:
    OutputString(" 1", 2);
    break;
  case PPCallbacks::ExitFile:
    OutputString(" 2", 2);
    break;
  case PPCallbacks::SystemHeaderPragma: break;
  case PPCallbacks::RenameFile: break;
  }

  if (FileType == DirectoryLookup::SystemHeaderDir)
    OutputString(" 3", 2);
  else if (FileType == DirectoryLookup::ExternCSystemHeaderDir)
    OutputString(" 3 4", 4);

  OutputChar('\n');
}

/// HandleIdent - Handle #ident directives when read by the preprocessor.
///
void PrintPPOutputPPCallbacks::Ident(SourceLocation Loc, const std::string &S) {
  MoveToLine(Loc);

  OutputString("#ident ", strlen("#ident "));
  OutputString(&S[0], S.size());
  EmittedTokensOnThisLine = true;
}

/// HandleFirstTokOnLine - When emitting a preprocessed file in -E mode, this
/// is called for the first token on each new line.
void PrintPPOutputPPCallbacks::HandleFirstTokOnLine(Token &Tok) {
  // Figure out what line we went to and insert the appropriate number of
  // newline characters.
  MoveToLine(Tok.getLocation());

  // Print out space characters so that the first token on a line is
  // indented for easy reading.
  const SourceManager &SourceMgr = PP.getSourceManager();
  unsigned ColNo = SourceMgr.getLogicalColumnNumber(Tok.getLocation());

  // This hack prevents stuff like:
  // #define HASH #
  // HASH define foo bar
  // From having the # character end up at column 1, which makes it so it
  // is not handled as a #define next time through the preprocessor if in
  // -fpreprocessed mode.
  if (ColNo <= 1 && Tok.getKind() == tok::hash)
    OutputChar(' ');

  // Otherwise, indent the appropriate number of spaces.
  for (; ColNo > 1; --ColNo)
    OutputChar(' ');
}

namespace {
struct UnknownPragmaHandler : public PragmaHandler {
  const char *Prefix;
  PrintPPOutputPPCallbacks *Callbacks;

  UnknownPragmaHandler(const char *prefix, PrintPPOutputPPCallbacks *callbacks)
    : PragmaHandler(0), Prefix(prefix), Callbacks(callbacks) {}
  virtual void HandlePragma(Preprocessor &PP, Token &PragmaTok) {
    // Figure out what line we went to and insert the appropriate number of
    // newline characters.
    Callbacks->MoveToLine(PragmaTok.getLocation());
    OutputString(Prefix, strlen(Prefix));

    // Read and print all of the pragma tokens.
    while (PragmaTok.getKind() != tok::eom) {
      if (PragmaTok.hasLeadingSpace())
        OutputChar(' ');
      std::string TokSpell = PP.getSpelling(PragmaTok);
      OutputString(&TokSpell[0], TokSpell.size());
      PP.LexUnexpandedToken(PragmaTok);
    }
    OutputChar('\n');
  }
};
} // end anonymous namespace

/// AvoidConcat - If printing PrevTok immediately followed by Tok would cause
/// the two individual tokens to be lexed as a single token, return true (which
/// causes a space to be printed between them).  This allows the output of -E
/// mode to be lexed to the same token stream as lexing the input directly
/// would.
///
/// This code must conservatively return true if it doesn't want to be 100%
/// accurate.  This will cause the output to include extra space characters, but
/// the resulting output won't have incorrect concatenations going on.  Examples
/// include "..", which we print with a space between, because we don't want to
/// track enough to tell "x.." from "...".
bool PrintPPOutputPPCallbacks::AvoidConcat(const Token &PrevTok,
                                           const Token &Tok) {
  char Buffer[256];

  // If we haven't emitted a token on this line yet, PrevTok isn't useful to
  // look at and no concatenation could happen anyway.
  if (!EmittedTokensOnThisLine)
    return false;

  // Basic algorithm: we look at the first character of the second token, and
  // determine whether it, if appended to the first token, would form (or would
  // contribute) to a larger token if concatenated.
  char FirstChar;
  if (IdentifierInfo *II = Tok.getIdentifierInfo()) {
    // Avoid spelling identifiers, the most common form of token.
    FirstChar = II->getName()[0];
  } else if (Tok.getLength() < 256) {
    const char *TokPtr = Buffer;
    PP.getSpelling(Tok, TokPtr);
    FirstChar = TokPtr[0];
  } else {
    FirstChar = PP.getSpelling(Tok)[0];
  }

  tok::TokenKind PrevKind = PrevTok.getKind();
  if (PrevTok.getIdentifierInfo())  // Language keyword or named operator.
    PrevKind = tok::identifier;

  switch (PrevKind) {
  default: return false;
  case tok::identifier:   // id+id or id+number or id+L"foo".
    return isalnum(FirstChar) || FirstChar == '_';
  case tok::numeric_constant:
    return isalnum(FirstChar) || Tok.getKind() == tok::numeric_constant ||
           FirstChar == '+' || FirstChar == '-' || FirstChar == '.';
  case tok::period:          // ..., .*, .1234
    return FirstChar == '.' || FirstChar == '*' || isdigit(FirstChar);
  case tok::amp:             // &&, &=
    return FirstChar == '&' || FirstChar == '=';
  case tok::plus:            // ++, +=
    return FirstChar == '+' || FirstChar == '=';
  case tok::minus:           // --, ->, -=, ->*
    return FirstChar == '-' || FirstChar == '>' || FirstChar == '=';
  case tok::slash:           // /=, /*, //
    return FirstChar == '=' || FirstChar == '*' || FirstChar == '/';
  case tok::less:            // <<, <<=, <=, <?=, <?, <:, <%
    return FirstChar == '<' || FirstChar == '?' || FirstChar == '=' ||
           FirstChar == ':' || FirstChar == '%';
  case tok::greater:         // >>, >=, >>=, >?=, >?
    return FirstChar == '>' || FirstChar == '?' || FirstChar == '=';
  case tok::pipe:            // ||, |=
    return FirstChar == '|' || FirstChar == '=';
  case tok::percent:         // %=, %>, %:
    return FirstChar == '=' || FirstChar == '>' || FirstChar == ':';
  case tok::colon:           // ::, :>
    return FirstChar == ':' || FirstChar == '>';
  case tok::hash:            // ##, #@, %:%:
    return FirstChar == '#' || FirstChar == '@' || FirstChar == '%';
  case tok::arrow:           // ->*
    return FirstChar == '*';

  case tok::star:            // *=
  case tok::exclaim:         // !=
  case tok::lessless:        // <<=
  case tok::greaterequal:    // >>=
  case tok::caret:           // ^=
  case tok::equal:           // ==
    // Cases that concatenate only if the next char is =.
    return FirstChar == '=';
  }
}

/// DoPrintPreprocessedInput - This implements -E mode.
///
void clang::DoPrintPreprocessedInput(unsigned MainFileID, Preprocessor &PP,
                                     const LangOptions &Options) {
  // Inform the preprocessor whether we want it to retain comments or not, due
  // to -C or -CC.
  PP.SetCommentRetentionState(EnableCommentOutput, EnableMacroCommentOutput);

  InitOutputBuffer();

  Token Tok, PrevTok;
  char Buffer[256];
  PrintPPOutputPPCallbacks *Callbacks = new PrintPPOutputPPCallbacks(PP);
  PP.setPPCallbacks(Callbacks);

  PP.AddPragmaHandler(0, new UnknownPragmaHandler("#pragma", Callbacks));
  PP.AddPragmaHandler("GCC", new UnknownPragmaHandler("#pragma GCC",Callbacks));

  // After we have configured the preprocessor, enter the main file.

  // Start parsing the specified input file.
  PP.EnterSourceFile(MainFileID, 0, true);

  do {
    PrevTok = Tok;
    PP.Lex(Tok);

    // If this token is at the start of a line, emit newlines if needed.
    if (Tok.isAtStartOfLine()) {
      Callbacks->HandleFirstTokOnLine(Tok);
    } else if (Tok.hasLeadingSpace() ||
               // Don't print "-" next to "-", it would form "--".
               Callbacks->AvoidConcat(PrevTok, Tok)) {
      OutputChar(' ');
    }

    if (Tok.getLength() < 256) {
      const char *TokPtr = Buffer;
      unsigned Len = PP.getSpelling(Tok, TokPtr);
      OutputString(TokPtr, Len);
    } else {
      std::string S = PP.getSpelling(Tok);
      OutputString(&S[0], S.size());
    }
    Callbacks->SetEmittedTokensOnThisLine();
  } while (Tok.getKind() != tok::eof);
  OutputChar('\n');

  CleanupOutputBuffer();
}

<commit_msg>A minor tweak to -E output, speeding up -E 1.5% on 447.dealII<commit_after>//===--- PrintPreprocessedOutput.cpp - Implement the -E mode --------------===//
//
//                     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 code simply runs the preprocessor on the input file and prints out the
// result.  This is the traditional behavior of the -E option.
//
//===----------------------------------------------------------------------===//

#include "clang.h"
#include "clang/Lex/PPCallbacks.h"
#include "clang/Lex/Preprocessor.h"
#include "clang/Lex/Pragma.h"
#include "clang/Basic/SourceManager.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/ADT/StringExtras.h"
#include "llvm/Config/config.h"
#include <cstdio>
using namespace clang;

//===----------------------------------------------------------------------===//
// Simple buffered I/O
//===----------------------------------------------------------------------===//
//
// Empirically, iostream is over 30% slower than stdio for this workload, and
// stdio itself isn't very well suited.  The problem with stdio is use of
// putchar_unlocked.  We have many newline characters that need to be emitted,
// but stdio needs to do extra checks to handle line buffering mode.  These
// extra checks make putchar_unlocked fall off its inlined code path, hitting
// slow system code.  In practice, using 'write' directly makes 'clang -E -P'
// about 10% faster than using the stdio path on darwin.

#ifdef HAVE_UNISTD_H
#include <unistd.h>
#else
#define USE_STDIO 1
#endif

static char *OutBufStart = 0, *OutBufEnd, *OutBufCur;

/// InitOutputBuffer - Initialize our output buffer.
///
static void InitOutputBuffer() {
#ifndef USE_STDIO
  OutBufStart = new char[64*1024];
  OutBufEnd = OutBufStart+64*1024;
  OutBufCur = OutBufStart;
#endif
}

/// FlushBuffer - Write the accumulated bytes to the output stream.
///
static void FlushBuffer() {
#ifndef USE_STDIO
  write(STDOUT_FILENO, OutBufStart, OutBufCur-OutBufStart);
  OutBufCur = OutBufStart;
#endif
}

/// CleanupOutputBuffer - Finish up output.
///
static void CleanupOutputBuffer() {
#ifndef USE_STDIO
  FlushBuffer();
  delete [] OutBufStart;
#endif
}

static void OutputChar(char c) {
#ifdef USE_STDIO
  putchar_unlocked(c);
#else
  if (OutBufCur >= OutBufEnd)
    FlushBuffer();
  *OutBufCur++ = c;
#endif
}

static void OutputString(const char *Ptr, unsigned Size) {
#ifdef USE_STDIO
  fwrite(Ptr, Size, 1, stdout);
#else
  if (OutBufCur+Size >= OutBufEnd)
    FlushBuffer();
  memcpy(OutBufCur, Ptr, Size);
  OutBufCur += Size;
#endif
}

//===----------------------------------------------------------------------===//
// Preprocessed token printer
//===----------------------------------------------------------------------===//

static llvm::cl::opt<bool>
DisableLineMarkers("P", llvm::cl::desc("Disable linemarker output in -E mode"));
static llvm::cl::opt<bool>
EnableCommentOutput("C", llvm::cl::desc("Enable comment output in -E mode"));
static llvm::cl::opt<bool>
EnableMacroCommentOutput("CC",
                         llvm::cl::desc("Enable comment output in -E mode, "
                                        "even from macro expansions"));

namespace {
class PrintPPOutputPPCallbacks : public PPCallbacks {
  Preprocessor &PP;
  unsigned CurLine;
  std::string CurFilename;
  bool EmittedTokensOnThisLine;
  DirectoryLookup::DirType FileType;
public:
  PrintPPOutputPPCallbacks(Preprocessor &pp) : PP(pp) {
    CurLine = 0;
    CurFilename = "<uninit>";
    EmittedTokensOnThisLine = false;
    FileType = DirectoryLookup::NormalHeaderDir;
  }

  void SetEmittedTokensOnThisLine() { EmittedTokensOnThisLine = true; }

  virtual void FileChanged(SourceLocation Loc, FileChangeReason Reason,
                           DirectoryLookup::DirType FileType);
  virtual void Ident(SourceLocation Loc, const std::string &str);

  void HandleFirstTokOnLine(Token &Tok);
  void MoveToLine(SourceLocation Loc);
  bool AvoidConcat(const Token &PrevTok, const Token &Tok);
};
}

/// MoveToLine - Move the output to the source line specified by the location
/// object.  We can do this by emitting some number of \n's, or be emitting a
/// #line directive.
void PrintPPOutputPPCallbacks::MoveToLine(SourceLocation Loc) {
  if (DisableLineMarkers) {
    if (EmittedTokensOnThisLine) {
      OutputChar('\n');
      EmittedTokensOnThisLine = false;
    }
    return;
  }

  unsigned LineNo = PP.getSourceManager().getLogicalLineNumber(Loc);

  // If this line is "close enough" to the original line, just print newlines,
  // otherwise print a #line directive.
  if (LineNo-CurLine < 8) {
    if (LineNo-CurLine == 1)
      OutputChar('\n');
    else {
      const char *NewLines = "\n\n\n\n\n\n\n\n";
      OutputString(NewLines, LineNo-CurLine);
      CurLine = LineNo;
    }
  } else {
    if (EmittedTokensOnThisLine) {
      OutputChar('\n');
      EmittedTokensOnThisLine = false;
    }

    CurLine = LineNo;

    OutputChar('#');
    OutputChar(' ');
    std::string Num = llvm::utostr_32(LineNo);
    OutputString(&Num[0], Num.size());
    OutputChar(' ');
    OutputChar('"');
    OutputString(&CurFilename[0], CurFilename.size());
    OutputChar('"');

    if (FileType == DirectoryLookup::SystemHeaderDir)
      OutputString(" 3", 2);
    else if (FileType == DirectoryLookup::ExternCSystemHeaderDir)
      OutputString(" 3 4", 4);
    OutputChar('\n');
  }
}

/// FileChanged - Whenever the preprocessor enters or exits a #include file
/// it invokes this handler.  Update our conception of the current source
/// position.
void PrintPPOutputPPCallbacks::FileChanged(SourceLocation Loc,
                                           FileChangeReason Reason,
                                           DirectoryLookup::DirType FileType) {
  if (DisableLineMarkers) return;

  // Unless we are exiting a #include, make sure to skip ahead to the line the
  // #include directive was at.
  SourceManager &SourceMgr = PP.getSourceManager();
  if (Reason == PPCallbacks::EnterFile) {
    MoveToLine(SourceMgr.getIncludeLoc(Loc));
  } else if (Reason == PPCallbacks::SystemHeaderPragma) {
    MoveToLine(Loc);

    // TODO GCC emits the # directive for this directive on the line AFTER the
    // directive and emits a bunch of spaces that aren't needed.  Emulate this
    // strange behavior.
  }

  Loc = SourceMgr.getLogicalLoc(Loc);
  CurLine = SourceMgr.getLineNumber(Loc);
  CurFilename = Lexer::Stringify(SourceMgr.getSourceName(Loc));
  FileType = FileType;

  if (EmittedTokensOnThisLine) {
    OutputChar('\n');
    EmittedTokensOnThisLine = false;
  }

  OutputChar('#');
  OutputChar(' ');
  std::string Num = llvm::utostr_32(CurLine);
  OutputString(&Num[0], Num.size());
  OutputChar(' ');
  OutputChar('"');
  OutputString(&CurFilename[0], CurFilename.size());
  OutputChar('"');

  switch (Reason) {
  case PPCallbacks::EnterFile:
    OutputString(" 1", 2);
    break;
  case PPCallbacks::ExitFile:
    OutputString(" 2", 2);
    break;
  case PPCallbacks::SystemHeaderPragma: break;
  case PPCallbacks::RenameFile: break;
  }

  if (FileType == DirectoryLookup::SystemHeaderDir)
    OutputString(" 3", 2);
  else if (FileType == DirectoryLookup::ExternCSystemHeaderDir)
    OutputString(" 3 4", 4);

  OutputChar('\n');
}

/// HandleIdent - Handle #ident directives when read by the preprocessor.
///
void PrintPPOutputPPCallbacks::Ident(SourceLocation Loc, const std::string &S) {
  MoveToLine(Loc);

  OutputString("#ident ", strlen("#ident "));
  OutputString(&S[0], S.size());
  EmittedTokensOnThisLine = true;
}

/// HandleFirstTokOnLine - When emitting a preprocessed file in -E mode, this
/// is called for the first token on each new line.
void PrintPPOutputPPCallbacks::HandleFirstTokOnLine(Token &Tok) {
  // Figure out what line we went to and insert the appropriate number of
  // newline characters.
  MoveToLine(Tok.getLocation());

  // Print out space characters so that the first token on a line is
  // indented for easy reading.
  const SourceManager &SourceMgr = PP.getSourceManager();
  unsigned ColNo = SourceMgr.getLogicalColumnNumber(Tok.getLocation());

  // This hack prevents stuff like:
  // #define HASH #
  // HASH define foo bar
  // From having the # character end up at column 1, which makes it so it
  // is not handled as a #define next time through the preprocessor if in
  // -fpreprocessed mode.
  if (ColNo <= 1 && Tok.getKind() == tok::hash)
    OutputChar(' ');

  // Otherwise, indent the appropriate number of spaces.
  for (; ColNo > 1; --ColNo)
    OutputChar(' ');
}

namespace {
struct UnknownPragmaHandler : public PragmaHandler {
  const char *Prefix;
  PrintPPOutputPPCallbacks *Callbacks;

  UnknownPragmaHandler(const char *prefix, PrintPPOutputPPCallbacks *callbacks)
    : PragmaHandler(0), Prefix(prefix), Callbacks(callbacks) {}
  virtual void HandlePragma(Preprocessor &PP, Token &PragmaTok) {
    // Figure out what line we went to and insert the appropriate number of
    // newline characters.
    Callbacks->MoveToLine(PragmaTok.getLocation());
    OutputString(Prefix, strlen(Prefix));

    // Read and print all of the pragma tokens.
    while (PragmaTok.getKind() != tok::eom) {
      if (PragmaTok.hasLeadingSpace())
        OutputChar(' ');
      std::string TokSpell = PP.getSpelling(PragmaTok);
      OutputString(&TokSpell[0], TokSpell.size());
      PP.LexUnexpandedToken(PragmaTok);
    }
    OutputChar('\n');
  }
};
} // end anonymous namespace

/// AvoidConcat - If printing PrevTok immediately followed by Tok would cause
/// the two individual tokens to be lexed as a single token, return true (which
/// causes a space to be printed between them).  This allows the output of -E
/// mode to be lexed to the same token stream as lexing the input directly
/// would.
///
/// This code must conservatively return true if it doesn't want to be 100%
/// accurate.  This will cause the output to include extra space characters, but
/// the resulting output won't have incorrect concatenations going on.  Examples
/// include "..", which we print with a space between, because we don't want to
/// track enough to tell "x.." from "...".
bool PrintPPOutputPPCallbacks::AvoidConcat(const Token &PrevTok,
                                           const Token &Tok) {
  char Buffer[256];

  // If we haven't emitted a token on this line yet, PrevTok isn't useful to
  // look at and no concatenation could happen anyway.
  if (!EmittedTokensOnThisLine)
    return false;

  // Basic algorithm: we look at the first character of the second token, and
  // determine whether it, if appended to the first token, would form (or would
  // contribute) to a larger token if concatenated.
  char FirstChar;
  if (IdentifierInfo *II = Tok.getIdentifierInfo()) {
    // Avoid spelling identifiers, the most common form of token.
    FirstChar = II->getName()[0];
  } else if (Tok.getLength() < 256) {
    const char *TokPtr = Buffer;
    PP.getSpelling(Tok, TokPtr);
    FirstChar = TokPtr[0];
  } else {
    FirstChar = PP.getSpelling(Tok)[0];
  }

  tok::TokenKind PrevKind = PrevTok.getKind();
  if (PrevTok.getIdentifierInfo())  // Language keyword or named operator.
    PrevKind = tok::identifier;

  switch (PrevKind) {
  default: return false;
  case tok::identifier:   // id+id or id+number or id+L"foo".
    return isalnum(FirstChar) || FirstChar == '_';
  case tok::numeric_constant:
    return isalnum(FirstChar) || Tok.getKind() == tok::numeric_constant ||
           FirstChar == '+' || FirstChar == '-' || FirstChar == '.';
  case tok::period:          // ..., .*, .1234
    return FirstChar == '.' || FirstChar == '*' || isdigit(FirstChar);
  case tok::amp:             // &&, &=
    return FirstChar == '&' || FirstChar == '=';
  case tok::plus:            // ++, +=
    return FirstChar == '+' || FirstChar == '=';
  case tok::minus:           // --, ->, -=, ->*
    return FirstChar == '-' || FirstChar == '>' || FirstChar == '=';
  case tok::slash:           // /=, /*, //
    return FirstChar == '=' || FirstChar == '*' || FirstChar == '/';
  case tok::less:            // <<, <<=, <=, <?=, <?, <:, <%
    return FirstChar == '<' || FirstChar == '?' || FirstChar == '=' ||
           FirstChar == ':' || FirstChar == '%';
  case tok::greater:         // >>, >=, >>=, >?=, >?
    return FirstChar == '>' || FirstChar == '?' || FirstChar == '=';
  case tok::pipe:            // ||, |=
    return FirstChar == '|' || FirstChar == '=';
  case tok::percent:         // %=, %>, %:
    return FirstChar == '=' || FirstChar == '>' || FirstChar == ':';
  case tok::colon:           // ::, :>
    return FirstChar == ':' || FirstChar == '>';
  case tok::hash:            // ##, #@, %:%:
    return FirstChar == '#' || FirstChar == '@' || FirstChar == '%';
  case tok::arrow:           // ->*
    return FirstChar == '*';

  case tok::star:            // *=
  case tok::exclaim:         // !=
  case tok::lessless:        // <<=
  case tok::greaterequal:    // >>=
  case tok::caret:           // ^=
  case tok::equal:           // ==
    // Cases that concatenate only if the next char is =.
    return FirstChar == '=';
  }
}

/// DoPrintPreprocessedInput - This implements -E mode.
///
void clang::DoPrintPreprocessedInput(unsigned MainFileID, Preprocessor &PP,
                                     const LangOptions &Options) {
  // Inform the preprocessor whether we want it to retain comments or not, due
  // to -C or -CC.
  PP.SetCommentRetentionState(EnableCommentOutput, EnableMacroCommentOutput);

  InitOutputBuffer();

  Token Tok, PrevTok;
  char Buffer[256];
  PrintPPOutputPPCallbacks *Callbacks = new PrintPPOutputPPCallbacks(PP);
  PP.setPPCallbacks(Callbacks);

  PP.AddPragmaHandler(0, new UnknownPragmaHandler("#pragma", Callbacks));
  PP.AddPragmaHandler("GCC", new UnknownPragmaHandler("#pragma GCC",Callbacks));

  // After we have configured the preprocessor, enter the main file.

  // Start parsing the specified input file.
  PP.EnterSourceFile(MainFileID, 0, true);

  do {
    PrevTok = Tok;
    PP.Lex(Tok);

    // If this token is at the start of a line, emit newlines if needed.
    if (Tok.isAtStartOfLine()) {
      Callbacks->HandleFirstTokOnLine(Tok);
    } else if (Tok.hasLeadingSpace() ||
               // Don't print "-" next to "-", it would form "--".
               Callbacks->AvoidConcat(PrevTok, Tok)) {
      OutputChar(' ');
    }

    if (Tok.getLength() < 256) {
      const char *TokPtr = Buffer;
      unsigned Len = PP.getSpelling(Tok, TokPtr);
      OutputString(TokPtr, Len);
    } else {
      std::string S = PP.getSpelling(Tok);
      OutputString(&S[0], S.size());
    }
    Callbacks->SetEmittedTokensOnThisLine();
  } while (Tok.getKind() != tok::eof);
  OutputChar('\n');

  CleanupOutputBuffer();
}

<|endoftext|>


<commit_before><commit_msg>gui: unregister timing cone if there are no cones selected<commit_after><|endoftext|>


<commit_before>// This file is part of the dune-gdt project:
//   http://users.dune-project.org/projects/dune-gdt
// Copyright holders: Felix Schindler
// License: BSD 2-Clause License (http://opensource.org/licenses/BSD-2-Clause)

#ifndef DUNE_GDT_ASSEMBLER_SYSTEM_HH
#define DUNE_GDT_ASSEMBLER_SYSTEM_HH

#include <type_traits>
#include <memory>

#include <dune/common/version.hh>

#if DUNE_VERSION_NEWER(DUNE_COMMON,3,9) //&& HAVE_TBB //EXADUNE
# include <dune/grid/utility/partitioning/seedlist.hh>
# include <dune/stuff/common/parallel/partitioner.hh>
#endif

#include <dune/stuff/grid/walker.hh>
#include <dune/stuff/common/parallel/helper.hh>

#include <dune/gdt/spaces/interface.hh>
#include <dune/gdt/spaces/constraints.hh>

#include "local/codim0.hh"
#include "local/codim1.hh"
#include "wrapper.hh"

namespace Dune {
namespace GDT {

template< class TestSpaceImp,
          class GridViewImp = typename TestSpaceImp::GridViewType,
          class AnsatzSpaceImp = TestSpaceImp >
class SystemAssembler
  : public DSG::Walker< GridViewImp >
{
  static_assert(std::is_base_of< SpaceInterface< typename TestSpaceImp::Traits >, TestSpaceImp >::value,
                "TestSpaceImp has to be derived from SpaceInterface!");
  static_assert(std::is_base_of< SpaceInterface< typename AnsatzSpaceImp::Traits >, AnsatzSpaceImp >::value,
                "AnsatzSpaceImp has to be derived from SpaceInterface!");
  static_assert(std::is_same< typename TestSpaceImp::RangeFieldType, typename AnsatzSpaceImp::RangeFieldType >::value,
                "Types do not match!");
  typedef DSG::Walker< GridViewImp >                                  BaseType;
  typedef SystemAssembler<TestSpaceImp, GridViewImp, AnsatzSpaceImp > ThisType;
public:
  typedef TestSpaceImp                           TestSpaceType;
  typedef AnsatzSpaceImp                         AnsatzSpaceType;
  typedef typename TestSpaceType::RangeFieldType RangeFieldType;

  typedef typename BaseType::GridViewType     GridViewType;
  typedef typename BaseType::EntityType       EntityType;
  typedef typename BaseType::IntersectionType IntersectionType;

  typedef DSG::ApplyOn::WhichEntity< GridViewType >       ApplyOnWhichEntity;
  typedef DSG::ApplyOn::WhichIntersection< GridViewType > ApplyOnWhichIntersection;

  SystemAssembler(TestSpaceType test, AnsatzSpaceType ansatz, GridViewType grid_view)
    : BaseType(grid_view)
    , test_space_(test)
    , ansatz_space_(ansatz)
  {}

  SystemAssembler(TestSpaceType test, AnsatzSpaceType ansatz)
    : BaseType(test.grid_view())
    , test_space_(test)
    , ansatz_space_(ansatz)
  {}

  explicit SystemAssembler(TestSpaceType test)
    : BaseType(test.grid_view())
    , test_space_(test)
    , ansatz_space_(test)
  {}

  SystemAssembler(TestSpaceType test, GridViewType grid_view)
    : BaseType(grid_view)
    , test_space_(test)
    , ansatz_space_(test_space_)
  {}

  const TestSpaceType& test_space() const
  {
    return *test_space_;
  }

  const AnsatzSpaceType& ansatz_space() const
  {
    return *ansatz_space_;
  }

  using BaseType::add;

  template< class C, class M >
  void add(Spaces::ConstraintsInterface< C, RangeFieldType >& constraints,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    assert(matrix.rows() == test_space_->mapper().size());
    assert(matrix.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalMatrixConstraintsWrapper< TestSpaceType,
                                                     AnsatzSpaceType,
                                                     GridViewType,
                                                     typename C::derived_type,
                                                     typename M::derived_type > WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_,
                                                        ansatz_space_,
                                                        where,
                                                        constraints.as_imp(),
                                                        matrix.as_imp()));
  } // ... add(...)

  /** \todo Investigate why the ConstraintsInterface is not used here! */
  template< class ConstraintsType, class V >
  void add(ConstraintsType& constraints,
           Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
           const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = vector.as_imp();
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalVectorConstraintsWrapper< ThisType, ConstraintsType, VectorType > WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_, where, constraints, vector_imp));
  } // ... add(...)

  template< class L, class M >
  void add(const LocalAssembler::Codim0Matrix< L >& local_assembler,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalVolumeMatrixAssemblerWrapper< ThisType, LocalAssembler::Codim0Matrix< L >, MatrixType >
        WrapperType;
    this->codim0_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class Codim0Assembler, class M >
  void add_codim0_assembler(const Codim0Assembler& local_assembler,
                            Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
                            const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalVolumeMatrixAssemblerWrapper< ThisType, Codim0Assembler, MatrixType > WrapperType;
    this->codim0_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class Codim0Assembler, class V >
  void add_codim0_assembler(const Codim0Assembler& local_assembler,
                            Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
                            const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = vector.as_imp();
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalVolumeVectorAssemblerWrapper< ThisType, Codim0Assembler, VectorType > WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_, where, local_assembler, vector_imp));
  } // ... add(...)

  template< class L, class M >
  void add(const LocalAssembler::Codim1CouplingMatrix< L >& local_assembler,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichIntersection* where
              = new DSG::ApplyOn::AllIntersections< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalFaceMatrixAssemblerWrapper< ThisType, LocalAssembler::Codim1CouplingMatrix< L >, MatrixType >
        WrapperType;
    this->codim1_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class L, class M >
  void add(const LocalAssembler::Codim1BoundaryMatrix< L >& local_assembler,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichIntersection* where
              = new DSG::ApplyOn::AllIntersections< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalFaceMatrixAssemblerWrapper< ThisType, LocalAssembler::Codim1BoundaryMatrix< L >, MatrixType >
        WrapperType;
    this->codim1_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class L, class V >
  void add(const LocalAssembler::Codim0Vector< L >& local_assembler,
           Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
           const ApplyOnWhichEntity* where
              = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = vector.as_imp();
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalVolumeVectorAssemblerWrapper< ThisType, LocalAssembler::Codim0Vector< L >, VectorType >
        WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_, where, local_assembler, vector_imp));
  } // ... add(...)

  template< class L, class V >
  void add(const LocalAssembler::Codim1Vector< L >& local_assembler,
           Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
           const ApplyOnWhichIntersection* where
              = new DSG::ApplyOn::AllIntersections< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = static_cast< VectorType& >(vector);
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalFaceVectorAssemblerWrapper< ThisType, LocalAssembler::Codim1Vector< L >, VectorType >
        WrapperType;
    this->codim1_functors_.emplace_back(new WrapperType(test_space_, where, local_assembler, vector_imp));
  } // ... add(...)

  void assemble(const bool use_tbb = false)
  {
#if DUNE_VERSION_NEWER(DUNE_COMMON,3,9) //EXADUNE
    if (use_tbb) {
      Stuff::IndexSetPartitioner< GridViewType > partitioner(this->grid_view_.indexSet());
      SeedListPartitioning< typename GridViewType::Grid, 0 > partitioning(this->grid_view_, partitioner);
      this->walk(partitioning);
    } else
#endif
    {
      const auto DUNE_UNUSED(no_warning_for_use_tbb) = use_tbb;
      this->walk();
    }
  }

private:
  const DS::PerThreadValue<const TestSpaceType> test_space_;
  const DS::PerThreadValue<const AnsatzSpaceType> ansatz_space_;
}; // class SystemAssembler

} // namespace GDT
} // namespace Dune

#endif // DUNE_GDT_ASSEMBLER_SYSTEM_HH
<commit_msg>[assembler] moves tbb stuff to walker completely<commit_after>// This file is part of the dune-gdt project:
//   http://users.dune-project.org/projects/dune-gdt
// Copyright holders: Felix Schindler
// License: BSD 2-Clause License (http://opensource.org/licenses/BSD-2-Clause)

#ifndef DUNE_GDT_ASSEMBLER_SYSTEM_HH
#define DUNE_GDT_ASSEMBLER_SYSTEM_HH

#include <type_traits>
#include <memory>

#include <dune/common/version.hh>

#include <dune/stuff/grid/walker.hh>
#include <dune/stuff/common/parallel/helper.hh>

#include <dune/gdt/spaces/interface.hh>
#include <dune/gdt/spaces/constraints.hh>

#include "local/codim0.hh"
#include "local/codim1.hh"
#include "wrapper.hh"

namespace Dune {
namespace GDT {

template< class TestSpaceImp,
          class GridViewImp = typename TestSpaceImp::GridViewType,
          class AnsatzSpaceImp = TestSpaceImp >
class SystemAssembler
  : public DSG::Walker< GridViewImp >
{
  static_assert(std::is_base_of< SpaceInterface< typename TestSpaceImp::Traits >, TestSpaceImp >::value,
                "TestSpaceImp has to be derived from SpaceInterface!");
  static_assert(std::is_base_of< SpaceInterface< typename AnsatzSpaceImp::Traits >, AnsatzSpaceImp >::value,
                "AnsatzSpaceImp has to be derived from SpaceInterface!");
  static_assert(std::is_same< typename TestSpaceImp::RangeFieldType, typename AnsatzSpaceImp::RangeFieldType >::value,
                "Types do not match!");
  typedef DSG::Walker< GridViewImp >                                  BaseType;
  typedef SystemAssembler<TestSpaceImp, GridViewImp, AnsatzSpaceImp > ThisType;
public:
  typedef TestSpaceImp                           TestSpaceType;
  typedef AnsatzSpaceImp                         AnsatzSpaceType;
  typedef typename TestSpaceType::RangeFieldType RangeFieldType;

  typedef typename BaseType::GridViewType     GridViewType;
  typedef typename BaseType::EntityType       EntityType;
  typedef typename BaseType::IntersectionType IntersectionType;

  typedef DSG::ApplyOn::WhichEntity< GridViewType >       ApplyOnWhichEntity;
  typedef DSG::ApplyOn::WhichIntersection< GridViewType > ApplyOnWhichIntersection;

  SystemAssembler(TestSpaceType test, AnsatzSpaceType ansatz, GridViewType grid_view)
    : BaseType(grid_view)
    , test_space_(test)
    , ansatz_space_(ansatz)
  {}

  SystemAssembler(TestSpaceType test, AnsatzSpaceType ansatz)
    : BaseType(test.grid_view())
    , test_space_(test)
    , ansatz_space_(ansatz)
  {}

  explicit SystemAssembler(TestSpaceType test)
    : BaseType(test.grid_view())
    , test_space_(test)
    , ansatz_space_(test)
  {}

  SystemAssembler(TestSpaceType test, GridViewType grid_view)
    : BaseType(grid_view)
    , test_space_(test)
    , ansatz_space_(test_space_)
  {}

  const TestSpaceType& test_space() const
  {
    return *test_space_;
  }

  const AnsatzSpaceType& ansatz_space() const
  {
    return *ansatz_space_;
  }

  using BaseType::add;

  template< class C, class M >
  void add(Spaces::ConstraintsInterface< C, RangeFieldType >& constraints,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    assert(matrix.rows() == test_space_->mapper().size());
    assert(matrix.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalMatrixConstraintsWrapper< TestSpaceType,
                                                     AnsatzSpaceType,
                                                     GridViewType,
                                                     typename C::derived_type,
                                                     typename M::derived_type > WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_,
                                                        ansatz_space_,
                                                        where,
                                                        constraints.as_imp(),
                                                        matrix.as_imp()));
  } // ... add(...)

  /** \todo Investigate why the ConstraintsInterface is not used here! */
  template< class ConstraintsType, class V >
  void add(ConstraintsType& constraints,
           Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
           const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = vector.as_imp();
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalVectorConstraintsWrapper< ThisType, ConstraintsType, VectorType > WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_, where, constraints, vector_imp));
  } // ... add(...)

  template< class L, class M >
  void add(const LocalAssembler::Codim0Matrix< L >& local_assembler,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalVolumeMatrixAssemblerWrapper< ThisType, LocalAssembler::Codim0Matrix< L >, MatrixType >
        WrapperType;
    this->codim0_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class Codim0Assembler, class M >
  void add_codim0_assembler(const Codim0Assembler& local_assembler,
                            Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
                            const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalVolumeMatrixAssemblerWrapper< ThisType, Codim0Assembler, MatrixType > WrapperType;
    this->codim0_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class Codim0Assembler, class V >
  void add_codim0_assembler(const Codim0Assembler& local_assembler,
                            Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
                            const ApplyOnWhichEntity* where = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = vector.as_imp();
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalVolumeVectorAssemblerWrapper< ThisType, Codim0Assembler, VectorType > WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_, where, local_assembler, vector_imp));
  } // ... add(...)

  template< class L, class M >
  void add(const LocalAssembler::Codim1CouplingMatrix< L >& local_assembler,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichIntersection* where
              = new DSG::ApplyOn::AllIntersections< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalFaceMatrixAssemblerWrapper< ThisType, LocalAssembler::Codim1CouplingMatrix< L >, MatrixType >
        WrapperType;
    this->codim1_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class L, class M >
  void add(const LocalAssembler::Codim1BoundaryMatrix< L >& local_assembler,
           Stuff::LA::MatrixInterface< M, RangeFieldType >& matrix,
           const ApplyOnWhichIntersection* where
              = new DSG::ApplyOn::AllIntersections< GridViewType >())
  {
    typedef typename M::derived_type MatrixType;
    MatrixType& matrix_imp = matrix.as_imp();
    assert(matrix_imp.rows() == test_space_->mapper().size());
    assert(matrix_imp.cols() == ansatz_space_->mapper().size());
    typedef internal::LocalFaceMatrixAssemblerWrapper< ThisType, LocalAssembler::Codim1BoundaryMatrix< L >, MatrixType >
        WrapperType;
    this->codim1_functors_.emplace_back(
          new WrapperType(test_space_, ansatz_space_, where, local_assembler, matrix_imp));
  } // ... add(...)

  template< class L, class V >
  void add(const LocalAssembler::Codim0Vector< L >& local_assembler,
           Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
           const ApplyOnWhichEntity* where
              = new DSG::ApplyOn::AllEntities< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = vector.as_imp();
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalVolumeVectorAssemblerWrapper< ThisType, LocalAssembler::Codim0Vector< L >, VectorType >
        WrapperType;
    this->codim0_functors_.emplace_back(new WrapperType(test_space_, where, local_assembler, vector_imp));
  } // ... add(...)

  template< class L, class V >
  void add(const LocalAssembler::Codim1Vector< L >& local_assembler,
           Stuff::LA::VectorInterface< V, RangeFieldType >& vector,
           const ApplyOnWhichIntersection* where
              = new DSG::ApplyOn::AllIntersections< GridViewType >())
  {
    typedef typename V::derived_type VectorType;
    VectorType& vector_imp = static_cast< VectorType& >(vector);
    assert(vector_imp.size() == test_space_->mapper().size());
    typedef internal::LocalFaceVectorAssemblerWrapper< ThisType, LocalAssembler::Codim1Vector< L >, VectorType >
        WrapperType;
    this->codim1_functors_.emplace_back(new WrapperType(test_space_, where, local_assembler, vector_imp));
  } // ... add(...)

  void assemble(const bool use_tbb = false)
  {
    this->walk(use_tbb);
  }

private:
  const DS::PerThreadValue<const TestSpaceType> test_space_;
  const DS::PerThreadValue<const AnsatzSpaceType> ansatz_space_;
}; // class SystemAssembler

} // namespace GDT
} // namespace Dune

#endif // DUNE_GDT_ASSEMBLER_SYSTEM_HH
<|endoftext|>


<commit_before>// This file is part of the dune-gdt project:
//   https://github.com/dune-community/dune-gdt
// Copyright 2010-2018 dune-gdt developers and contributors. All rights reserved.
// License: Dual licensed as BSD 2-Clause License (http://opensource.org/licenses/BSD-2-Clause)
//      or  GPL-2.0+ (http://opensource.org/licenses/gpl-license)
//          with "runtime exception" (http://www.dune-project.org/license.html)
// Authors:
//   Felix Schindler (2013 - 2017)
//   Rene Milk       (2014, 2016 - 2018)
//   Sven Kaulmann   (2014)
//   Tobias Leibner  (2014, 2016 - 2017)

#ifndef DUNE_GDT_SPACES_INTERFACE_HH
#define DUNE_GDT_SPACES_INTERFACE_HH

#include <dune/geometry/type.hh>

#include <dune/xt/la/container/vector-interface.hh>
#include <dune/xt/grid/type_traits.hh>

#include <dune/gdt/exceptions.hh>
#include <dune/gdt/local/finite-elements/interfaces.hh>
#include <dune/gdt/spaces/basis/interface.hh>
#include <dune/gdt/spaces/mapper/interfaces.hh>
#include <dune/gdt/spaces/parallel/communication.hh>
#include <dune/gdt/type_traits.hh>

namespace Dune {
namespace GDT {

// forward
template <class V, class GV, size_t r, size_t rC, class R>
class ConstDiscreteFunction;

template <class GridView, size_t range_dim = 1, size_t range_dim_columns = 1, class RangeField = double>
class SpaceInterface
{
  static_assert(XT::Grid::is_view<GridView>::value, "");

public:
  using GridViewType = GridView;
  using GV = GridViewType;
  using D = typename GridViewType::ctype;
  static const constexpr size_t d = GridViewType::dimension;
  using R = RangeField;
  static const constexpr size_t r = range_dim;
  static const constexpr size_t rC = range_dim_columns;

  using GlobalBasisType = GlobalBasisInterface<GridViewType, r, rC, R>;
  using MapperType = MapperInterface<GridViewType>;
  using FiniteElementType = LocalFiniteElementInterface<D, d, R, r, rC>;

  using DofCommunicatorType = typename DofCommunicationChooser<GridViewType>::Type;

  SpaceInterface()
    : dof_communicator_(nullptr)
  {
  }

  virtual ~SpaceInterface() = default;

  /// \name These methods provide the actual functionality, they have to be implemented.
  /// \{

  virtual const GridViewType& grid_view() const = 0;

  virtual const MapperType& mapper() const = 0;

  virtual const GlobalBasisType& basis() const = 0;

  virtual const FiniteElementType& finite_element(const GeometryType& geometry_type) const = 0;

  /// \}
  /// \name These methods help to identify the space, they have to be implemented.
  /// \{

  virtual SpaceType type() const = 0;

  virtual int min_polorder() const = 0;

  virtual int max_polorder() const = 0;

  /**
   * To query if elements of this space (functions) are continuous (i.e., in C^0), use `continuous(0)`.
   */
  virtual bool continuous(const int diff_order) const = 0;

  virtual bool continuous_normal_components() const = 0;

  /**
   * If this returns true, every finite_element() is expected to provide lagrange_points().
   */
  virtual bool is_lagrangian() const = 0;

  /// \}
  /// \name These methods are required for MPI communication, they are provided.
  /// \{

  virtual const DofCommunicatorType& dof_communicator() const
  {
    if (!dof_communicator_)
      DUNE_THROW(Exceptions::space_error,
                 "The actual space has to either implement its own dof_communicator() or call "
                 "create_communicator() in the ctor!");
    return *dof_communicator_;
  }

  /// \}
  /// \name These methods are provided for convenience.
  /// \{

  template <class V>
  bool contains(const XT::LA::VectorInterface<V>& vector) const
  {
    return vector.size() == this->mapper().size();
  }

  /**
   * \note A return value of true cannot be ultimately trusted yet.
   *
   * \sa https://github.com/dune-community/dune-gdt/issues/123
   */
  template <class V>
  bool contains(const ConstDiscreteFunction<V, GV, r, rC, R>& function) const
  {
    // this is the only case where we are sure^^
    if (&function.space() == this)
      return true;
    if (function.space().type() != this->type())
      return false;
    if (function.space().mapper().size() != this->mapper().size())
      return false;
    // the spaces might still differ (different grid views of same size), but we have no means to check this
    return true;
  }

  /// \}

protected:
  void create_communicator()
  {
    if (!dof_communicator_) {
      dof_communicator_ =
          std::shared_ptr<DofCommunicatorType>(DofCommunicationChooser<GridViewType>::create(grid_view()));
      DofCommunicationChooser<GridViewType>::prepare(*this, *dof_communicator_);
    }
  }

private:
  std::shared_ptr<DofCommunicatorType> dof_communicator_;
}; // class SpaceInterface

template <class GV, size_t r, size_t rC, class R>
std::ostream& operator<<(std::ostream& out, const SpaceInterface<GV, r, rC, R>& space)
{
  out << "Space(" << space.type() << ", " << space.mapper().size() << " DoFs)";
  return out;
}

} // namespace GDT
} // namespace Dune

#include <dune/gdt/discretefunction/default.hh>

#endif // DUNE_GDT_SPACES_INTERFACE_HH
<commit_msg>[spaces.interface] drop include which lead to circular includes<commit_after>// This file is part of the dune-gdt project:
//   https://github.com/dune-community/dune-gdt
// Copyright 2010-2018 dune-gdt developers and contributors. All rights reserved.
// License: Dual licensed as BSD 2-Clause License (http://opensource.org/licenses/BSD-2-Clause)
//      or  GPL-2.0+ (http://opensource.org/licenses/gpl-license)
//          with "runtime exception" (http://www.dune-project.org/license.html)
// Authors:
//   Felix Schindler (2013 - 2017)
//   Rene Milk       (2014, 2016 - 2018)
//   Sven Kaulmann   (2014)
//   Tobias Leibner  (2014, 2016 - 2017)

#ifndef DUNE_GDT_SPACES_INTERFACE_HH
#define DUNE_GDT_SPACES_INTERFACE_HH

#include <dune/geometry/type.hh>

#include <dune/xt/la/container/vector-interface.hh>
#include <dune/xt/grid/type_traits.hh>

#include <dune/gdt/exceptions.hh>
#include <dune/gdt/local/finite-elements/interfaces.hh>
#include <dune/gdt/spaces/basis/interface.hh>
#include <dune/gdt/spaces/mapper/interfaces.hh>
#include <dune/gdt/spaces/parallel/communication.hh>
#include <dune/gdt/type_traits.hh>

namespace Dune {
namespace GDT {

// forward
template <class V, class GV, size_t r, size_t rC, class R>
class ConstDiscreteFunction;

template <class GridView, size_t range_dim = 1, size_t range_dim_columns = 1, class RangeField = double>
class SpaceInterface
{
  static_assert(XT::Grid::is_view<GridView>::value, "");

public:
  using GridViewType = GridView;
  using GV = GridViewType;
  using D = typename GridViewType::ctype;
  static const constexpr size_t d = GridViewType::dimension;
  using R = RangeField;
  static const constexpr size_t r = range_dim;
  static const constexpr size_t rC = range_dim_columns;

  using GlobalBasisType = GlobalBasisInterface<GridViewType, r, rC, R>;
  using MapperType = MapperInterface<GridViewType>;
  using FiniteElementType = LocalFiniteElementInterface<D, d, R, r, rC>;

  using DofCommunicatorType = typename DofCommunicationChooser<GridViewType>::Type;

  SpaceInterface()
    : dof_communicator_(nullptr)
  {
  }

  virtual ~SpaceInterface() = default;

  /// \name These methods provide the actual functionality, they have to be implemented.
  /// \{

  virtual const GridViewType& grid_view() const = 0;

  virtual const MapperType& mapper() const = 0;

  virtual const GlobalBasisType& basis() const = 0;

  virtual const FiniteElementType& finite_element(const GeometryType& geometry_type) const = 0;

  /// \}
  /// \name These methods help to identify the space, they have to be implemented.
  /// \{

  virtual SpaceType type() const = 0;

  virtual int min_polorder() const = 0;

  virtual int max_polorder() const = 0;

  /**
   * To query if elements of this space (functions) are continuous (i.e., in C^0), use `continuous(0)`.
   */
  virtual bool continuous(const int diff_order) const = 0;

  virtual bool continuous_normal_components() const = 0;

  /**
   * If this returns true, every finite_element() is expected to provide lagrange_points().
   */
  virtual bool is_lagrangian() const = 0;

  /// \}
  /// \name These methods are required for MPI communication, they are provided.
  /// \{

  virtual const DofCommunicatorType& dof_communicator() const
  {
    if (!dof_communicator_)
      DUNE_THROW(Exceptions::space_error,
                 "The actual space has to either implement its own dof_communicator() or call "
                 "create_communicator() in the ctor!");
    return *dof_communicator_;
  }

  /// \}
  /// \name These methods are provided for convenience.
  /// \{

  template <class V>
  bool contains(const XT::LA::VectorInterface<V>& vector) const
  {
    return vector.size() == this->mapper().size();
  }

  /**
   * \note A return value of true cannot be ultimately trusted yet.
   *
   * \sa https://github.com/dune-community/dune-gdt/issues/123
   */
  template <class V>
  bool contains(const ConstDiscreteFunction<V, GV, r, rC, R>& function) const
  {
    // this is the only case where we are sure^^
    if (&function.space() == this)
      return true;
    if (function.space().type() != this->type())
      return false;
    if (function.space().mapper().size() != this->mapper().size())
      return false;
    // the spaces might still differ (different grid views of same size), but we have no means to check this
    return true;
  }

  /// \}

protected:
  void create_communicator()
  {
    if (!dof_communicator_) {
      dof_communicator_ =
          std::shared_ptr<DofCommunicatorType>(DofCommunicationChooser<GridViewType>::create(grid_view()));
      DofCommunicationChooser<GridViewType>::prepare(*this, *dof_communicator_);
    }
  }

private:
  std::shared_ptr<DofCommunicatorType> dof_communicator_;
}; // class SpaceInterface

template <class GV, size_t r, size_t rC, class R>
std::ostream& operator<<(std::ostream& out, const SpaceInterface<GV, r, rC, R>& space)
{
  out << "Space(" << space.type() << ", " << space.mapper().size() << " DoFs)";
  return out;
}

} // namespace GDT
} // namespace Dune

#endif // DUNE_GDT_SPACES_INTERFACE_HH
<|endoftext|>


<commit_before>/**************************************************************************
 * Copyright(c) 1998-2002, ALICE Experiment at CERN, All rights reserved. *
 *                                                                        *
 * Author: The ALICE Off-line Project.                                    *
 * Contributors are mentioned in the code where appropriate.              *
 *                                                                        *
 * Permission to use, copy, modify and distribute this software and its   *
 * documentation strictly for non-commercial purposes is hereby granted   *
 * without fee, provided that the above copyright notice appears in all   *
 * copies and that both the copyright notice and this permission notice   *
 * appear in the supporting documentation. The authors make no claims     *
 * about the suitability of this software for any purpose. It is          *
 * provided "as is" without express or implied warranty.                  *
 **************************************************************************/

/* $Id$ */

//
//
// Hadron correction base class
//
//
//
//

#include "AliEMCALHadronCorrection.h"

ClassImp(AliEMCALHadronCorrection)

AliEMCALHadronCorrection::AliEMCALHadronCorrection(const char *name,const char *title)
:TNamed(name,title) { }
<commit_msg>Reduced violations<commit_after>/**************************************************************************
 * Copyright(c) 1998-2002, ALICE Experiment at CERN, All rights reserved. *
 *                                                                        *
 * Author: The ALICE Off-line Project.                                    *
 * Contributors are mentioned in the code where appropriate.              *
 *                                                                        *
 * Permission to use, copy, modify and distribute this software and its   *
 * documentation strictly for non-commercial purposes is hereby granted   *
 * without fee, provided that the above copyright notice appears in all   *
 * copies and that both the copyright notice and this permission notice   *
 * appear in the supporting documentation. The authors make no claims     *
 * about the suitability of this software for any purpose. It is          *
 * provided "as is" without express or implied warranty.                  *
 **************************************************************************/

/* $Id$ */
//--
//--
//--  Hadron correction base class
//--
//--
//--

#include "AliEMCALHadronCorrection.h"

ClassImp(AliEMCALHadronCorrection)

AliEMCALHadronCorrection::AliEMCALHadronCorrection(const char *name,const char *title)
:TNamed(name,title) { }
<|endoftext|>


<commit_before>//-----------------------------------------------
//
//	This file is part of the Siv3D Engine.
//
//	Copyright (c) 2008-2019 Ryo Suzuki
//	Copyright (c) 2016-2019 OpenSiv3D Project
//
//	Licensed under the MIT License.
//
//-----------------------------------------------

# pragma once
# include "Types.hpp"

/// <summary>
/// ライブラリのバージョン表示
/// Version text
/// </summary>
# define SIV3D_VERSION	U"0.4.0"

namespace s3d
{
	/// <summary>
	/// バージョン ID
	/// Version value
	/// </summary>
	inline constexpr uint32 Siv3DVersion = 200'004'003u;
}
<commit_msg>start 0.4.1<commit_after>//-----------------------------------------------
//
//	This file is part of the Siv3D Engine.
//
//	Copyright (c) 2008-2019 Ryo Suzuki
//	Copyright (c) 2016-2019 OpenSiv3D Project
//
//	Licensed under the MIT License.
//
//-----------------------------------------------

# pragma once
# include "Types.hpp"

/// <summary>
/// ライブラリのバージョン表示
/// Version text
/// </summary>
# define SIV3D_VERSION	U"0.4.1dev"

namespace s3d
{
	/// <summary>
	/// バージョン ID
	/// Version value
	/// </summary>
	inline constexpr uint32 Siv3DVersion = 200'004'010u;
}
<|endoftext|>


<commit_before>#include <iostream>
#include <thread>
#include "DoryProcessSpawn.hpp"

using namespace std;
using namespace spawn;

void loop(uv_loop_t* uv_loop) {
  uv_timer_t timer;
  int r;

  r = uv_timer_init(uv_loop, &timer);
  ASSERT(r==0);

  // repeat every 1000 millisec to make the loop lives forever
  // later, it will be used as whatdog.
  r = uv_timer_start(&timer, [](uv_timer_t* timer){
    cout << "in timer" << endl;
  }, 0, 1000);
  ASSERT(r == 0);
  uv_run(uv_loop, UV_RUN_DEFAULT);
}

int main() {
  uv_loop_t* uv_loop = uv_default_loop();
  char* args[3];
  args[0] = (char*)"./child";
  args[1] = (char*)"200";
  args[2] = NULL;

  DoryProcessSpawn process(uv_loop, args);
  //process.timeout = 1000;
  int r = process.on("timeout", []() {
    cout << "timeout fired" << endl;
  })
  .on("stdout", [](char* buf, ssize_t nread) {
    for(int i=0;i<nread;i++)
      printf("%c", buf[i]);
  })
  .on("stderr", [](char* buf, ssize_t nread) {
    for(int i=0;i<nread;i++)
      printf("%c", buf[i]);
  })
  .on("exit", [](int64_t exitStatus, int termSignal) {
    cout << "exit code : " << exitStatus << endl;
    cout << "signal : " << termSignal << endl;
  })
  .spawn();

  // check the result of spawn()
  if (r != 0)
    cout << uv_err_name(r) << " " << uv_strerror(r) << endl;

  std::thread n(loop, uv_loop);
  n.join();

  return 0;
}<commit_msg>using random, and thread detach in example.<commit_after>#include <iostream>
#include <stdlib.h>
#include <time.h>
#include <thread>
#include <unistd.h>
#include "DoryProcessSpawn.hpp"

using namespace std;
using namespace spawn;

std::thread *n;
uv_loop_t* uv_loop = uv_default_loop();

void loop(uv_loop_t* uv_loop) {
  uv_timer_t timer;
  int r;

  r = uv_timer_init(uv_loop, &timer);
  ASSERT(r==0);

  // repeat every 1000 millisec to make the loop lives forever
  // later, it will be used as whatdog.
  r = uv_timer_start(&timer, [](uv_timer_t* timer){
    cout << "in timer" << endl;
  }, 0, 1000);
  ASSERT(r == 0);
  uv_run(uv_loop, UV_RUN_DEFAULT);
}

int main() {
  //init
  n = new std::thread(loop, uv_loop);
  n->detach();
  srand(time(NULL));

  int i=0;
  while(1) {
    i++;

    if (i > 10) {
      usleep(10*1000);
      continue;
    }
    char buf[10];
    sprintf(buf,"%i",rand()%10000);

    char* args[3];
    args[0] = (char*)"./child";
    args[1] = buf;  // (char*)"2000";
    args[2] = NULL;

    // FIXME : leak
    DoryProcessSpawn *process = new DoryProcessSpawn(uv_loop, args);
    //process.timeout = 1000;
    int r = process->on("timeout", []() {
      cout << "timeout fired" << endl;
    })
    .on("stdout", [](char* buf, ssize_t nread) {
      for(int i=0;i<nread;i++)
        printf("%c", buf[i]);
    })
    .on("stderr", [](char* buf, ssize_t nread) {
      for(int i=0;i<nread;i++)
        printf("%c", buf[i]);
    })
    .on("exit", [](int64_t exitStatus, int termSignal) {
      cout << "exit code : " << exitStatus << endl;
      cout << "signal : " << termSignal << endl;
    })
    .spawn();

    // check the result of spawn()
    if (r != 0)
      cout << uv_err_name(r) << " " << uv_strerror(r) << endl;
  }

  return 0;
}<|endoftext|>


<commit_before>/*
The OpenTRV project licenses this file to you
under the Apache Licence, Version 2.0 (the "Licence");
you may not use this file except in compliance
with the Licence. You may obtain a copy of the Licence at

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

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

Author(s) / Copyright (s): Damon Hart-Davis 2016
*/

/*
 * OTRadValve TempControl tests.
 */

#include <gtest/gtest.h>

#include "OTSIM900Link.h"

// Test for general sanity of OTSIM900Link.
// In particular, simulate some nominal REV7/DORM1/TRV1 numbers.
TEST(OTSIM900Link,basics)
{
    class NULLSerialStream final : public Stream
      {
      public:
        void begin(unsigned long) { }
        void begin(unsigned long, uint8_t);
        void end();

        virtual size_t write(uint8_t) override { return(0); }
        virtual int available() override { return(-1); }
        virtual int read() override { return(-1); }
        virtual int peek() override { return(-1); }
        virtual void flush() override { }
      };
    OTSIM900Link::OTSIM900Link<0, 0, 0, NULLSerialStream> l0;
    EXPECT_TRUE(l0.begin());
    // Try to hang just by calling poll() repeatedly.
    for(int i = 0; i < 1000; ++i) { l0.poll(); }
    // ...
    l0.end();
}

<commit_msg>TODO-1029: trying to set up SIM900 test harness<commit_after>/*
The OpenTRV project licenses this file to you
under the Apache Licence, Version 2.0 (the "Licence");
you may not use this file except in compliance
with the Licence. You may obtain a copy of the Licence at

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

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

Author(s) / Copyright (s): Damon Hart-Davis 2016
*/

/*
 * OTRadValve TempControl tests.
 */

#include <gtest/gtest.h>

#include "OTSIM900Link.h"

// Test for general sanity of OTSIM900Link.
// Make sure than an instance can be created and does not die horribly.
TEST(OTSIM900Link,basics)
{
    class NULLSerialStream final : public Stream
      {
      public:
        void begin(unsigned long) { }
        void begin(unsigned long, uint8_t);
        void end();

        virtual size_t write(uint8_t) override { return(0); }
        virtual int available() override { return(-1); }
        virtual int read() override { return(-1); }
        virtual int peek() override { return(-1); }
        virtual void flush() override { }
      };
    OTSIM900Link::OTSIM900Link<0, 0, 0, NULLSerialStream> l0;
    EXPECT_TRUE(l0.begin());
    // Try to hang just by calling poll() repeatedly.
    for(int i = 0; i < 1000; ++i) { l0.poll(); }
    // ...
    l0.end();
}

<|endoftext|>


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

  Program:   ORFEO Toolbox
  Language:  C++
  Date:      $Date$
  Version:   $Revision$

  Copyright (c) Centre National d'Etudes Spatiales. All rights reserved.
  See OTBCopyright.txt 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 notices for more information.

=========================================================================*/
#include "otbWrapperApplication.h"
#include "otbWrapperApplicationFactory.h"

#include "itkVariableLengthVector.h"
#include "otbChangeLabelImageFilter.h"
#include "otbStandardWriterWatcher.h"
#include "otbStatisticsXMLFileReader.h"
#include "otbShiftScaleVectorImageFilter.h"
#include "otbSVMImageClassificationFilter.h"
#include "otbMultiToMonoChannelExtractROI.h"
#include "otbImageToVectorImageCastFilter.h"

namespace otb
{
namespace Wrapper
{

class ImageSVMClassifier : public Application
{
public:
  /** Standard class typedefs. */
  typedef ImageSVMClassifier            Self;
  typedef Application                   Superclass;
  typedef itk::SmartPointer<Self>       Pointer;
  typedef itk::SmartPointer<const Self> ConstPointer;

  /** Standard macro */
  itkNewMacro(Self);

  itkTypeMacro(ImageSVMClassifier, otb::Application);

  /** Filters typedef */
  typedef itk::VariableLengthVector<FloatVectorImageType::InternalPixelType>            MeasurementType;
  typedef otb::StatisticsXMLFileReader<MeasurementType>                                 StatisticsReader;
  typedef otb::ShiftScaleVectorImageFilter<FloatVectorImageType, FloatVectorImageType>  RescalerType;
  typedef otb::SVMImageClassificationFilter<FloatVectorImageType, UInt8ImageType>       ClassificationFilterType;
  typedef ClassificationFilterType::Pointer                                             ClassificationFilterPointerType;
  typedef ClassificationFilterType::ModelType                                           ModelType;
  typedef ModelType::Pointer                                                            ModelPointerType;

private:
  ImageSVMClassifier()
  {
    SetName("ImageSVMClassifier");
    SetDescription("Perform SVM classification based on a previous computed SVM model");

    // Documentation
    SetDocName("Image SVM Classifier Application");
    SetDocLongDescription("This application performs an image classification based on the SVM classifier. The image to classify and the SVM model are given in input, the application will generate the classified output image. Optionnally, the user can give an image statistics file (that contains min, max) to normalize the input image before the classification. Furthemore, the user can give a mask to define area of work (only pixel with value greater to 0 will be porceed), this no classify pixels will appear in the output image with the value 0.");
    SetDocLimitations("None");
    SetDocAuthors("OTB-Team");
    SetDocSeeAlso("TrainSVMImagesClassifier application, ValidateSVMImagesClassifier");
    SetDocCLExample("otbApplicationLauncherCommandLine ImageSVMClassifier ${OTB-BIN}/bin --in ${OTB-DATA}/Classification/QB_1_ortho.tif  --imstat ${OTB-DATA}/Baseline/OTB-Applications/Files/clImageStatisticsQB1.xml --svn ${OTB-DATA}/Baseline/OTB-Applications/Files/clsvmModelQB1.svm --out otbConcatenateImages.png uchar");
    AddDocTag("Classification");
    AddDocTag("SVM");

  }

  virtual ~ImageSVMClassifier()
  {
  }

  void DoCreateParameters()
  {
    AddParameter(ParameterType_InputImage, "in",  "Input Image to classify");
    SetParameterDescription( "in", "Input Image to classify");

    AddParameter(ParameterType_InputImage,  "mask",   "Input Mask to classify");
    SetParameterDescription( "mask", "A mask associated with the new image to classify");
    MandatoryOff("mask");

    AddParameter(ParameterType_Filename, "imstat", "Image statistics file.");
    SetParameterDescription("imstat", "a XML file containing mean and standard deviation of input images used to train svm model");
    MandatoryOff("imstat");

    AddParameter(ParameterType_Filename, "svm", "SVM Model.");
    SetParameterDescription("svm", "An estimated SVM model previously computed");

    AddParameter(ParameterType_OutputImage, "out",  "Output Image");
    SetParameterDescription( "out", "Output labeled image");
    SetParameterOutputImagePixelType( "out", ImagePixelType_uint8);
  }

  void DoUpdateParameters()
  {
    // Nothing to do here : all parameters are independent
  }

  void DoExecute()
  {
    // Load input image
    FloatVectorImageType::Pointer inImage = GetParameterImage("in");
    inImage->UpdateOutputInformation();

    // Load svm model
    otbAppLogINFO("Loading SVM model");
    m_ModelSVM = ModelType::New();
    m_ModelSVM->LoadModel(GetParameterString("svm").c_str());
    otbAppLogINFO("SVM model loaded");

    // Normalize input image (optional)
    StatisticsReader::Pointer  statisticsReader = StatisticsReader::New();
    MeasurementType  meanMeasurementVector;
    MeasurementType  stddevMeasurementVector;
    m_Rescaler = RescalerType::New();

    // Classify
    m_ClassificationFilter = ClassificationFilterType::New();
    m_ClassificationFilter->SetModel(m_ModelSVM);

    // Normalize input image if asked
    if( HasValue("imstat")  )
      {
      otbAppLogINFO("Input image normalization activated.");
      // Load input image statistics
      statisticsReader->SetFileName(GetParameterString("imstat"));
      meanMeasurementVector   = statisticsReader->GetStatisticVectorByName("mean");
      stddevMeasurementVector = statisticsReader->GetStatisticVectorByName("stddev");
      otbAppLogINFO( "mean used: " << meanMeasurementVector );
      otbAppLogINFO( "standard deviation used: " << stddevMeasurementVector );
      // Rescale vector image
      m_Rescaler->SetScale(stddevMeasurementVector);
      m_Rescaler->SetShift(meanMeasurementVector);
      m_Rescaler->SetInput(inImage);

      m_ClassificationFilter->SetInput(m_Rescaler->GetOutput());
      }
    else
      {
      otbAppLogINFO("Input image normalization deactivated.");
      m_ClassificationFilter->SetInput(inImage);
      }

    if( HasValue("mask")  )
      {
      otbAppLogINFO("Using input mask");
      // Load mask image and cast into LabeledImageType
      UInt8ImageType::Pointer inMask = GetParameterUInt8Image("mask");

      m_ClassificationFilter->SetInputMask(inMask);
      }

    SetParameterOutputImage<UInt8ImageType>("out", m_ClassificationFilter->GetOutput());
  }

  ClassificationFilterType::Pointer m_ClassificationFilter;
  ModelPointerType m_ModelSVM;
  RescalerType::Pointer m_Rescaler;
};

}
}

OTB_APPLICATION_EXPORT(otb::Wrapper::ImageSVMClassifier)
<commit_msg>DOC:  Images SVM Classifier Doc update.<commit_after>/*=========================================================================

  Program:   ORFEO Toolbox
  Language:  C++
  Date:      $Date$
  Version:   $Revision$

  Copyright (c) Centre National d'Etudes Spatiales. All rights reserved.
  See OTBCopyright.txt 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 notices for more information.

=========================================================================*/
#include "otbWrapperApplication.h"
#include "otbWrapperApplicationFactory.h"

#include "itkVariableLengthVector.h"
#include "otbChangeLabelImageFilter.h"
#include "otbStandardWriterWatcher.h"
#include "otbStatisticsXMLFileReader.h"
#include "otbShiftScaleVectorImageFilter.h"
#include "otbSVMImageClassificationFilter.h"
#include "otbMultiToMonoChannelExtractROI.h"
#include "otbImageToVectorImageCastFilter.h"

namespace otb
{
namespace Wrapper
{

class ImageSVMClassifier : public Application
{
public:
  /** Standard class typedefs. */
  typedef ImageSVMClassifier            Self;
  typedef Application                   Superclass;
  typedef itk::SmartPointer<Self>       Pointer;
  typedef itk::SmartPointer<const Self> ConstPointer;

  /** Standard macro */
  itkNewMacro(Self);

  itkTypeMacro(ImageSVMClassifier, otb::Application);

  /** Filters typedef */
  typedef itk::VariableLengthVector<FloatVectorImageType::InternalPixelType>            MeasurementType;
  typedef otb::StatisticsXMLFileReader<MeasurementType>                                 StatisticsReader;
  typedef otb::ShiftScaleVectorImageFilter<FloatVectorImageType, FloatVectorImageType>  RescalerType;
  typedef otb::SVMImageClassificationFilter<FloatVectorImageType, UInt8ImageType>       ClassificationFilterType;
  typedef ClassificationFilterType::Pointer                                             ClassificationFilterPointerType;
  typedef ClassificationFilterType::ModelType                                           ModelType;
  typedef ModelType::Pointer                                                            ModelPointerType;

private:
  ImageSVMClassifier()
  {
    SetName("ImageSVMClassifier");
    SetDescription("Perform SVM classification based on a previous computed SVM model");

    // Documentation
    SetDocName("Image SVM Classifier Application");
    SetDocLongDescription("This application performs an image classification based on the SVM classifier."
        "The image to classify and the SVM model are given in input, the application will generate the classified output image. "
        " Optionally, the user can give an image statistics file (that contains min, max) to normalize the input image before the classification."
        " Furthemore, the user can give a mask to define area of work (only pixels with values greater to 0 will be proceed), "
        "these no classify pixels will appear in the output image with the value 0.");
    SetDocLimitations("None");
    SetDocAuthors("OTB-Team");
    SetDocSeeAlso("TrainSVMImagesClassifier, ValidateSVMImagesClassifier, EstimatesImagesStatistics");
    SetDocCLExample("otbApplicationLauncherCommandLine ImageSVMClassifier ${OTB-BIN}/bin --in ${OTB-DATA}/Classification/QB_1_ortho.tif  --imstat ${OTB-DATA}/Baseline/OTB-Applications/Files/clImageStatisticsQB1.xml --svn ${OTB-DATA}/Baseline/OTB-Applications/Files/clsvmModelQB1.svm --out otbConcatenateImages.png uchar");
    AddDocTag("Classification");
    AddDocTag("SVM");

  }

  virtual ~ImageSVMClassifier()
  {
  }

  void DoCreateParameters()
  {
    AddParameter(ParameterType_InputImage, "in",  "Input Image to classify");
    SetParameterDescription( "in", "Input Image to classify");

    AddParameter(ParameterType_InputImage,  "mask",   "Input Mask to classify");
    SetParameterDescription( "mask", "A mask associated with the new image to classify");
    MandatoryOff("mask");

    AddParameter(ParameterType_Filename, "imstat", "Image statistics file.");
    SetParameterDescription("imstat", "a XML file containing mean and standard deviation of input images used to train svm model");
    MandatoryOff("imstat");

    AddParameter(ParameterType_Filename, "svm", "SVM Model.");
    SetParameterDescription("svm", "An estimated SVM model previously computed");

    AddParameter(ParameterType_OutputImage, "out",  "Output Image");
    SetParameterDescription( "out", "Output labeled image");
    SetParameterOutputImagePixelType( "out", ImagePixelType_uint8);
  }

  void DoUpdateParameters()
  {
    // Nothing to do here : all parameters are independent
  }

  void DoExecute()
  {
    // Load input image
    FloatVectorImageType::Pointer inImage = GetParameterImage("in");
    inImage->UpdateOutputInformation();

    // Load svm model
    otbAppLogINFO("Loading SVM model");
    m_ModelSVM = ModelType::New();
    m_ModelSVM->LoadModel(GetParameterString("svm").c_str());
    otbAppLogINFO("SVM model loaded");

    // Normalize input image (optional)
    StatisticsReader::Pointer  statisticsReader = StatisticsReader::New();
    MeasurementType  meanMeasurementVector;
    MeasurementType  stddevMeasurementVector;
    m_Rescaler = RescalerType::New();

    // Classify
    m_ClassificationFilter = ClassificationFilterType::New();
    m_ClassificationFilter->SetModel(m_ModelSVM);

    // Normalize input image if asked
    if( HasValue("imstat")  )
      {
      otbAppLogINFO("Input image normalization activated.");
      // Load input image statistics
      statisticsReader->SetFileName(GetParameterString("imstat"));
      meanMeasurementVector   = statisticsReader->GetStatisticVectorByName("mean");
      stddevMeasurementVector = statisticsReader->GetStatisticVectorByName("stddev");
      otbAppLogINFO( "mean used: " << meanMeasurementVector );
      otbAppLogINFO( "standard deviation used: " << stddevMeasurementVector );
      // Rescale vector image
      m_Rescaler->SetScale(stddevMeasurementVector);
      m_Rescaler->SetShift(meanMeasurementVector);
      m_Rescaler->SetInput(inImage);

      m_ClassificationFilter->SetInput(m_Rescaler->GetOutput());
      }
    else
      {
      otbAppLogINFO("Input image normalization deactivated.");
      m_ClassificationFilter->SetInput(inImage);
      }

    if( HasValue("mask")  )
      {
      otbAppLogINFO("Using input mask");
      // Load mask image and cast into LabeledImageType
      UInt8ImageType::Pointer inMask = GetParameterUInt8Image("mask");

      m_ClassificationFilter->SetInputMask(inMask);
      }

    SetParameterOutputImage<UInt8ImageType>("out", m_ClassificationFilter->GetOutput());
  }

  ClassificationFilterType::Pointer m_ClassificationFilter;
  ModelPointerType m_ModelSVM;
  RescalerType::Pointer m_Rescaler;
};

}
}

OTB_APPLICATION_EXPORT(otb::Wrapper::ImageSVMClassifier)
<|endoftext|>


<commit_before>#include "OniFrameManager.h"
#include <XnOSCpp.h>

ONI_NAMESPACE_IMPLEMENTATION_BEGIN

FrameManager::FrameManager()
{
}

FrameManager::~FrameManager()
{
}

OniFrameInternal* FrameManager::acquireFrame()
{
	OniFrameInternal* pFrame = m_frames.Acquire();
    xnOSMemSet(pFrame, 0, sizeof(OniFrameInternal);
	pFrame->refCount = 1;
	return pFrame;
}

void FrameManager::addRef(OniFrame* pFrame)
{
	OniFrameInternal* pInternal = (OniFrameInternal*)pFrame;
	m_frames.Lock();
	++pInternal->refCount;
	m_frames.Unlock();
}

void FrameManager::release(OniFrame* pFrame)
{
	OniFrameInternal* pInternal = (OniFrameInternal*)pFrame;
	m_frames.Lock();
	if (--pInternal->refCount == 0)
	{
		// notify frame is back to pool
        if (pInternal->backToPoolFunc != NULL)
        {
            pInternal->backToPoolFunc(pInternal, pInternal->backToPoolFuncCookie);
        }

		// and return frame to pool
		m_frames.Release(pInternal);
	}
	m_frames.Unlock();
}

ONI_NAMESPACE_IMPLEMENTATION_END
<commit_msg>Fixed typo.<commit_after>#include "OniFrameManager.h"
#include <XnOSCpp.h>

ONI_NAMESPACE_IMPLEMENTATION_BEGIN

FrameManager::FrameManager()
{
}

FrameManager::~FrameManager()
{
}

OniFrameInternal* FrameManager::acquireFrame()
{
	OniFrameInternal* pFrame = m_frames.Acquire();
    xnOSMemSet(pFrame, 0, sizeof(OniFrameInternal));
	pFrame->refCount = 1;
	return pFrame;
}

void FrameManager::addRef(OniFrame* pFrame)
{
	OniFrameInternal* pInternal = (OniFrameInternal*)pFrame;
	m_frames.Lock();
	++pInternal->refCount;
	m_frames.Unlock();
}

void FrameManager::release(OniFrame* pFrame)
{
	OniFrameInternal* pInternal = (OniFrameInternal*)pFrame;
	m_frames.Lock();
	if (--pInternal->refCount == 0)
	{
		// notify frame is back to pool
        if (pInternal->backToPoolFunc != NULL)
        {
            pInternal->backToPoolFunc(pInternal, pInternal->backToPoolFuncCookie);
        }

		// and return frame to pool
		m_frames.Release(pInternal);
	}
	m_frames.Unlock();
}

ONI_NAMESPACE_IMPLEMENTATION_END
<|endoftext|>