<commit_before>/*
    Copyright 2008 Brain Research Institute, Melbourne, Australia

    Written by David Raffelt, 06/07/11.

    This file is part of MRtrix.

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

    MRtrix 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 General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with MRtrix.  If not, see <http://www.gnu.org/licenses/>.
*/

#include "app.h"
#include "math/SH.h"
#include "progressbar.h"
#include "thread/exec.h"
#include "thread/queue.h"
#include "dataset/loop.h"
#include "image/voxel.h"
#include "dwi/gradient.h"

using namespace MR;
using namespace App;

MRTRIX_APPLICATION

void usage ()
{
  AUTHOR = "David Raffelt (d.raffelt@brain.org.au)";

  DESCRIPTION
  + "Evaluate the amplitude of an image of spherical harmonic functions "
    "along the specified directions";

  ARGUMENTS
    + Argument ("input",
                "the input image consisting of spherical harmonic (SH) "
                "coefficients.").type_image_in ()
    + Argument ("directions",
                "the list of directions along which the SH functions will "
                "be sampled, generated using the gendir command").type_file ()
    + Argument ("output",
                "the output image consisting of the amplitude of the SH "
                "functions along the specified directions.").type_image_out ();

  OPTIONS
    + Option ("gradient",
              "assume input directions are supplied as a gradient encoding file"),
    + Option ("nonnegative",
              "cap all negative amplitudes to zero");
}

typedef float value_type;

class Item {
  public:
    Math::Vector<value_type> data;
    ssize_t pos[3];
};

class ItemAllocator {
  public:
    ItemAllocator (size_t data_size) : N (data_size) { }
    Item* alloc () { Item* item = new Item; item->data.allocate (N); return (item); }
    void reset (Item* item) { }
    void dealloc (Item* item) { delete item; }
  private:
    size_t N;
};

typedef Thread::Queue<Item,ItemAllocator> Queue;

class DataLoader {
  public:
  DataLoader (Queue& queue,
              Image::Header& header) :
              writer (queue), sh_voxel (header) { }

    void execute () {
      Queue::Writer::Item item (writer);

      DataSet::Loop outer ("computing amplitudes...", 0, 3 );
      for (outer.start (sh_voxel); outer.ok(); outer.next (sh_voxel)) {
        item->pos[0] = sh_voxel[0];
        item->pos[1] = sh_voxel[1];
        item->pos[2] = sh_voxel[2];
        DataSet::Loop inner (3);
        unsigned int c = 0;
        for (inner.start (sh_voxel); inner.ok(); inner.next (sh_voxel))
          item->data[c++] = sh_voxel.value();
        if (!item.write()) throw Exception ("error writing to work queue");
      }
    }

  private:
    Queue::Writer writer;
    Image::Voxel<value_type>  sh_voxel;
};

class Processor {
  public:
    Processor (Queue& queue,
               Image::Header& header,
               Math::Matrix<value_type>& directions,
               int lmax,
               bool nonnegative) :
               reader (queue),
               amp_voxel (header),
               transformer (directions, lmax),
               nonnegative (nonnegative) { }

    void execute () {
      Queue::Reader::Item item (reader);

      while ((item.read())) {
        Math::Vector<value_type> amplitudes;
        transformer.SH2A(amplitudes, item->data);

        amp_voxel[0] = item->pos[0];
        amp_voxel[1] = item->pos[1];
        amp_voxel[2] = item->pos[2];
        for (amp_voxel[3] = 0; amp_voxel[3] < amp_voxel.dim(3); ++amp_voxel[3]) {
          if (nonnegative && amplitudes[amp_voxel[3]] < 0)
            amplitudes[amp_voxel[3]] = 0.0;
          amp_voxel.value() = amplitudes[amp_voxel[3]];
        }
      }
    }

 private:
   Queue::Reader reader;
   Image::Voxel<value_type> amp_voxel;
   Math::SH::Transform<value_type> transformer;
   bool nonnegative;
};

void run ()
{
  Image::Header sh_header(argument[0]);
  assert (!sh_header.is_complex());

  if (sh_header.ndim() != 4)
    throw Exception ("The input spherical harmonic image should contain 4 dimensions");

  Image::Header amp_header (sh_header);

  Math::Matrix<value_type> dirs;
  bool gradients = get_options("gradient").size();

  if (gradients) {
    Math::Matrix<value_type> grad;
    grad.load (argument[1]);
    std::vector<int> bzeros, dwis;
    DWI::guess_DW_directions (dwis, bzeros, grad);
    DWI::gen_direction_matrix(dirs, grad, dwis);

    Math::Matrix<value_type> grad_dwis(dwis.size(), 4);
    for (unsigned int i = 0; i < dwis.size(); i++){
      grad_dwis(i,0) = grad(dwis[i],0);
      grad_dwis(i,1) = grad(dwis[i],1);
      grad_dwis(i,2) = grad(dwis[i],2);
      grad_dwis(i,3) = grad(dwis[i],3);
    }
    amp_header.set_DW_scheme(grad_dwis);
  } else {
    dirs.load(argument[1]);
  }
  amp_header.set_dim(3, dirs.rows());
  amp_header.set_stride (0, 2);
  amp_header.set_stride (1, 3);
  amp_header.set_stride (2, 4);
  amp_header.set_stride (3, 1);
  amp_header.create(argument[2]);

  Queue queue ("sh2amp queue", 100, ItemAllocator (sh_header.dim(3)));
  DataLoader loader (queue, sh_header);
  Processor processor (queue, amp_header, dirs, Math::SH::LforN(sh_header.dim(3)), get_options("nonnegative").size());

  Thread::Exec loader_thread (loader, "loader");
  Thread::Array<Processor> processor_list (processor);
  Thread::Exec processor_threads (processor_list, "processor");
}
<commit_msg>Added option in SH2amp to clamp all negative amplitudes to zero.<commit_after>/*
    Copyright 2008 Brain Research Institute, Melbourne, Australia

    Written by David Raffelt, 06/07/11.

    This file is part of MRtrix.

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

    MRtrix 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 General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with MRtrix.  If not, see <http://www.gnu.org/licenses/>.
*/

#include "app.h"
#include "math/SH.h"
#include "progressbar.h"
#include "thread/exec.h"
#include "thread/queue.h"
#include "dataset/loop.h"
#include "image/voxel.h"
#include "dwi/gradient.h"

using namespace MR;
using namespace App;

MRTRIX_APPLICATION

void usage ()
{
  AUTHOR = "David Raffelt (d.raffelt@brain.org.au)";

  DESCRIPTION
  + "Evaluate the amplitude of an image of spherical harmonic functions "
    "along the specified directions";

  ARGUMENTS
    + Argument ("input",
                "the input image consisting of spherical harmonic (SH) "
                "coefficients.").type_image_in ()
    + Argument ("directions",
                "the list of directions along which the SH functions will "
                "be sampled, generated using the gendir command").type_file ()
    + Argument ("output",
                "the output image consisting of the amplitude of the SH "
                "functions along the specified directions.").type_image_out ();

  OPTIONS
    + Option ("gradient",
              "assume input directions are supplied as a gradient encoding file")
    + Option ("nonnegative",
              "cap all negative amplitudes to zero");
}

typedef float value_type;

class Item {
  public:
    Math::Vector<value_type> data;
    ssize_t pos[3];
};

class ItemAllocator {
  public:
    ItemAllocator (size_t data_size) : N (data_size) { }
    Item* alloc () { Item* item = new Item; item->data.allocate (N); return (item); }
    void reset (Item* item) { }
    void dealloc (Item* item) { delete item; }
  private:
    size_t N;
};

typedef Thread::Queue<Item,ItemAllocator> Queue;

class DataLoader {
  public:
  DataLoader (Queue& queue,
              Image::Header& header) :
              writer (queue), sh_voxel (header) { }

    void execute () {
      Queue::Writer::Item item (writer);

      DataSet::Loop outer ("computing amplitudes...", 0, 3 );
      for (outer.start (sh_voxel); outer.ok(); outer.next (sh_voxel)) {
        item->pos[0] = sh_voxel[0];
        item->pos[1] = sh_voxel[1];
        item->pos[2] = sh_voxel[2];
        DataSet::Loop inner (3);
        unsigned int c = 0;
        for (inner.start (sh_voxel); inner.ok(); inner.next (sh_voxel))
          item->data[c++] = sh_voxel.value();
        if (!item.write()) throw Exception ("error writing to work queue");
      }
    }

  private:
    Queue::Writer writer;
    Image::Voxel<value_type>  sh_voxel;
};

class Processor {
  public:
    Processor (Queue& queue,
               Image::Header& header,
               Math::Matrix<value_type>& directions,
               int lmax,
               bool nonnegative) :
               reader (queue),
               amp_voxel (header),
               transformer (directions, lmax),
               nonnegative (nonnegative) { }

    void execute () {
      Queue::Reader::Item item (reader);

      while ((item.read())) {
        Math::Vector<value_type> amplitudes;
        transformer.SH2A(amplitudes, item->data);

        amp_voxel[0] = item->pos[0];
        amp_voxel[1] = item->pos[1];
        amp_voxel[2] = item->pos[2];
        for (amp_voxel[3] = 0; amp_voxel[3] < amp_voxel.dim(3); ++amp_voxel[3]) {
          if (nonnegative && amplitudes[amp_voxel[3]] < 0)
            amplitudes[amp_voxel[3]] = 0.0;
          amp_voxel.value() = amplitudes[amp_voxel[3]];
        }
      }
    }

 private:
   Queue::Reader reader;
   Image::Voxel<value_type> amp_voxel;
   Math::SH::Transform<value_type> transformer;
   bool nonnegative;
};

void run ()
{
  Image::Header sh_header(argument[0]);
  assert (!sh_header.is_complex());

  if (sh_header.ndim() != 4)
    throw Exception ("The input spherical harmonic image should contain 4 dimensions");

  Image::Header amp_header (sh_header);

  Math::Matrix<value_type> dirs;
  bool gradients = get_options("gradient").size();

  if (gradients) {
    Math::Matrix<value_type> grad;
    grad.load (argument[1]);
    std::vector<int> bzeros, dwis;
    DWI::guess_DW_directions (dwis, bzeros, grad);
    DWI::gen_direction_matrix(dirs, grad, dwis);

    Math::Matrix<value_type> grad_dwis(dwis.size(), 4);
    for (unsigned int i = 0; i < dwis.size(); i++){
      grad_dwis(i,0) = grad(dwis[i],0);
      grad_dwis(i,1) = grad(dwis[i],1);
      grad_dwis(i,2) = grad(dwis[i],2);
      grad_dwis(i,3) = grad(dwis[i],3);
    }
    amp_header.set_DW_scheme(grad_dwis);
  } else {
    dirs.load(argument[1]);
  }
  amp_header.set_dim(3, dirs.rows());
  amp_header.set_stride (0, 2);
  amp_header.set_stride (1, 3);
  amp_header.set_stride (2, 4);
  amp_header.set_stride (3, 1);
  amp_header.create(argument[2]);

  Queue queue ("sh2amp queue", 100, ItemAllocator (sh_header.dim(3)));
  DataLoader loader (queue, sh_header);
  Processor processor (queue, amp_header, dirs, Math::SH::LforN(sh_header.dim(3)), get_options("nonnegative").size());

  Thread::Exec loader_thread (loader, "loader");
  Thread::Array<Processor> processor_list (processor);
  Thread::Exec processor_threads (processor_list, "processor");
}
<|endoftext|>


<commit_before>//
//  schema.cpp
//  erlcass
//
//  Created by silviu on 6/5/15.
//
//

#include "schema.h"
#include <cstring>

const char kValidatorAscii[] = "org.apache.cassandra.db.marshal.AsciiType";
const char kValidatorUUID[] = "org.apache.cassandra.db.marshal.UUIDType";
const char kValidatorUTF8[] = "org.apache.cassandra.db.marshal.UTF8Type";
const char kValidatorInteger[] = "org.apache.cassandra.db.marshal.IntegerType";
const char kValidatorTimeUUID[] = "org.apache.cassandra.db.marshal.TimeUUIDType";
const char kValidatorInetAddress[] = "org.apache.cassandra.db.marshal.InetAddressType";
const char kValidatorLong[] = "org.apache.cassandra.db.marshal.LongType";
const char kValidatorBytes[] = "org.apache.cassandra.db.marshal.BytesType";
const char kValidatorBoolean[] = "org.apache.cassandra.db.marshal.BooleanType";
const char kValidatorDecimal[] = "org.apache.cassandra.db.marshal.DecimalType";
const char kValidatorDouble[] = "org.apache.cassandra.db.marshal.DoubleType";
const char kValidatorFloat[] = "org.apache.cassandra.db.marshal.FloatType";
const char kValidatorInt32[] = "org.apache.cassandra.db.marshal.Int32Type";
const char kValidatorTimestamp[] = "org.apache.cassandra.db.marshal.TimestampType";
const char kValidatorSet[] = "org.apache.cassandra.db.marshal.SetType";
const char kValidatorList[] = "org.apache.cassandra.db.marshal.ListType";
const char kValidatorMap[] = "org.apache.cassandra.db.marshal.MapType";
const char kValidatorCounter[] = "org.apache.cassandra.db.marshal.CounterColumnType";
const char kValidatorReversedType[] = "org.apache.cassandra.db.marshal.ReversedType";

#define VALIDATOR_MAP_INSERT(Key, Value) map[Key] = Value

std::map<std::string, CassValueType> create_validators_map()
{
	std::map<std::string, CassValueType> map;

	VALIDATOR_MAP_INSERT(kValidatorAscii, CASS_VALUE_TYPE_ASCII);
	VALIDATOR_MAP_INSERT(kValidatorLong, CASS_VALUE_TYPE_BIGINT);
	VALIDATOR_MAP_INSERT(kValidatorBytes, CASS_VALUE_TYPE_BLOB);
	VALIDATOR_MAP_INSERT(kValidatorBoolean, CASS_VALUE_TYPE_BOOLEAN);
	VALIDATOR_MAP_INSERT(kValidatorCounter, CASS_VALUE_TYPE_COUNTER);
	VALIDATOR_MAP_INSERT(kValidatorDecimal, CASS_VALUE_TYPE_DECIMAL);
	VALIDATOR_MAP_INSERT(kValidatorDouble, CASS_VALUE_TYPE_DOUBLE);
	VALIDATOR_MAP_INSERT(kValidatorFloat, CASS_VALUE_TYPE_FLOAT);
	VALIDATOR_MAP_INSERT(kValidatorInt32, CASS_VALUE_TYPE_INT);
	VALIDATOR_MAP_INSERT(kValidatorUTF8, CASS_VALUE_TYPE_TEXT);
	VALIDATOR_MAP_INSERT(kValidatorTimestamp, CASS_VALUE_TYPE_TIMESTAMP);
	VALIDATOR_MAP_INSERT(kValidatorUUID, CASS_VALUE_TYPE_UUID);
	VALIDATOR_MAP_INSERT(kValidatorInteger, CASS_VALUE_TYPE_VARINT);
	VALIDATOR_MAP_INSERT(kValidatorTimeUUID, CASS_VALUE_TYPE_TIMEUUID);
	VALIDATOR_MAP_INSERT(kValidatorInetAddress, CASS_VALUE_TYPE_INET);

	return map;
}

const std::map<std::string, CassValueType> kValidatorsMap = create_validators_map();

class SchemaScope
{
public:

    SchemaScope(const CassSchema* schema) : schema_(schema) {}
    ~SchemaScope() {cass_schema_free(schema_);}

    const CassSchema* get() const {return schema_;}

private:

    const CassSchema* schema_;
};

std::string get_subtype(const std::string& validator, const char begin, const char end)
{
    size_t start_index = validator.find(begin);
    size_t end_index = validator.find(end);

    if(start_index == std::string::npos || end_index == std::string::npos)
        return "";

    start_index = start_index + 1;

    return validator.substr(start_index, end_index - start_index);
}

SchemaColumn validator_to_cass_value_type(const std::string & validator)
{
    std::map<std::string, CassValueType>::const_iterator it = kValidatorsMap.find(validator);

    if(it == kValidatorsMap.end())
    {
        //test for collections or reversed types

        static size_t set_length = strlen(kValidatorSet);
        static size_t list_length = strlen(kValidatorList);
        static size_t map_length = strlen(kValidatorMap);
        static size_t reversed_type_length = strlen(kValidatorReversedType);

        if (validator.compare(0, reversed_type_length, kValidatorReversedType) == 0)
        {
            CassValueType subtype = validator_to_cass_value_type(get_subtype(validator, '(', ')')).type;

            if(subtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(subtype);

            return SchemaColumn();
        }

        if (validator.compare(0, list_length, kValidatorList) == 0)
        {
            CassValueType subtype = validator_to_cass_value_type(get_subtype(validator, '(', ')')).type;

            if(subtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(CASS_VALUE_TYPE_LIST, subtype);

            return SchemaColumn();
        }

        if (validator.compare(0, set_length, kValidatorSet) == 0)
        {
            CassValueType subtype = validator_to_cass_value_type(get_subtype(validator, '(', ')')).type;

            if(subtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(CASS_VALUE_TYPE_SET, subtype);

            return SchemaColumn();
        }

        if (validator.compare(0, map_length, kValidatorMap) == 0)
        {
            CassValueType keySubtype = validator_to_cass_value_type(get_subtype(validator, '(', ',')).type;
            CassValueType valueSubtype = validator_to_cass_value_type(get_subtype(validator, ',', ')')).type;

            if(keySubtype != CASS_VALUE_TYPE_UNKNOWN && valueSubtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(CASS_VALUE_TYPE_MAP, keySubtype, valueSubtype);

            return SchemaColumn();
        }

        return SchemaColumn();
    }

    return SchemaColumn(it->second);
}

bool get_schema_field_value(const CassSchemaMeta* schema, const char * name, std::string* value)
{
    const CassSchemaMetaField* field = cass_schema_meta_get_field(schema, name);

    const char* buffer;
    size_t buffer_length;

    if(cass_value_get_string(cass_schema_meta_field_value(field), &buffer, &buffer_length) != CASS_OK)
        return false;

    *value = std::string(buffer, buffer_length);
    return true;
}

bool get_table_schema(CassSession* session, const std::string& keyspace, const std::string& table, ColumnsMap* schema_map)
{
    SchemaScope ss(cass_session_get_schema(session));

    if(!ss.get())
        return false;

    const CassSchemaMeta* keyspace_meta = cass_schema_get_keyspace(ss.get(), keyspace.c_str());

    if(!keyspace_meta)
        return false;

    const CassSchemaMeta* table_meta = cass_schema_meta_get_entry(keyspace_meta, table.c_str());

    if(!table_meta)
        return false;

    CassIterator* entries = cass_iterator_from_schema_meta(table_meta);

    bool success = true;

    std::string column_name;
    std::string validator;

    while (cass_iterator_next(entries))
    {
        const CassSchemaMeta* schema_meta = cass_iterator_get_schema_meta(entries);

        if(!get_schema_field_value(schema_meta, "column_name", &column_name) ||
           !get_schema_field_value(schema_meta, "validator", &validator))
        {
            success = false;
            break;
        }

        SchemaColumn type = validator_to_cass_value_type(validator);

        if(type.type == CASS_VALUE_TYPE_UNKNOWN)
        {
            success = false;
            break;
        }

        (*schema_map)[column_name] = type;
    }

    cass_iterator_free(entries);

    return success;
}
<commit_msg>Add validator for date type<commit_after>//
//  schema.cpp
//  erlcass
//
//  Created by silviu on 6/5/15.
//
//

#include "schema.h"
#include <cstring>

const char kValidatorAscii[] = "org.apache.cassandra.db.marshal.AsciiType";
const char kValidatorUUID[] = "org.apache.cassandra.db.marshal.UUIDType";
const char kValidatorUTF8[] = "org.apache.cassandra.db.marshal.UTF8Type";
const char kValidatorInteger[] = "org.apache.cassandra.db.marshal.IntegerType";
const char kValidatorTimeUUID[] = "org.apache.cassandra.db.marshal.TimeUUIDType";
const char kValidatorInetAddress[] = "org.apache.cassandra.db.marshal.InetAddressType";
const char kValidatorLong[] = "org.apache.cassandra.db.marshal.LongType";
const char kValidatorBytes[] = "org.apache.cassandra.db.marshal.BytesType";
const char kValidatorBoolean[] = "org.apache.cassandra.db.marshal.BooleanType";
const char kValidatorDecimal[] = "org.apache.cassandra.db.marshal.DecimalType";
const char kValidatorDouble[] = "org.apache.cassandra.db.marshal.DoubleType";
const char kValidatorFloat[] = "org.apache.cassandra.db.marshal.FloatType";
const char kValidatorInt32[] = "org.apache.cassandra.db.marshal.Int32Type";
const char kValidatorTimestamp[] = "org.apache.cassandra.db.marshal.TimestampType";
const char kValidatorDate[] = "org.apache.cassandra.db.marshal.DateType";
const char kValidatorSet[] = "org.apache.cassandra.db.marshal.SetType";
const char kValidatorList[] = "org.apache.cassandra.db.marshal.ListType";
const char kValidatorMap[] = "org.apache.cassandra.db.marshal.MapType";
const char kValidatorCounter[] = "org.apache.cassandra.db.marshal.CounterColumnType";
const char kValidatorReversedType[] = "org.apache.cassandra.db.marshal.ReversedType";

#define VALIDATOR_MAP_INSERT(Key, Value) map[Key] = Value

std::map<std::string, CassValueType> create_validators_map()
{
	std::map<std::string, CassValueType> map;

	VALIDATOR_MAP_INSERT(kValidatorAscii, CASS_VALUE_TYPE_ASCII);
	VALIDATOR_MAP_INSERT(kValidatorLong, CASS_VALUE_TYPE_BIGINT);
	VALIDATOR_MAP_INSERT(kValidatorBytes, CASS_VALUE_TYPE_BLOB);
	VALIDATOR_MAP_INSERT(kValidatorBoolean, CASS_VALUE_TYPE_BOOLEAN);
	VALIDATOR_MAP_INSERT(kValidatorCounter, CASS_VALUE_TYPE_COUNTER);
	VALIDATOR_MAP_INSERT(kValidatorDecimal, CASS_VALUE_TYPE_DECIMAL);
	VALIDATOR_MAP_INSERT(kValidatorDouble, CASS_VALUE_TYPE_DOUBLE);
	VALIDATOR_MAP_INSERT(kValidatorFloat, CASS_VALUE_TYPE_FLOAT);
	VALIDATOR_MAP_INSERT(kValidatorInt32, CASS_VALUE_TYPE_INT);
	VALIDATOR_MAP_INSERT(kValidatorUTF8, CASS_VALUE_TYPE_TEXT);
	VALIDATOR_MAP_INSERT(kValidatorTimestamp, CASS_VALUE_TYPE_TIMESTAMP);
	VALIDATOR_MAP_INSERT(kValidatorDate, CASS_VALUE_TYPE_TIMESTAMP);
	VALIDATOR_MAP_INSERT(kValidatorUUID, CASS_VALUE_TYPE_UUID);
	VALIDATOR_MAP_INSERT(kValidatorInteger, CASS_VALUE_TYPE_VARINT);
	VALIDATOR_MAP_INSERT(kValidatorTimeUUID, CASS_VALUE_TYPE_TIMEUUID);
	VALIDATOR_MAP_INSERT(kValidatorInetAddress, CASS_VALUE_TYPE_INET);

	return map;
}

const std::map<std::string, CassValueType> kValidatorsMap = create_validators_map();

class SchemaScope
{
public:

    SchemaScope(const CassSchema* schema) : schema_(schema) {}
    ~SchemaScope() {cass_schema_free(schema_);}

    const CassSchema* get() const {return schema_;}

private:

    const CassSchema* schema_;
};

std::string get_subtype(const std::string& validator, const char begin, const char end)
{
    size_t start_index = validator.find(begin);
    size_t end_index = validator.find(end);

    if(start_index == std::string::npos || end_index == std::string::npos)
        return "";

    start_index = start_index + 1;

    return validator.substr(start_index, end_index - start_index);
}

SchemaColumn validator_to_cass_value_type(const std::string & validator)
{
    std::map<std::string, CassValueType>::const_iterator it = kValidatorsMap.find(validator);

    if(it == kValidatorsMap.end())
    {
        //test for collections or reversed types

        static size_t set_length = strlen(kValidatorSet);
        static size_t list_length = strlen(kValidatorList);
        static size_t map_length = strlen(kValidatorMap);
        static size_t reversed_type_length = strlen(kValidatorReversedType);

        if (validator.compare(0, reversed_type_length, kValidatorReversedType) == 0)
        {
            CassValueType subtype = validator_to_cass_value_type(get_subtype(validator, '(', ')')).type;

            if(subtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(subtype);

            return SchemaColumn();
        }

        if (validator.compare(0, list_length, kValidatorList) == 0)
        {
            CassValueType subtype = validator_to_cass_value_type(get_subtype(validator, '(', ')')).type;

            if(subtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(CASS_VALUE_TYPE_LIST, subtype);

            return SchemaColumn();
        }

        if (validator.compare(0, set_length, kValidatorSet) == 0)
        {
            CassValueType subtype = validator_to_cass_value_type(get_subtype(validator, '(', ')')).type;

            if(subtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(CASS_VALUE_TYPE_SET, subtype);

            return SchemaColumn();
        }

        if (validator.compare(0, map_length, kValidatorMap) == 0)
        {
            CassValueType keySubtype = validator_to_cass_value_type(get_subtype(validator, '(', ',')).type;
            CassValueType valueSubtype = validator_to_cass_value_type(get_subtype(validator, ',', ')')).type;

            if(keySubtype != CASS_VALUE_TYPE_UNKNOWN && valueSubtype != CASS_VALUE_TYPE_UNKNOWN)
                return SchemaColumn(CASS_VALUE_TYPE_MAP, keySubtype, valueSubtype);

            return SchemaColumn();
        }

        return SchemaColumn();
    }

    return SchemaColumn(it->second);
}

bool get_schema_field_value(const CassSchemaMeta* schema, const char * name, std::string* value)
{
    const CassSchemaMetaField* field = cass_schema_meta_get_field(schema, name);

    const char* buffer;
    size_t buffer_length;

    if(cass_value_get_string(cass_schema_meta_field_value(field), &buffer, &buffer_length) != CASS_OK)
        return false;

    *value = std::string(buffer, buffer_length);
    return true;
}

bool get_table_schema(CassSession* session, const std::string& keyspace, const std::string& table, ColumnsMap* schema_map)
{
    SchemaScope ss(cass_session_get_schema(session));

    if(!ss.get())
        return false;

    const CassSchemaMeta* keyspace_meta = cass_schema_get_keyspace(ss.get(), keyspace.c_str());

    if(!keyspace_meta)
        return false;

    const CassSchemaMeta* table_meta = cass_schema_meta_get_entry(keyspace_meta, table.c_str());

    if(!table_meta)
        return false;

    CassIterator* entries = cass_iterator_from_schema_meta(table_meta);

    bool success = true;

    std::string column_name;
    std::string validator;

    while (cass_iterator_next(entries))
    {
        const CassSchemaMeta* schema_meta = cass_iterator_get_schema_meta(entries);

        if(!get_schema_field_value(schema_meta, "column_name", &column_name) ||
           !get_schema_field_value(schema_meta, "validator", &validator))
        {
            success = false;
            break;
        }

        SchemaColumn type = validator_to_cass_value_type(validator);

        if(type.type == CASS_VALUE_TYPE_UNKNOWN)
        {
            success = false;
            break;
        }

        (*schema_map)[column_name] = type;
    }

    cass_iterator_free(entries);

    return success;
}
<|endoftext|>


<commit_before>// g++ -std=c++11 generate_data.cpp -o generate_data
// /home/sjx/graph-query/generate/generate_data lubm_raw_40 id_lubm_40

//to generate minimal_index
// grep "<http://www.University0.edu>" str_normal >> str_normal_minimal
// grep "<http://www.Department0.University0.edu>" str_normal >> str_normal_minimal

#include <string>
#include <fstream>
#include <iostream>
#include <stdio.h>
#include <dirent.h>
#include <unordered_map>
#include <unordered_set>
#include <vector>
#include <algorithm>
#include <assert.h>

using namespace std;

int
main(int argc, char** argv)
{
    unordered_map<string, int> str_to_id;
    vector<string> normal_str;
    vector<string> index_str;

    struct dirent *ptr;
    DIR *dir;
    if (argc <= 2) {
        printf("usage: ./generate_data src_dir dst_dir\n");
        return 0;
    }
    dir = opendir(argv[1]);

    //init

    str_to_id["__PREDICT__"] = 0;
    index_str.push_back("__PREDICT__");
    str_to_id["<http://www.w3.org/1999/02/22-rdf-syntax-ns#type>"] = 1;
    index_str.push_back("<http://www.w3.org/1999/02/22-rdf-syntax-ns#type>");

    int nbit_predict = 17;
    size_t next_index_id = 2;
    size_t next_normal_id = 1 << nbit_predict;
    int count = 1;

    while ((ptr = readdir(dir)) != NULL) {
        if (ptr->d_name[0] == '.')
            continue;
        ifstream file((string(argv[1]) + "/" + string(ptr->d_name)).c_str());
        ofstream output((string(argv[2]) + "/id_" + string(ptr->d_name)).c_str());
        cout << "No." << count << ", loading " << ptr->d_name << endl;
        //printf("No.%d, loading %s ...\n",count,ptr->d_name);
        count++;
        string subject;
        string predict;
        string object;
        string useless_dot;
        while (file >> subject >> predict >> object >> useless_dot) {
            int id[3];
            if (str_to_id.find(subject) == str_to_id.end()) {
                str_to_id[subject] = next_normal_id;
                next_normal_id++;
                normal_str.push_back(subject);
            }
            if (str_to_id.find(predict) == str_to_id.end()) {
                str_to_id[predict] = next_index_id;
                next_index_id++;
                index_str.push_back(predict);
            }
            if (predict == "<http://www.w3.org/1999/02/22-rdf-syntax-ns#type>") {
                if (str_to_id.find(object) == str_to_id.end()) {
                    str_to_id[object] = next_index_id;
                    next_index_id++;
                    index_str.push_back(object);
                }
            } else {
                if (str_to_id.find(object) == str_to_id.end()) {
                    str_to_id[object] = next_normal_id;
                    next_normal_id++;
                    normal_str.push_back(object);
                }
            }
            id[0] = str_to_id[subject];
            id[1] = str_to_id[predict];
            id[2] = str_to_id[object];
            output << id[0] << "\t" << id[1] << "\t" << id[2] << endl;
        }
    }

    {
        ofstream f_normal((string(argv[2]) + "/str_normal").c_str());
        for (int i = 0; i < normal_str.size(); i++) {
            f_normal << normal_str[i] << "\t" << str_to_id[normal_str[i]] << endl;
        }
    }

    {
        ofstream f_index((string(argv[2]) + "/str_index").c_str());
        for (int i = 0; i < index_str.size(); i++) {
            f_index << index_str[i] << "\t" << str_to_id[index_str[i]] << endl;
        }
    }

    cout << "sizeof str_to_id=" << str_to_id.size() << endl;
    cout << "sizeof normal_str=" << normal_str.size() << endl;
    cout << "sizeof index_str=" << index_str.size() << endl;
}
<commit_msg>refine generate_data<commit_after>#include <string>
#include <fstream>
#include <iostream>
#include <stdio.h>
#include <dirent.h>
#include <unordered_map>
#include <unordered_set>
#include <vector>
#include <algorithm>
#include <assert.h>

#include <sys/stat.h>
#include <sys/types.h>

/**
 * A simple manual
 *  $g++ -std=c++11 generate_data.cpp -o generate_data
 *  $./generate_data lubm_raw_40 id_lubm_40
 */

/**
 * How to generate minimal_index file
 *  $grep "<http://www.University0.edu>" str_normal >> str_normal_minimal
 *  $grep "<http://www.Department0.University0.edu>" str_normal >> str_normal_minimal
 *  ...
 */

using namespace std;

enum { NBTITS_IDX = 17 };

int
main(int argc, char** argv)
{
    unordered_map<string, int> str_to_id;
    vector<string> normal_str;
    vector<string> index_str;

    if (argc != 3) {
        printf("usage: ./generate_data src_dir dst_dir\n");
        return -1;
    }

    if (mkdir(argv[2], S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH) < 0) {
        cout << "Error: Creating dst_dir (" << argv[2] << ") failed." << endl;
        exit(-1);
    }

    DIR *src = opendir(argv[1]);
    if (!src) {
        cout << "Error: Opening src_dir (" << argv[1] << ") failed." << endl;
        exit(-1);
    }

    str_to_id["__PREDICT__"] = 0;
    index_str.push_back("__PREDICT__");

    str_to_id["<http://www.w3.org/1999/02/22-rdf-syntax-ns#type>"] = 1;
    index_str.push_back("<http://www.w3.org/1999/02/22-rdf-syntax-ns#type>");

    // reserve the first two ids for the class of index vertex (i.e, predicate or type)
    size_t next_index_id = 2;
    size_t next_normal_id = 1 << NBTITS_IDX; // reserve 2^NBTITS_IDX ids for index vertices
    int count = 0;

    struct dirent *dent;
    while ((dent = readdir(src)) != NULL) {
        if (dent->d_name[0] == '.')
            continue;

        ifstream file((string(argv[1]) + "/" + string(dent->d_name)).c_str());
        ofstream output((string(argv[2]) + "/id_" + string(dent->d_name)).c_str());
        cout << "Process No." << ++count << " file: " << dent->d_name << "." << endl;

        string subject, predict, object, dot;
        while (file >> subject >> predict >> object >> dot) {
            /* add a new normal vertex */
            if (str_to_id.find(subject) == str_to_id.end()) {
                str_to_id[subject] = next_normal_id;
                next_normal_id ++;
                normal_str.push_back(subject);
            }

            /* add a new predicate index vertex (i.e., p-idx) */
            if (str_to_id.find(predict) == str_to_id.end()) {
                str_to_id[predict] = next_index_id;
                next_index_id ++;
                index_str.push_back(predict);
            }

            /* treat different types as individual indexes */
            if (predict == "<http://www.w3.org/1999/02/22-rdf-syntax-ns#type>") {
                /* add a new type index vertex (i.e., t-idx) */
                if (str_to_id.find(object) == str_to_id.end()) {
                    str_to_id[object] = next_index_id;
                    next_index_id ++;
                    index_str.push_back(object);
                }
            } else {
                /* add a new normal vertex */
                if (str_to_id.find(object) == str_to_id.end()) {
                    str_to_id[object] = next_normal_id;
                    next_normal_id ++;
                    normal_str.push_back(object);
                }
            }

            int id[3];
            id[0] = str_to_id[subject];
            id[1] = str_to_id[predict];
            id[2] = str_to_id[object];
            output << id[0] << "\t" << id[1] << "\t" << id[2] << endl;
        }
    }
    closedir(src);

    /* generate a file of the mapping between name and id for nomrmal vertices */
    {
        ofstream f_normal((string(argv[2]) + "/str_normal").c_str());
        for (int i = 0; i < normal_str.size(); i++)
            f_normal << normal_str[i] << "\t" << str_to_id[normal_str[i]] << endl;
    }

    /* generate a file of the mapping between name and id for index vertices */
    {
        ofstream f_index((string(argv[2]) + "/str_index").c_str());
        for (int i = 0; i < index_str.size(); i++)
            f_index << index_str[i] << "\t" << str_to_id[index_str[i]] << endl;
    }

    cout << "#total_vertex = " << str_to_id.size() << endl;
    cout << "#normal_vertex = " << normal_str.size() << endl;
    cout << "#index_vertex = " << index_str.size() << endl;

    return 0;
}
<|endoftext|>


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

#include <atomic>
#include <mutex>
#include <folly/Indestructible.h>
#include <folly/Synchronized.h>
#include <thrift/lib/cpp2/server/ConcurrencyControllerBase.h>

namespace apache::thrift {

using Observer = ConcurrencyControllerBase::Observer;

auto& getObserverStorage() {
  class Storage {
   public:
    void set(std::shared_ptr<Observer> o) {
      static std::once_flag observerSetFlag;
      std::call_once(observerSetFlag, [&] {
        instance_ = std::move(o);
        isset_.store(true, std::memory_order_release);
      });
    }
    Observer* get() {
      if (!isset_.load(std::memory_order_acquire)) {
        return {};
      }
      return instance_.get();
    }

   private:
    std::atomic<bool> isset_{false};
    std::shared_ptr<Observer> instance_;
  };

  static auto observer = folly::Indestructible<Storage>();
  return *observer;
}

Observer* ConcurrencyControllerBase::getGlobalObserver() {
  return getObserverStorage().get();
}

void ConcurrencyControllerBase::setGlobalObserver(
    std::shared_ptr<Observer> observer) {
  getObserverStorage().set(std::move(observer));
}

void ConcurrencyControllerBase::setObserver(std::unique_ptr<Observer> ob) {
  observer_ = std::move(ob);
}

std::optional<ConcurrencyControllerBase::PerRequestStats>
ConcurrencyControllerBase::onExecute(ServerRequest& req) {
  // use local observer
  if (observer_) {
    return observer_->onExecute(req);
  } else {
    // use global observer
    if (auto observer = getGlobalObserver()) {
      return observer->onExecute(req);
    }
  }
  return std::nullopt;
}

void ConcurrencyControllerBase::onFinishExecution(PerRequestStats& stats) {
  // use local observer
  if (observer_) {
    observer_->onFinishExecution(stats);
  } else {
    // use global observer
    if (auto observer = getGlobalObserver()) {
      observer->onFinishExecution(stats);
    }
  }
}

} // namespace apache::thrift
<commit_msg>use folly::once_flag instead of std::once_flag<commit_after>/*
 * Copyright (c) Meta Platforms, Inc. and affiliates.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include <atomic>
#include <folly/Indestructible.h>
#include <folly/Synchronized.h>
#include <folly/synchronization/CallOnce.h>
#include <thrift/lib/cpp2/server/ConcurrencyControllerBase.h>

namespace apache::thrift {

using Observer = ConcurrencyControllerBase::Observer;

auto& getObserverStorage() {
  class Storage {
   public:
    void set(std::shared_ptr<Observer> o) {
      folly::call_once(observerSetFlag_, [&] { instance_ = std::move(o); });
    }
    Observer* get() {
      if (!folly::test_once(observerSetFlag_)) {
        return {};
      }
      return instance_.get();
    }

   private:
    folly::once_flag observerSetFlag_;
    std::shared_ptr<Observer> instance_;
  };

  static auto observer = folly::Indestructible<Storage>();
  return *observer;
}

Observer* ConcurrencyControllerBase::getGlobalObserver() {
  return getObserverStorage().get();
}

void ConcurrencyControllerBase::setGlobalObserver(
    std::shared_ptr<Observer> observer) {
  getObserverStorage().set(std::move(observer));
}

void ConcurrencyControllerBase::setObserver(std::unique_ptr<Observer> ob) {
  observer_ = std::move(ob);
}

std::optional<ConcurrencyControllerBase::PerRequestStats>
ConcurrencyControllerBase::onExecute(ServerRequest& req) {
  // use local observer
  if (observer_) {
    return observer_->onExecute(req);
  } else {
    // use global observer
    if (auto observer = getGlobalObserver()) {
      return observer->onExecute(req);
    }
  }
  return std::nullopt;
}

void ConcurrencyControllerBase::onFinishExecution(PerRequestStats& stats) {
  // use local observer
  if (observer_) {
    observer_->onFinishExecution(stats);
  } else {
    // use global observer
    if (auto observer = getGlobalObserver()) {
      observer->onFinishExecution(stats);
    }
  }
}

} // namespace apache::thrift
<|endoftext|>


<commit_before>/*
 * Copyright (c) 2008-2016 the MRtrix3 contributors
 *
 * This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/
 *
 * MRtrix 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.
 *
 * For more details, see www.mrtrix.org
 *
 */

#include "command.h"
#include "progressbar.h"
#include "memory.h"
#include "image.h"
#include "algo/threaded_loop.h"
#include "math/math.h"
#include "math/median.h"

#include <limits>
#include <vector>

using namespace MR;
using namespace App;

const char* operations[] = {
  "mean",
  "median",
  "sum",
  "product",
  "rms",
  "var",
  "std",
  "min",
  "max",
  "absmax", // Maximum of absolute values
  "magmax", // Value for which the magnitude is the maximum (i.e. preserves signed-ness)
  NULL
};

void usage ()
{
  DESCRIPTION
    + "compute summary statistic on image intensities either across images, "
    "or along a specified axis for a single image. Supported operations are:"

    + "mean, median, sum, product, rms (root-mean-square value), var (unbiased variance), "
    "std (unbiased standard deviation), min, max, absmax (maximum absolute value), "
    "magmax (value with maximum absolute value, preserving its sign)."

    + "See also 'mrcalc' to compute per-voxel operations.";

  ARGUMENTS
  + Argument ("input", "the input image(s).").type_image_in ().allow_multiple()
  + Argument ("operation", "the operation to apply, one of: " + join(operations, ", ") + ".").type_choice (operations)
  + Argument ("output", "the output image.").type_image_out ();

  OPTIONS
  + Option ("axis", "perform operation along a specified axis of a single input image")
  +   Argument ("index").type_integer()

  + DataType::options();
}

typedef float value_type;

class Mean {
  public:
    Mean () : sum (0.0), count (0) { }
    void operator() (value_type val) {
      if (std::isfinite (val)) {
        sum += val;
        ++count;
      }
    }
    value_type result () const {
      if (!count)
        return NAN;
      return sum / count;
    }
    double sum;
    size_t count;
};

class Median {
  public:
    Median () { }
    void operator() (value_type val) {
      if (!std::isnan (val))
        values.push_back(val);
    }
    value_type result () {
      return Math::median(values);
    }
    std::vector<value_type> values;
};

class Sum {
  public:
    Sum () : sum (0.0) { }
    void operator() (value_type val) {
      if (std::isfinite (val))
        sum += val;
    }
    value_type result () const {
      return sum;
    }
    double sum;
};

class Product {
  public:
    Product () : product (0.0) { }
    void operator() (value_type val) {
      if (std::isfinite (val))
        product += val;
    }
    value_type result () const {
      return product;
    }
    double product;
};

class RMS {
  public:
    RMS() : sum (0.0), count (0) { }
    void operator() (value_type val) {
      if (std::isfinite (val)) {
        sum += Math::pow2 (val);
        ++count;
      }
    }
    value_type result() const {
      if (!count)
        return NAN;
      return std::sqrt(sum / count);
    }
    double sum;
    size_t count;
};

class Var {
  public:
    Var () : sum (0.0), sum_sqr (0.0), count (0) { }
    void operator() (value_type val) {
      if (std::isfinite (val)) {
        sum += val;
        sum_sqr += Math::pow2 (val);
        ++count;
      }
    }
    value_type result () const {
      if (count < 2)
        return NAN;
      return  (sum_sqr - Math::pow2 (sum) / static_cast<double> (count)) / (static_cast<double> (count) - 1.0);
    }
    double sum, sum_sqr;
    size_t count;
};

class Std : public Var {
  public:
    Std() : Var() { }
    value_type result () const { return std::sqrt (Var::result()); }
};

class Min {
  public:
    Min () : min (std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && val < min)
        min = val;
    }
    value_type result () const { return std::isfinite (min) ? min : NAN; }
    value_type min;
};

class Max {
  public:
    Max () : max (-std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && val > max)
        max = val;
    }
    value_type result () const { return std::isfinite (max) ? max : NAN; }
    value_type max;
};

class AbsMax {
  public:
    AbsMax () : max (-std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && std::abs(val) > max)
        max = std::abs(val);
    }
    value_type result () const { return std::isfinite (max) ? max : NAN; }
    value_type max;
};

class MagMax {
  public:
    MagMax () : max (-std::numeric_limits<value_type>::infinity()) { }
    MagMax (const int i) : max (-std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && (!std::isfinite (max) || std::abs(val) > std::abs (max)))
        max = val;
    }
    value_type result () const { return std::isfinite (max) ? max : NAN; }
    value_type max;
};

template <class Operation>
class AxisKernel {
  public:
    AxisKernel (size_t axis) : axis (axis) { }

    template <class InputImageType, class OutputImageType>
      void operator() (InputImageType& in, OutputImageType& out) {
        Operation op;
        for (auto l = Loop (axis) (in); l; ++l)
          op (in.value());
        out.value() = op.result();
      }
  protected:
    const size_t axis;
};

class ImageKernelBase {
  public:
    virtual void process (Header& image_in) = 0;
    virtual void write_back (Image<value_type>& out) = 0;
};

template <class Operation>
class ImageKernel : public ImageKernelBase {
  protected:
    class InitFunctor {
      public:
        template <class ImageType>
          void operator() (ImageType& out) const { out.value() = Operation(); }
    };
    class ProcessFunctor {
      public:
        template <class ImageType1, class ImageType2>
          void operator() (ImageType1& out, ImageType2& in) const {
            Operation op = out.value();
            op (in.value());
            out.value() = op;
          }
    };
    class ResultFunctor {
      public:
        template <class ImageType1, class ImageType2>
          void operator() (ImageType1& out, ImageType2& in) const {
            Operation op = in.value();
            out.value() = op.result();
          }
    };

  public:
    ImageKernel (const Header& header) :
      image (Header::scratch (header).get_image<Operation>()) {
        ThreadedLoop (image).run (InitFunctor(), image);
      }

    void write_back (Image<value_type>& out)
    {
      ThreadedLoop (image).run (ResultFunctor(), out, image);
    }

    void process (Header& header_in)
    {
      auto in = header_in.get_image<value_type>();
      ThreadedLoop (image).run (ProcessFunctor(), image, in);
    }

  protected:
    Image<Operation> image;
};

void run ()
{
  const size_t num_inputs = argument.size() - 2;
  const int op = argument[num_inputs];
  const std::string& output_path = argument.back();

  auto opt = get_options ("axis");
  if (opt.size()) {

    if (num_inputs != 1)
      throw Exception ("Option -axis only applies if a single input image is used");

    const size_t axis = opt[0][0];

    auto image_in = Header::open (argument[0]).get_image<value_type>().with_direct_io (axis);

    if (axis >= image_in.ndim())
      throw Exception ("Cannot perform operation along axis " + str (axis) + "; image only has " + str(image_in.ndim()) + " axes");

    Header header_out (image_in.original_header());

    header_out.datatype() = DataType::from_command_line (DataType::Float32);
    header_out.size(axis) = 1;
    squeeze_dim (header_out);

    auto image_out = Header::create (output_path, header_out).get_image<float>();

    auto loop = ThreadedLoop (std::string("computing ") + operations[op] + " along axis " + str(axis) + "...", image_out);

    switch (op) {
      case 0: loop.run  (AxisKernel<Mean>   (axis), image_in, image_out); return;
      case 1: loop.run  (AxisKernel<Median> (axis), image_in, image_out); return;
      case 2: loop.run  (AxisKernel<Sum>    (axis), image_in, image_out); return;
      case 3: loop.run  (AxisKernel<Product>(axis), image_in, image_out); return;
      case 4: loop.run  (AxisKernel<RMS>    (axis), image_in, image_out); return;
      case 5: loop.run  (AxisKernel<Var>    (axis), image_in, image_out); return;
      case 6: loop.run  (AxisKernel<Std>    (axis), image_in, image_out); return;
      case 7: loop.run  (AxisKernel<Min>    (axis), image_in, image_out); return;
      case 8: loop.run  (AxisKernel<Max>    (axis), image_in, image_out); return;
      case 9: loop.run  (AxisKernel<AbsMax> (axis), image_in, image_out); return;
      case 10: loop.run (AxisKernel<MagMax> (axis), image_in, image_out); return;
      default: assert (0);
    }

  } else {

    if (num_inputs < 2)
      throw Exception ("mrmath requires either multiple input images, or the -axis option to be provided");

    // Pre-load all image headers
    std::vector<Header> headers_in;
    // std::vector<std::unique_ptr<Header>> headers_in;

    // Header of first input image is the template to which all other input images are compared
    headers_in.push_back (Header::open (argument[0]));
    Header header (headers_in[0]);
    header.datatype() = DataType::from_command_line (DataType::Float32);

    // Wipe any excess unary-dimensional axes
    while (header.size (header.ndim() - 1) == 1)
      header.set_ndim (header.ndim() - 1);

    // Verify that dimensions of all input images adequately match
    for (size_t i = 1; i != num_inputs; ++i) {
      const std::string path = argument[i];
      // headers_in.push_back (std::unique_ptr<Header> (new Header (Header::open (path))));
      headers_in.push_back (Header::open (path));
      const Header& temp (headers_in[i]);
      if (temp.ndim() < header.ndim())
        throw Exception ("Image " + path + " has fewer axes than first imput image " + header.name());
      for (size_t axis = 0; axis != header.ndim(); ++axis) {
        if (temp.size(axis) != header.size(axis))
          throw Exception ("Dimensions of image " + path + " do not match those of first input image " + header.name());
      }
      for (size_t axis = header.ndim(); axis != temp.ndim(); ++axis) {
        if (temp.size(axis) != 1)
          throw Exception ("Image " + path + " has axis with non-unary dimension beyond first input image " + header.name());
      }
    }

    // Instantiate a kernel depending on the operation requested
    std::unique_ptr<ImageKernelBase> kernel;
    switch (op) {
      case 0:  kernel.reset (new ImageKernel<Mean>    (header)); break;
      case 1:  kernel.reset (new ImageKernel<Median>  (header)); break;
      case 2:  kernel.reset (new ImageKernel<Sum>     (header)); break;
      case 3:  kernel.reset (new ImageKernel<Product> (header)); break;
      case 4:  kernel.reset (new ImageKernel<RMS>     (header)); break;
      case 5:  kernel.reset (new ImageKernel<Var>     (header)); break;
      case 6:  kernel.reset (new ImageKernel<Std>     (header)); break;
      case 7:  kernel.reset (new ImageKernel<Min>     (header)); break;
      case 8:  kernel.reset (new ImageKernel<Max>     (header)); break;
      case 9:  kernel.reset (new ImageKernel<AbsMax>  (header)); break;
      case 10: kernel.reset (new ImageKernel<MagMax>  (header)); break;
      default: assert (0);
    }

    // Feed the input images to the kernel one at a time
    {
      ProgressBar progress (std::string("computing ") + operations[op] + " across "
          + str(headers_in.size()) + " images", num_inputs);
      for (size_t i = 0; i != headers_in.size(); ++i) {
        assert (headers_in[i].is_file_backed());
        kernel->process (headers_in[i]);
        ++progress;
      }
    }

    auto out = Header::create (output_path, header).get_image<value_type>();
    kernel->write_back (out);
  }

}

<commit_msg>mrmath: product was doing a sum<commit_after>/*
 * Copyright (c) 2008-2016 the MRtrix3 contributors
 *
 * This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/
 *
 * MRtrix 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.
 *
 * For more details, see www.mrtrix.org
 *
 */

#include "command.h"
#include "progressbar.h"
#include "memory.h"
#include "image.h"
#include "algo/threaded_loop.h"
#include "math/math.h"
#include "math/median.h"

#include <limits>
#include <vector>

using namespace MR;
using namespace App;

const char* operations[] = {
  "mean",
  "median",
  "sum",
  "product",
  "rms",
  "var",
  "std",
  "min",
  "max",
  "absmax", // Maximum of absolute values
  "magmax", // Value for which the magnitude is the maximum (i.e. preserves signed-ness)
  NULL
};

void usage ()
{
  DESCRIPTION
    + "compute summary statistic on image intensities either across images, "
    "or along a specified axis for a single image. Supported operations are:"

    + "mean, median, sum, product, rms (root-mean-square value), var (unbiased variance), "
    "std (unbiased standard deviation), min, max, absmax (maximum absolute value), "
    "magmax (value with maximum absolute value, preserving its sign)."

    + "See also 'mrcalc' to compute per-voxel operations.";

  ARGUMENTS
  + Argument ("input", "the input image(s).").type_image_in ().allow_multiple()
  + Argument ("operation", "the operation to apply, one of: " + join(operations, ", ") + ".").type_choice (operations)
  + Argument ("output", "the output image.").type_image_out ();

  OPTIONS
  + Option ("axis", "perform operation along a specified axis of a single input image")
  +   Argument ("index").type_integer()

  + DataType::options();
}

typedef float value_type;

class Mean {
  public:
    Mean () : sum (0.0), count (0) { }
    void operator() (value_type val) {
      if (std::isfinite (val)) {
        sum += val;
        ++count;
      }
    }
    value_type result () const {
      if (!count)
        return NAN;
      return sum / count;
    }
    double sum;
    size_t count;
};

class Median {
  public:
    Median () { }
    void operator() (value_type val) {
      if (!std::isnan (val))
        values.push_back(val);
    }
    value_type result () {
      return Math::median(values);
    }
    std::vector<value_type> values;
};

class Sum {
  public:
    Sum () : sum (0.0) { }
    void operator() (value_type val) {
      if (std::isfinite (val))
        sum += val;
    }
    value_type result () const {
      return sum;
    }
    double sum;
};

class Product {
  public:
    Product () : product (1.0) { }
    void operator() (value_type val) {
      if (std::isfinite (val))
        product *= val;
    }
    value_type result () const {
      return product;
    }
    double product;
};

class RMS {
  public:
    RMS() : sum (0.0), count (0) { }
    void operator() (value_type val) {
      if (std::isfinite (val)) {
        sum += Math::pow2 (val);
        ++count;
      }
    }
    value_type result() const {
      if (!count)
        return NAN;
      return std::sqrt(sum / count);
    }
    double sum;
    size_t count;
};

class Var {
  public:
    Var () : sum (0.0), sum_sqr (0.0), count (0) { }
    void operator() (value_type val) {
      if (std::isfinite (val)) {
        sum += val;
        sum_sqr += Math::pow2 (val);
        ++count;
      }
    }
    value_type result () const {
      if (count < 2)
        return NAN;
      return  (sum_sqr - Math::pow2 (sum) / static_cast<double> (count)) / (static_cast<double> (count) - 1.0);
    }
    double sum, sum_sqr;
    size_t count;
};

class Std : public Var {
  public:
    Std() : Var() { }
    value_type result () const { return std::sqrt (Var::result()); }
};

class Min {
  public:
    Min () : min (std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && val < min)
        min = val;
    }
    value_type result () const { return std::isfinite (min) ? min : NAN; }
    value_type min;
};

class Max {
  public:
    Max () : max (-std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && val > max)
        max = val;
    }
    value_type result () const { return std::isfinite (max) ? max : NAN; }
    value_type max;
};

class AbsMax {
  public:
    AbsMax () : max (-std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && std::abs(val) > max)
        max = std::abs(val);
    }
    value_type result () const { return std::isfinite (max) ? max : NAN; }
    value_type max;
};

class MagMax {
  public:
    MagMax () : max (-std::numeric_limits<value_type>::infinity()) { }
    MagMax (const int i) : max (-std::numeric_limits<value_type>::infinity()) { }
    void operator() (value_type val) {
      if (std::isfinite (val) && (!std::isfinite (max) || std::abs(val) > std::abs (max)))
        max = val;
    }
    value_type result () const { return std::isfinite (max) ? max : NAN; }
    value_type max;
};

template <class Operation>
class AxisKernel {
  public:
    AxisKernel (size_t axis) : axis (axis) { }

    template <class InputImageType, class OutputImageType>
      void operator() (InputImageType& in, OutputImageType& out) {
        Operation op;
        for (auto l = Loop (axis) (in); l; ++l)
          op (in.value());
        out.value() = op.result();
      }
  protected:
    const size_t axis;
};

class ImageKernelBase {
  public:
    virtual void process (Header& image_in) = 0;
    virtual void write_back (Image<value_type>& out) = 0;
};

template <class Operation>
class ImageKernel : public ImageKernelBase {
  protected:
    class InitFunctor {
      public:
        template <class ImageType>
          void operator() (ImageType& out) const { out.value() = Operation(); }
    };
    class ProcessFunctor {
      public:
        template <class ImageType1, class ImageType2>
          void operator() (ImageType1& out, ImageType2& in) const {
            Operation op = out.value();
            op (in.value());
            out.value() = op;
          }
    };
    class ResultFunctor {
      public:
        template <class ImageType1, class ImageType2>
          void operator() (ImageType1& out, ImageType2& in) const {
            Operation op = in.value();
            out.value() = op.result();
          }
    };

  public:
    ImageKernel (const Header& header) :
      image (Header::scratch (header).get_image<Operation>()) {
        ThreadedLoop (image).run (InitFunctor(), image);
      }

    void write_back (Image<value_type>& out)
    {
      ThreadedLoop (image).run (ResultFunctor(), out, image);
    }

    void process (Header& header_in)
    {
      auto in = header_in.get_image<value_type>();
      ThreadedLoop (image).run (ProcessFunctor(), image, in);
    }

  protected:
    Image<Operation> image;
};

void run ()
{
  const size_t num_inputs = argument.size() - 2;
  const int op = argument[num_inputs];
  const std::string& output_path = argument.back();

  auto opt = get_options ("axis");
  if (opt.size()) {

    if (num_inputs != 1)
      throw Exception ("Option -axis only applies if a single input image is used");

    const size_t axis = opt[0][0];

    auto image_in = Header::open (argument[0]).get_image<value_type>().with_direct_io (axis);

    if (axis >= image_in.ndim())
      throw Exception ("Cannot perform operation along axis " + str (axis) + "; image only has " + str(image_in.ndim()) + " axes");

    Header header_out (image_in.original_header());

    header_out.datatype() = DataType::from_command_line (DataType::Float32);
    header_out.size(axis) = 1;
    squeeze_dim (header_out);

    auto image_out = Header::create (output_path, header_out).get_image<float>();

    auto loop = ThreadedLoop (std::string("computing ") + operations[op] + " along axis " + str(axis) + "...", image_out);

    switch (op) {
      case 0: loop.run  (AxisKernel<Mean>   (axis), image_in, image_out); return;
      case 1: loop.run  (AxisKernel<Median> (axis), image_in, image_out); return;
      case 2: loop.run  (AxisKernel<Sum>    (axis), image_in, image_out); return;
      case 3: loop.run  (AxisKernel<Product>(axis), image_in, image_out); return;
      case 4: loop.run  (AxisKernel<RMS>    (axis), image_in, image_out); return;
      case 5: loop.run  (AxisKernel<Var>    (axis), image_in, image_out); return;
      case 6: loop.run  (AxisKernel<Std>    (axis), image_in, image_out); return;
      case 7: loop.run  (AxisKernel<Min>    (axis), image_in, image_out); return;
      case 8: loop.run  (AxisKernel<Max>    (axis), image_in, image_out); return;
      case 9: loop.run  (AxisKernel<AbsMax> (axis), image_in, image_out); return;
      case 10: loop.run (AxisKernel<MagMax> (axis), image_in, image_out); return;
      default: assert (0);
    }

  } else {

    if (num_inputs < 2)
      throw Exception ("mrmath requires either multiple input images, or the -axis option to be provided");

    // Pre-load all image headers
    std::vector<Header> headers_in;
    // std::vector<std::unique_ptr<Header>> headers_in;

    // Header of first input image is the template to which all other input images are compared
    headers_in.push_back (Header::open (argument[0]));
    Header header (headers_in[0]);
    header.datatype() = DataType::from_command_line (DataType::Float32);

    // Wipe any excess unary-dimensional axes
    while (header.size (header.ndim() - 1) == 1)
      header.set_ndim (header.ndim() - 1);

    // Verify that dimensions of all input images adequately match
    for (size_t i = 1; i != num_inputs; ++i) {
      const std::string path = argument[i];
      // headers_in.push_back (std::unique_ptr<Header> (new Header (Header::open (path))));
      headers_in.push_back (Header::open (path));
      const Header& temp (headers_in[i]);
      if (temp.ndim() < header.ndim())
        throw Exception ("Image " + path + " has fewer axes than first imput image " + header.name());
      for (size_t axis = 0; axis != header.ndim(); ++axis) {
        if (temp.size(axis) != header.size(axis))
          throw Exception ("Dimensions of image " + path + " do not match those of first input image " + header.name());
      }
      for (size_t axis = header.ndim(); axis != temp.ndim(); ++axis) {
        if (temp.size(axis) != 1)
          throw Exception ("Image " + path + " has axis with non-unary dimension beyond first input image " + header.name());
      }
    }

    // Instantiate a kernel depending on the operation requested
    std::unique_ptr<ImageKernelBase> kernel;
    switch (op) {
      case 0:  kernel.reset (new ImageKernel<Mean>    (header)); break;
      case 1:  kernel.reset (new ImageKernel<Median>  (header)); break;
      case 2:  kernel.reset (new ImageKernel<Sum>     (header)); break;
      case 3:  kernel.reset (new ImageKernel<Product> (header)); break;
      case 4:  kernel.reset (new ImageKernel<RMS>     (header)); break;
      case 5:  kernel.reset (new ImageKernel<Var>     (header)); break;
      case 6:  kernel.reset (new ImageKernel<Std>     (header)); break;
      case 7:  kernel.reset (new ImageKernel<Min>     (header)); break;
      case 8:  kernel.reset (new ImageKernel<Max>     (header)); break;
      case 9:  kernel.reset (new ImageKernel<AbsMax>  (header)); break;
      case 10: kernel.reset (new ImageKernel<MagMax>  (header)); break;
      default: assert (0);
    }

    // Feed the input images to the kernel one at a time
    {
      ProgressBar progress (std::string("computing ") + operations[op] + " across "
          + str(headers_in.size()) + " images", num_inputs);
      for (size_t i = 0; i != headers_in.size(); ++i) {
        assert (headers_in[i].is_file_backed());
        kernel->process (headers_in[i]);
        ++progress;
      }
    }

    auto out = Header::create (output_path, header).get_image<value_type>();
    kernel->write_back (out);
  }

}

<|endoftext|>


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

#include <folly/Range.h>
#include <proxygen/lib/http/codec/CodecUtil.h>
#include <proxygen/lib/utils/Base64.h>
#include <thrift/lib/cpp2/transport/http2/client/H2ClientConnection.h>

namespace apache {
namespace thrift {

using proxygen::HTTPMessage;
using std::map;
using std::string;

void H2Channel::encodeHeaders(
    const map<string, string>& source,
    HTTPMessage& dest) noexcept {
  auto& msgHeaders = dest.getHeaders();
  for (auto it = source.begin(); it != source.end(); ++it) {
    // Keys in Thrift may not comply with HTTP key format requirements.
    // The following algorithm is implemented at multiple locations and
    // should be kept in sync.
    //
    // If the key does not contain a ":", we assume it is compliant
    // and we use the key and value as is.  In case such a key is not
    // compliant, things will break.
    //
    // If it contains a ":", we encode both the key and the value.  We
    // add a prefix tag ("encode_") to the and encode both the key and
    // the value into the value.
    if (!proxygen::CodecUtil::validateHeaderName(
            folly::ByteRange(folly::StringPiece(it->first))) ||
        !proxygen::CodecUtil::validateHeaderValue(
            folly::ByteRange(folly::StringPiece(it->second)),
            proxygen::CodecUtil::CtlEscapeMode::STRICT)) {
      auto name = proxygen::Base64::urlEncode(folly::StringPiece(it->first));
      auto value = proxygen::Base64::urlEncode(folly::StringPiece(it->second));
      msgHeaders.set(
          folly::to<std::string>("encode_", name),
          folly::to<std::string>(name, "_", value));
    } else {
      msgHeaders.set(it->first, it->second);
    }
  }
}

void H2Channel::decodeHeaders(
    const HTTPMessage& source,
    map<string, string>& dest) noexcept {
  auto decodeAndCopyKeyValue = [&](const string& key, const string& val) {
    // This decodes key-value pairs that have been encoded using
    // encodeHeaders() or equivalent methods.  If the key starts with
    // "encode_", the value is split at the underscore and then the
    // key and value are decoded from there.  The key is not used
    // because it will get converted to lowercase and therefore the
    // original key cannot be recovered.
    if (key.find("encode_") == 0) {
      auto us = val.find("_");
      if (us == string::npos) {
        LOG(ERROR) << "Encoded value does not contain underscore";
      }
      auto decodedKey = proxygen::Base64::urlDecode(val.substr(0, us));
      auto decodedVal = proxygen::Base64::urlDecode(val.substr(us + 1));
      dest[decodedKey] = decodedVal;
    } else {
      dest[key] = val;
    }
  };
  source.getHeaders().forEach(decodeAndCopyKeyValue);
}

} // namespace thrift
} // namespace apache
<commit_msg>Fix HTTP header decoding<commit_after>/*
 * Copyright 2017-present Facebook, Inc.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
#include <thrift/lib/cpp2/transport/http2/common/H2Channel.h>

#include <folly/Range.h>
#include <proxygen/lib/http/codec/CodecUtil.h>
#include <proxygen/lib/utils/Base64.h>
#include <thrift/lib/cpp2/transport/http2/client/H2ClientConnection.h>

namespace apache {
namespace thrift {

using proxygen::HTTPMessage;
using std::map;
using std::string;

void H2Channel::encodeHeaders(
    const map<string, string>& source,
    HTTPMessage& dest) noexcept {
  auto& msgHeaders = dest.getHeaders();
  for (auto it = source.begin(); it != source.end(); ++it) {
    // Keys in Thrift may not comply with HTTP key format requirements.
    // The following algorithm is implemented at multiple locations and
    // should be kept in sync.
    //
    // If the key does not contain a ":", we assume it is compliant
    // and we use the key and value as is.  In case such a key is not
    // compliant, things will break.
    //
    // If it contains a ":", we encode both the key and the value.  We
    // add a prefix tag ("encode_") to the and encode both the key and
    // the value into the value.
    if (!proxygen::CodecUtil::validateHeaderName(
            folly::ByteRange(folly::StringPiece(it->first))) ||
        !proxygen::CodecUtil::validateHeaderValue(
            folly::ByteRange(folly::StringPiece(it->second)),
            proxygen::CodecUtil::CtlEscapeMode::STRICT)) {
      auto name = proxygen::Base64::urlEncode(folly::StringPiece(it->first));
      auto value = proxygen::Base64::urlEncode(folly::StringPiece(it->second));
      msgHeaders.set(
          folly::to<std::string>("encode_", name),
          folly::to<std::string>(name, "_", value));
    } else {
      msgHeaders.set(it->first, it->second);
    }
  }
}

void H2Channel::decodeHeaders(
    const HTTPMessage& source,
    map<string, string>& dest) noexcept {
  auto decodeAndCopyKeyValue = [&](const string& key, const string& val) {
    // This decodes key-value pairs that have been encoded using
    // encodeHeaders() or equivalent methods.  If the key starts with
    // "encode_", the value is split at the underscore and then the
    // key and value are decoded from there.  The key is not used
    // because it will get converted to lowercase and therefore the
    // original key cannot be recovered.
    if (key.find("encode_") == 0) {
      auto us = val.find("_");
      if (us != string::npos) {
        auto decodedKey = proxygen::Base64::urlDecode(val.substr(0, us));
        auto decodedVal = proxygen::Base64::urlDecode(val.substr(us + 1));
        dest[decodedKey] = decodedVal;
        return;
      }
      LOG(ERROR) << "Encoded value does not contain '_'; preserving original";
    }
    dest[key] = val;
  };
  source.getHeaders().forEach(decodeAndCopyKeyValue);
}

} // namespace thrift
} // namespace apache
<|endoftext|>


<commit_before>// Copyright (c) 2010 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 "app/message_box_flags.h"
#include "base/file_path.h"
#include "chrome/app/chrome_dll_resource.h"
#include "chrome/browser/view_ids.h"
#include "chrome/test/automation/automation_proxy.h"
#include "chrome/test/automation/browser_proxy.h"
#include "chrome/test/automation/tab_proxy.h"
#include "chrome/test/automation/window_proxy.h"
#include "chrome/test/ui/ui_test.h"
#include "chrome/test/ui_test_utils.h"
#include "gfx/rect.h"
#include "views/event.h"

class FastShutdown : public UITest {
};

#if defined(OS_MACOSX)
// SimulateOSClick is broken on the Mac: http://crbug.com/45162
#define MAYBE_SlowTermination DISABLED_SlowTermination
#elif defined(OS_LINUX)
#define MAYBE_SlowTermination SlowTermination
#elif defined(OS_WIN)
// Times out: http://crbug.com/46616
#define MAYBE_SlowTermination DISABLED_SlowTermination
#else
#define MAYBE_SlowTermination SlowTermination
#endif

// This tests for a previous error where uninstalling an onbeforeunload
// handler would enable fast shutdown even if an onUnload handler still
// existed.
TEST_F(FastShutdown, MAYBE_SlowTermination) {
  scoped_refptr<BrowserProxy> browser(automation()->GetBrowserWindow(0));
  ASSERT_TRUE(browser.get());
  scoped_refptr<WindowProxy> window(browser->GetWindow());
  ASSERT_TRUE(window.get());

  // This page has an unload handler.
  const FilePath dir(FILE_PATH_LITERAL("fast_shutdown"));
  const FilePath file(FILE_PATH_LITERAL("on_unloader.html"));
  NavigateToURL(ui_test_utils::GetTestUrl(dir, file));
  gfx::Rect bounds;
  ASSERT_TRUE(window->GetViewBounds(VIEW_ID_TAB_CONTAINER, &bounds, true));
  // This click will launch a popup which has a before unload handler.
  ASSERT_TRUE(window->SimulateOSClick(bounds.CenterPoint(),
                                      views::Event::EF_LEFT_BUTTON_DOWN));
  ASSERT_TRUE(browser->WaitForTabCountToBecome(2));
  // Close the tab, removing the one and only before unload handler.
  scoped_refptr<TabProxy> tab(browser->GetTab(1));
  ASSERT_TRUE(tab->Close(true));

  // Close the browser. We should launch the unload handler, which is an
  // alert().
  ASSERT_TRUE(browser->ApplyAccelerator(IDC_CLOSE_WINDOW));
  ASSERT_TRUE(automation()->WaitForAppModalDialog());
  ASSERT_TRUE(automation()->ClickAppModalDialogButton(
                  MessageBoxFlags::DIALOGBUTTON_OK));
  ASSERT_TRUE(WaitForBrowserProcessToQuit());
}
<commit_msg>Enable FastShutdown interactive ui test on Windows.<commit_after>// Copyright (c) 2010 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 "app/message_box_flags.h"
#include "base/file_path.h"
#include "chrome/app/chrome_dll_resource.h"
#include "chrome/browser/view_ids.h"
#include "chrome/test/automation/automation_proxy.h"
#include "chrome/test/automation/browser_proxy.h"
#include "chrome/test/automation/tab_proxy.h"
#include "chrome/test/automation/window_proxy.h"
#include "chrome/test/ui/ui_test.h"
#include "chrome/test/ui_test_utils.h"
#include "gfx/rect.h"
#include "views/event.h"

class FastShutdown : public UITest {
};

#if defined(OS_MACOSX)
// SimulateOSClick is broken on the Mac: http://crbug.com/45162
#define MAYBE_SlowTermination DISABLED_SlowTermination
#else
#define MAYBE_SlowTermination SlowTermination
#endif

// This tests for a previous error where uninstalling an onbeforeunload
// handler would enable fast shutdown even if an onUnload handler still
// existed.
TEST_F(FastShutdown, MAYBE_SlowTermination) {
  scoped_refptr<BrowserProxy> browser(automation()->GetBrowserWindow(0));
  ASSERT_TRUE(browser.get());
  scoped_refptr<WindowProxy> window(browser->GetWindow());
  ASSERT_TRUE(window.get());

  // This page has an unload handler.
  const FilePath dir(FILE_PATH_LITERAL("fast_shutdown"));
  const FilePath file(FILE_PATH_LITERAL("on_unloader.html"));
  NavigateToURL(ui_test_utils::GetTestUrl(dir, file));
  gfx::Rect bounds;
  ASSERT_TRUE(window->GetViewBounds(VIEW_ID_TAB_CONTAINER, &bounds, true));
  // This click will launch a popup which has a before unload handler.
  ASSERT_TRUE(window->SimulateOSClick(bounds.CenterPoint(),
                                      views::Event::EF_LEFT_BUTTON_DOWN));
  ASSERT_TRUE(browser->WaitForTabCountToBecome(2));
  // Close the tab, removing the one and only before unload handler.
  scoped_refptr<TabProxy> tab(browser->GetTab(1));
  ASSERT_TRUE(tab->Close(true));

  // Close the browser. We should launch the unload handler, which is an
  // alert().
  ASSERT_TRUE(browser->ApplyAccelerator(IDC_CLOSE_WINDOW));
  ASSERT_TRUE(automation()->WaitForAppModalDialog());
  ASSERT_TRUE(automation()->ClickAppModalDialogButton(
                  MessageBoxFlags::DIALOGBUTTON_OK));
  ASSERT_TRUE(WaitForBrowserProcessToQuit());
}
<|endoftext|>


<commit_before>// $Id: fourth_error_estimators.C,v 1.1 2005-05-27 14:45:39 roystgnr Exp $

// The libMesh Finite Element Library.
// Copyright (C) 2002-2004  Benjamin S. Kirk, John W. Peterson

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

// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
// 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

// C++ includes
#include <algorithm> // for std::fill
#include <math.h>    // for sqrt

// Local Includes
#include "libmesh_common.h"
#include "fourth_error_estimators.h"
#include "dof_map.h"
#include "fe.h"
#include "fe_interface.h"
#include "quadrature_clough.h"
#include "libmesh_logging.h"
#include "elem.h"

//-----------------------------------------------------------------
// ErrorEstimator implementations
void LaplacianErrorEstimator::estimate_error (const System& system,
					   std::vector<float>& error_per_cell)
{
  START_LOG("laplacian_jump()", "LaplacianErrorEstimator");

  /*

  - e & f are global element ids

  Case (1.) Elements are at the same level, e<f
            Compute the laplacian jump on the face and
	    add it as a contribution to error_per_cell[e]
	    and error_per_cell[f]

                   ----------------------
		  |           |          |
		  |           |    f     |
		  |           |          |
		  |    e      |---> n    |
		  |           |          |
		  |           |          |
                   ----------------------

   Case (2.) The neighbor is at a higher level.
             Compute the laplacian jump on e's face and
	     add it as a contribution to error_per_cell[e]
	     and error_per_cell[f]

                   ----------------------
		  |     |     |          |
		  |     |  e  |---> n    |
		  |     |     |          |
		  |-----------|    f     |
		  |     |     |          |
		  |     |     |          |
		  |     |     |          |
                   ----------------------
*/

  // The current mesh
  const Mesh& mesh = system.get_mesh();

  // The dimensionality of the mesh
  const unsigned int dim = mesh.mesh_dimension();

  // The number of variables in the system
  const unsigned int n_vars = system.n_vars();

  // The DofMap for this system
  const DofMap& dof_map = system.get_dof_map();

  // Resize the error_per_cell vector to be
  // the number of elements, initialize it to 0.
  error_per_cell.resize (mesh.n_elem());
  std::fill (error_per_cell.begin(), error_per_cell.end(), 0.);

  // Check for a valid component_mask
  if (!component_mask.empty())
    if (component_mask.size() != n_vars)
      {
	std::cerr << "ERROR: component_mask is the wrong size:"
		  << std::endl
		  << " component_mask.size()=" << component_mask.size()
		  << std::endl
		  << " n_vars=" << n_vars
		  << std::endl;
	error();
      }

  // Loop over all the variables in the system
  for (unsigned int var=0; var<n_vars; var++)
    {
      // Possibly skip this variable
      if (!component_mask.empty())
	if (component_mask[var] == false) continue;

      // The type of finite element to use for this variable
      const FEType& fe_type = dof_map.variable_type (var);

      // Finite element objects for the same face from
      // different sides
      AutoPtr<FEBase> fe_e (FEBase::build (dim, fe_type));
      AutoPtr<FEBase> fe_f (FEBase::build (dim, fe_type));

      // Build an appropriate Clough-Tocher quadrature rule
      QClough qrule (dim-1, fe_type.default_quadrature_order());

      // Tell the finite element for element e about the quadrature
      // rule.  The finite element for element f need not know about it
      fe_e->attach_quadrature_rule (&qrule);

      // By convention we will always do the integration
      // on the face of element e.  Get its Jacobian values, etc..
      const std::vector<Real>&  JxW_face     = fe_e->get_JxW();
      const std::vector<Point>& qface_point  = fe_e->get_xyz();
//      const std::vector<Point>& face_normals = fe_e->get_normals();

      // The quadrature points on element f.  These will be computed
      // from the quadrature points on element e.
      std::vector<Point> qp_f;

      // The shape function second derivatives on elements e & f
      const std::vector<std::vector<RealTensor> > & d2phi_e =
		      fe_e->get_d2phi();
      const std::vector<std::vector<RealTensor> > & d2phi_f =
		      fe_f->get_d2phi();

      // The global DOF indices for elements e & f
      std::vector<unsigned int> dof_indices_e;
      std::vector<unsigned int> dof_indices_f;

      // Iterate over all the active elements in the mesh
      // that live on this processor.

      MeshBase::const_element_iterator       elem_it  =
		      mesh.active_local_elements_begin();
      const MeshBase::const_element_iterator elem_end =
		      mesh.active_local_elements_end();

      for (; elem_it != elem_end; ++elem_it)
	{
	  // e is necessarily an active element on the local processor
	  const Elem* e = *elem_it;
	  const unsigned int e_id = e->id();

	  // Loop over the neighbors of element e
	  for (unsigned int n_e=0; n_e<e->n_neighbors(); n_e++)
	    if (e->neighbor(n_e) != NULL) // e is not on the boundary
	      {
		const Elem* f           = e->neighbor(n_e);
		const unsigned int f_id = f->id();

		if (   //-------------------------------------
		    ((f->active()) &&
		     (f->level() == e->level()) &&
		     (e_id < f_id))                 // Case 1.

		    || //-------------------------------------

		    (f->level() < e->level())       // Case 2.

		    )  //-------------------------------------
		  {
		    // Update the shape functions on side s_e of
		    // element e
		    fe_e->reinit (e, n_e);

		    // Build the side
		    AutoPtr<Elem> side (e->side(n_e));

		    // Get the maximum h for this side
		    const Real h = side->hmax();

		    // Get the DOF indices for the two elements
		    dof_map.dof_indices (e, dof_indices_e, var);
		    dof_map.dof_indices (f, dof_indices_f, var);

		    // The number of DOFS on each element
		    const unsigned int n_dofs_e = dof_indices_e.size();
		    const unsigned int n_dofs_f = dof_indices_f.size();

		    // The number of quadrature points
		    const unsigned int n_qp = qrule.n_points();

		    // Find the location of the quadrature points
		    // on element f
		    FEInterface::inverse_map (dim, fe_type, f,
					      qface_point, qp_f);

		    // Compute the shape functions on element f
		    // at the quadrature points of element e
		    fe_f->reinit (f, &qp_f);

		    // The error contribution from this face
		    Real error = 1.e-10;

		    // loop over the integration points on the face
		    for (unsigned int qp=0; qp<n_qp; qp++)
		      {
			// The solution laplacian from each element
			Number lap_e = 0., lap_f = 0.;

			// Compute the solution laplacian on element e
			for (unsigned int i=0; i<n_dofs_e; i++)
			  {
			  lap_e += d2phi_e[i][qp](0,0) *
				system.current_solution(dof_indices_e[i]);
			  lap_e += d2phi_e[i][qp](1,1) *
				system.current_solution(dof_indices_e[i]);
			  }

			// Compute the solution gradient on element f
			for (unsigned int i=0; i<n_dofs_f; i++)
			  {
			  lap_f += d2phi_f[i][qp](0,0) *
				system.current_solution(dof_indices_f[i]);
			  lap_f += d2phi_f[i][qp](1,1) *
				system.current_solution(dof_indices_f[i]);
			  }

			// The flux jump at the face
			const Number jump = lap_e - lap_f;

			// The flux jump squared
#ifndef USE_COMPLEX_NUMBERS
			const Real jump2 = jump*jump;
#else
			const Real jump2 = std::norm(jump);
#endif

			// Integrate the error on the face
			error += JxW_face[qp]*h*jump2;

		      } // End quadrature point loop

		    // Add the error contribution to elements e & f
		    error_per_cell[e_id] += error;
		    error_per_cell[f_id] += error;

		  }
	      } // if (e->neigbor(n_e) != NULL)

	} // End loop over active local elements

    } // End loop over variables

  // Each processor has now computed the error contribuions
  // for its local elements.  We need to sum the vector
  // and then take the square-root of each component.  Note
  // that we only need to sum if we are running on multiple
  // processors, and we only need to take the square-root
  // if the value is nonzero.  There will in general be many
  // zeros for the inactive elements.

  // First sum the vector
  this->reduce_error(error_per_cell);

  // Compute the square-root of each component.
  for (unsigned int i=0; i<error_per_cell.size(); i++)
    if (error_per_cell[i] != 0.)
      error_per_cell[i] = sqrt(error_per_cell[i]);

  STOP_LOG("laplacian_jump()", "LaplacianErrorEstimator");
}
<commit_msg>fix for when second derivatives are absent<commit_after>// $Id: fourth_error_estimators.C,v 1.2 2005-05-27 17:21:25 benkirk Exp $

// The libMesh Finite Element Library.
// Copyright (C) 2002-2004  Benjamin S. Kirk, John W. Peterson

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

// This library is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
// 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

// C++ includes
#include <algorithm> // for std::fill
#include <math.h>    // for sqrt

// Local Includes
#include "libmesh_common.h"
#include "fourth_error_estimators.h"
#include "dof_map.h"
#include "fe.h"
#include "fe_interface.h"
#include "quadrature_clough.h"
#include "libmesh_logging.h"
#include "elem.h"

//-----------------------------------------------------------------
// ErrorEstimator implementations
#ifndef ENABLE_SECOND_DERIVATIVES

void LaplacianErrorEstimator::estimate_error (const System&,
					      std::vector<float>&)
{
  std::cerr << "ERROR:  This functionalitry requires second-derivative support!"
	    << std::endl;
  error();
}

#else // defined (ENABLE_SECOND_DERIVATIVES)

void LaplacianErrorEstimator::estimate_error (const System& system,
					      std::vector<float>& error_per_cell)
{
  START_LOG("laplacian_jump()", "LaplacianErrorEstimator");

  /*

  - e & f are global element ids

  Case (1.) Elements are at the same level, e<f
            Compute the laplacian jump on the face and
	    add it as a contribution to error_per_cell[e]
	    and error_per_cell[f]

                   ----------------------
		  |           |          |
		  |           |    f     |
		  |           |          |
		  |    e      |---> n    |
		  |           |          |
		  |           |          |
                   ----------------------

   Case (2.) The neighbor is at a higher level.
             Compute the laplacian jump on e's face and
	     add it as a contribution to error_per_cell[e]
	     and error_per_cell[f]

                   ----------------------
		  |     |     |          |
		  |     |  e  |---> n    |
		  |     |     |          |
		  |-----------|    f     |
		  |     |     |          |
		  |     |     |          |
		  |     |     |          |
                   ----------------------
*/

  // The current mesh
  const Mesh& mesh = system.get_mesh();

  // The dimensionality of the mesh
  const unsigned int dim = mesh.mesh_dimension();

  // The number of variables in the system
  const unsigned int n_vars = system.n_vars();

  // The DofMap for this system
  const DofMap& dof_map = system.get_dof_map();

  // Resize the error_per_cell vector to be
  // the number of elements, initialize it to 0.
  error_per_cell.resize (mesh.n_elem());
  std::fill (error_per_cell.begin(), error_per_cell.end(), 0.);

  // Check for a valid component_mask
  if (!component_mask.empty())
    if (component_mask.size() != n_vars)
      {
	std::cerr << "ERROR: component_mask is the wrong size:"
		  << std::endl
		  << " component_mask.size()=" << component_mask.size()
		  << std::endl
		  << " n_vars=" << n_vars
		  << std::endl;
	error();
      }

  // Loop over all the variables in the system
  for (unsigned int var=0; var<n_vars; var++)
    {
      // Possibly skip this variable
      if (!component_mask.empty())
	if (component_mask[var] == false) continue;

      // The type of finite element to use for this variable
      const FEType& fe_type = dof_map.variable_type (var);

      // Finite element objects for the same face from
      // different sides
      AutoPtr<FEBase> fe_e (FEBase::build (dim, fe_type));
      AutoPtr<FEBase> fe_f (FEBase::build (dim, fe_type));

      // Build an appropriate Clough-Tocher quadrature rule
      QClough qrule (dim-1, fe_type.default_quadrature_order());

      // Tell the finite element for element e about the quadrature
      // rule.  The finite element for element f need not know about it
      fe_e->attach_quadrature_rule (&qrule);

      // By convention we will always do the integration
      // on the face of element e.  Get its Jacobian values, etc..
      const std::vector<Real>&  JxW_face     = fe_e->get_JxW();
      const std::vector<Point>& qface_point  = fe_e->get_xyz();
//      const std::vector<Point>& face_normals = fe_e->get_normals();

      // The quadrature points on element f.  These will be computed
      // from the quadrature points on element e.
      std::vector<Point> qp_f;

      // The shape function second derivatives on elements e & f
      const std::vector<std::vector<RealTensor> > & d2phi_e =
		      fe_e->get_d2phi();
      const std::vector<std::vector<RealTensor> > & d2phi_f =
		      fe_f->get_d2phi();

      // The global DOF indices for elements e & f
      std::vector<unsigned int> dof_indices_e;
      std::vector<unsigned int> dof_indices_f;

      // Iterate over all the active elements in the mesh
      // that live on this processor.

      MeshBase::const_element_iterator       elem_it  =
		      mesh.active_local_elements_begin();
      const MeshBase::const_element_iterator elem_end =
		      mesh.active_local_elements_end();

      for (; elem_it != elem_end; ++elem_it)
	{
	  // e is necessarily an active element on the local processor
	  const Elem* e = *elem_it;
	  const unsigned int e_id = e->id();

	  // Loop over the neighbors of element e
	  for (unsigned int n_e=0; n_e<e->n_neighbors(); n_e++)
	    if (e->neighbor(n_e) != NULL) // e is not on the boundary
	      {
		const Elem* f           = e->neighbor(n_e);
		const unsigned int f_id = f->id();

		if (   //-------------------------------------
		    ((f->active()) &&
		     (f->level() == e->level()) &&
		     (e_id < f_id))                 // Case 1.

		    || //-------------------------------------

		    (f->level() < e->level())       // Case 2.

		    )  //-------------------------------------
		  {
		    // Update the shape functions on side s_e of
		    // element e
		    fe_e->reinit (e, n_e);

		    // Build the side
		    AutoPtr<Elem> side (e->side(n_e));

		    // Get the maximum h for this side
		    const Real h = side->hmax();

		    // Get the DOF indices for the two elements
		    dof_map.dof_indices (e, dof_indices_e, var);
		    dof_map.dof_indices (f, dof_indices_f, var);

		    // The number of DOFS on each element
		    const unsigned int n_dofs_e = dof_indices_e.size();
		    const unsigned int n_dofs_f = dof_indices_f.size();

		    // The number of quadrature points
		    const unsigned int n_qp = qrule.n_points();

		    // Find the location of the quadrature points
		    // on element f
		    FEInterface::inverse_map (dim, fe_type, f,
					      qface_point, qp_f);

		    // Compute the shape functions on element f
		    // at the quadrature points of element e
		    fe_f->reinit (f, &qp_f);

		    // The error contribution from this face
		    Real error = 1.e-10;

		    // loop over the integration points on the face
		    for (unsigned int qp=0; qp<n_qp; qp++)
		      {
			// The solution laplacian from each element
			Number lap_e = 0., lap_f = 0.;

			// Compute the solution laplacian on element e
			for (unsigned int i=0; i<n_dofs_e; i++)
			  {
			  lap_e += d2phi_e[i][qp](0,0) *
				system.current_solution(dof_indices_e[i]);
			  lap_e += d2phi_e[i][qp](1,1) *
				system.current_solution(dof_indices_e[i]);
			  }

			// Compute the solution gradient on element f
			for (unsigned int i=0; i<n_dofs_f; i++)
			  {
			  lap_f += d2phi_f[i][qp](0,0) *
				system.current_solution(dof_indices_f[i]);
			  lap_f += d2phi_f[i][qp](1,1) *
				system.current_solution(dof_indices_f[i]);
			  }

			// The flux jump at the face
			const Number jump = lap_e - lap_f;

			// The flux jump squared
#ifndef USE_COMPLEX_NUMBERS
			const Real jump2 = jump*jump;
#else
			const Real jump2 = std::norm(jump);
#endif

			// Integrate the error on the face
			error += JxW_face[qp]*h*jump2;

		      } // End quadrature point loop

		    // Add the error contribution to elements e & f
		    error_per_cell[e_id] += error;
		    error_per_cell[f_id] += error;

		  }
	      } // if (e->neigbor(n_e) != NULL)

	} // End loop over active local elements

    } // End loop over variables

  // Each processor has now computed the error contribuions
  // for its local elements.  We need to sum the vector
  // and then take the square-root of each component.  Note
  // that we only need to sum if we are running on multiple
  // processors, and we only need to take the square-root
  // if the value is nonzero.  There will in general be many
  // zeros for the inactive elements.

  // First sum the vector
  this->reduce_error(error_per_cell);

  // Compute the square-root of each component.
  for (unsigned int i=0; i<error_per_cell.size(); i++)
    if (error_per_cell[i] != 0.)
      error_per_cell[i] = sqrt(error_per_cell[i]);

  STOP_LOG("laplacian_jump()", "LaplacianErrorEstimator");
}

#endif // defined (ENABLE_SECOND_DERIVATIVES)
<|endoftext|>