text:
namespace cc {

namespace {

class PixelBufferWorkerPoolTaskImpl : public internal::WorkerPoolTask {
 public:
  typedef base::Callback<void(bool was_canceled, bool needs_upload)> Reply;

  PixelBufferWorkerPoolTaskImpl(internal::RasterWorkerPoolTask* task,
                                uint8_t* buffer,
                                const Reply& reply)
      : task_(task),
        buffer_(buffer),
        reply_(reply),
        needs_upload_(false) {
  }

  // Overridden from internal::WorkerPoolTask:
  virtual void RunOnWorkerThread(unsigned thread_index) OVERRIDE {
    // |buffer_| can be NULL in lost context situations.
    if (!buffer_) {
      // |needs_upload_| still needs to be true as task has not
      // been canceled.
      needs_upload_ = true;
      return;
    }
    SkBitmap bitmap;
    bitmap.setConfig(SkBitmap::kARGB_8888_Config,
                     task_->resource()->size().width(),
                     task_->resource()->size().height());
    bitmap.setPixels(buffer_);
    SkDevice device(bitmap);
    needs_upload_ = task_->RunOnWorkerThread(&device, thread_index);
  }
  virtual void CompleteOnOriginThread() OVERRIDE {
    // |needs_upload_| must be be false if task didn't run.
    DCHECK(HasFinishedRunning() || !needs_upload_);
    reply_.Run(!HasFinishedRunning(), needs_upload_);
  }

 private:
  virtual ~PixelBufferWorkerPoolTaskImpl() {}

  scoped_refptr<internal::RasterWorkerPoolTask> task_;
  uint8_t* buffer_;
  const Reply reply_;
  bool needs_upload_;

  DISALLOW_COPY_AND_ASSIGN(PixelBufferWorkerPoolTaskImpl);
};

// If we raster too fast we become upload bound, and pending
// uploads consume memory. For maximum upload throughput, we would
// want to allow for upload_throughput * pipeline_time of pending
// uploads, after which we are just wasting memory. Since we don't
// know our upload throughput yet, this just caps our memory usage.
#if defined(OS_ANDROID)
// For reference Nexus10 can upload 1MB in about 2.5ms.
const size_t kMaxBytesUploadedPerMs = (2 * 1024 * 1024) / 5;
#else
// For reference Chromebook Pixel can upload 1MB in about 0.5ms.
const size_t kMaxBytesUploadedPerMs = 1024 * 1024 * 2;
#endif

// Assuming a two frame deep pipeline.
const size_t kMaxPendingUploadBytes = 16 * 2 * kMaxBytesUploadedPerMs;

const int kCheckForCompletedRasterTasksDelayMs = 6;

const size_t kMaxScheduledRasterTasks = 48;

typedef base::StackVector<internal::GraphNode*,
                          kMaxScheduledRasterTasks> NodeVector;

void AddDependenciesToGraphNode(
    internal::GraphNode* node,
    const NodeVector::ContainerType& dependencies) {
  for (NodeVector::ContainerType::const_iterator it = dependencies.begin();
       it != dependencies.end(); ++it) {
    internal::GraphNode* dependency = *it;

    node->add_dependency();
    dependency->add_dependent(node);
  }
}

// Only used as std::find_if predicate for DCHECKs.
bool WasCanceled(const internal::RasterWorkerPoolTask* task) {
  return task->WasCanceled();
}

}  // namespace

PixelBufferRasterWorkerPool::PixelBufferRasterWorkerPool(
    ResourceProvider* resource_provider,
    size_t num_threads)
    : RasterWorkerPool(resource_provider, num_threads),
      shutdown_(false),
      scheduled_raster_task_count_(0),
      bytes_pending_upload_(0),
      has_performed_uploads_since_last_flush_(false),
      check_for_completed_raster_tasks_pending_(false),
      should_notify_client_if_no_tasks_are_pending_(false),
      should_notify_client_if_no_tasks_required_for_activation_are_pending_(
          false) {
}

PixelBufferRasterWorkerPool::~PixelBufferRasterWorkerPool() {
  DCHECK(shutdown_);
  DCHECK(!check_for_completed_raster_tasks_pending_);
  DCHECK_EQ(0u, pixel_buffer_tasks_.size());
  DCHECK_EQ(0u, tasks_with_pending_upload_.size());
  DCHECK_EQ(0u, completed_tasks_.size());
}

void PixelBufferRasterWorkerPool::Shutdown() {
  shutdown_ = true;
  RasterWorkerPool::Shutdown();
  RasterWorkerPool::CheckForCompletedTasks();
  CheckForCompletedUploads();
  check_for_completed_raster_tasks_callback_.Cancel();
  check_for_completed_raster_tasks_pending_ = false;
  for (TaskMap::iterator it = pixel_buffer_tasks_.begin();
       it != pixel_buffer_tasks_.end(); ++it) {
    internal::RasterWorkerPoolTask* task = it->first;
    internal::WorkerPoolTask* pixel_buffer_task = it->second.get();

    // All inactive tasks needs to be canceled.
    if (!pixel_buffer_task && !task->HasFinishedRunning()) {
      task->DidRun(true);
      completed_tasks_.push_back(task);
    }
  }
  DCHECK_EQ(completed_tasks_.size(), pixel_buffer_tasks_.size());
}

void PixelBufferRasterWorkerPool::ScheduleTasks(RasterTask::Queue* queue) {
  TRACE_EVENT0("cc", "PixelBufferRasterWorkerPool::ScheduleTasks");

  RasterWorkerPool::SetRasterTasks(queue);

  if (!should_notify_client_if_no_tasks_are_pending_)
    TRACE_EVENT_ASYNC_BEGIN0("cc", "ScheduledTasks", this);

  should_notify_client_if_no_tasks_are_pending_ = true;
  should_notify_client_if_no_tasks_required_for_activation_are_pending_ = true;

  // Build new pixel buffer task set.
  TaskMap new_pixel_buffer_tasks;
  for (RasterTaskVector::const_iterator it = raster_tasks().begin();
       it != raster_tasks().end(); ++it) {
    internal::RasterWorkerPoolTask* task = it->get();
    DCHECK(new_pixel_buffer_tasks.find(task) == new_pixel_buffer_tasks.end());
    DCHECK(!task->HasCompleted());

    // Use existing pixel buffer task if available.
    TaskMap::iterator pixel_buffer_it = pixel_buffer_tasks_.find(task);
    if (pixel_buffer_it == pixel_buffer_tasks_.end()) {
      new_pixel_buffer_tasks[task] = NULL;
      continue;
    }

    new_pixel_buffer_tasks[task] = pixel_buffer_it->second;
    pixel_buffer_tasks_.erase(task);
  }

  // Transfer remaining pixel buffer tasks to |new_pixel_buffer_tasks|
  // and cancel all remaining inactive tasks.
  for (TaskMap::iterator it = pixel_buffer_tasks_.begin();
       it != pixel_buffer_tasks_.end(); ++it) {
    internal::RasterWorkerPoolTask* task = it->first;
    internal::WorkerPoolTask* pixel_buffer_task = it->second.get();

    // Move task to |new_pixel_buffer_tasks|
    new_pixel_buffer_tasks[task] = pixel_buffer_task;

    // Inactive task can be canceled.
    if (!pixel_buffer_task && !task->HasFinishedRunning()) {
      task->DidRun(true);
      DCHECK(std::find(completed_tasks_.begin(),
                       completed_tasks_.end(),
                       task) == completed_tasks_.end());
      completed_tasks_.push_back(task);
    }
  }

  tasks_required_for_activation_.clear();
  for (TaskMap::iterator it = new_pixel_buffer_tasks.begin();
       it != new_pixel_buffer_tasks.end(); ++it) {
    internal::RasterWorkerPoolTask* task = it->first;
    if (IsRasterTaskRequiredForActivation(task))
      tasks_required_for_activation_.insert(task);
  }

  // |tasks_required_for_activation_| contains all tasks that need to
  // complete before we can send a "ready to activate" signal. Tasks
  // that have already completed should not be part of this set.
  for (TaskDeque::const_iterator it = completed_tasks_.begin();
       it != completed_tasks_.end(); ++it) {
    tasks_required_for_activation_.erase(*it);
  }

  pixel_buffer_tasks_.swap(new_pixel_buffer_tasks);

  // Check for completed tasks when ScheduleTasks() is called as
  // priorities might have changed and this maximizes the number
  // of top priority tasks that are scheduled.
  RasterWorkerPool::CheckForCompletedTasks();
  CheckForCompletedUploads();
  FlushUploads();

  // Schedule new tasks.
  ScheduleMoreTasks();

  // Cancel any pending check for completed raster tasks and schedule
  // another check.
  check_for_completed_raster_tasks_callback_.Cancel();
  check_for_completed_raster_tasks_pending_ = false;
  ScheduleCheckForCompletedRasterTasks();

  TRACE_EVENT_ASYNC_STEP1(
      "cc", "ScheduledTasks", this, StateName(),
      "state", TracedValue::FromValue(StateAsValue().release()));
}

void PixelBufferRasterWorkerPool::CheckForCompletedTasks() {
  TRACE_EVENT0("cc", "PixelBufferRasterWorkerPool::CheckForCompletedTasks");

  RasterWorkerPool::CheckForCompletedTasks();
  CheckForCompletedUploads();
  FlushUploads();

  TaskDeque completed_tasks;
  completed_tasks_.swap(completed_tasks);

  while (!completed_tasks.empty()) {
    internal::RasterWorkerPoolTask* task = completed_tasks.front().get();
    DCHECK(pixel_buffer_tasks_.find(task) != pixel_buffer_tasks_.end());

    pixel_buffer_tasks_.erase(task);

    task->WillComplete();
    task->CompleteOnOriginThread();
    task->DidComplete();

    completed_tasks.pop_front();
  }
}

void PixelBufferRasterWorkerPool::OnRasterTasksFinished() {
  // |should_notify_client_if_no_tasks_are_pending_| can be set to false as
  // a result of a scheduled CheckForCompletedRasterTasks() call. No need to
  // perform another check in that case as we've already notified the client.
  if (!should_notify_client_if_no_tasks_are_pending_)
    return;

  // Call CheckForCompletedRasterTasks() when we've finished running all
  // raster tasks needed since last time ScheduleTasks() was called.
  // This reduces latency between the time when all tasks have finished
  // running and the time when the client is notified.
  CheckForCompletedRasterTasks();
}

void PixelBufferRasterWorkerPool::OnRasterTasksRequiredForActivationFinished() {
  // Analogous to OnRasterTasksFinished(), there's no need to call
  // CheckForCompletedRasterTasks() if the client has already been notified.
  if (!should_notify_client_if_no_tasks_required_for_activation_are_pending_)
    return;

  // This reduces latency between the time when all tasks required for
  // activation have finished running and the time when the client is
  // notified.
  CheckForCompletedRasterTasks();
}

void PixelBufferRasterWorkerPool::FlushUploads() {
  if (!has_performed_uploads_since_last_flush_)
    return;

  resource_provider()->ShallowFlushIfSupported();
  has_performed_uploads_since_last_flush_ = false;
}

void PixelBufferRasterWorkerPool::CheckForCompletedUploads() {
  TaskDeque tasks_with_completed_uploads;

  // First check if any have completed.
  while (!tasks_with_pending_upload_.empty()) {
    internal::RasterWorkerPoolTask* task =
        tasks_with_pending_upload_.front().get();

    // Uploads complete in the order they are issued.
    if (!resource_provider()->DidSetPixelsComplete(task->resource()->id()))
      break;

    tasks_with_completed_uploads.push_back(task);
    tasks_with_pending_upload_.pop_front();
  }

  DCHECK(client());
  bool should_force_some_uploads_to_complete =
      shutdown_ || client()->ShouldForceTasksRequiredForActivationToComplete();

  if (should_force_some_uploads_to_complete) {
    TaskDeque tasks_with_uploads_to_force;
    TaskDeque::iterator it = tasks_with_pending_upload_.begin();
    while (it != tasks_with_pending_upload_.end()) {
      internal::RasterWorkerPoolTask* task = it->get();
      DCHECK(pixel_buffer_tasks_.find(task) != pixel_buffer_tasks_.end());

      // Force all uploads required for activation to complete.
      // During shutdown, force all pending uploads to complete.
      if (shutdown_ || IsRasterTaskRequiredForActivation(task)) {
        tasks_with_uploads_to_force.push_back(task);
        tasks_with_completed_uploads.push_back(task);
        it = tasks_with_pending_upload_.erase(it);
        continue;
      }

      ++it;
    }

    // Force uploads in reverse order. Since forcing can cause a wait on
    // all previous uploads, we would rather wait only once downstream.
    for (TaskDeque::reverse_iterator it = tasks_with_uploads_to_force.rbegin();
         it != tasks_with_uploads_to_force.rend();
         ++it) {
      resource_provider()->ForceSetPixelsToComplete((*it)->resource()->id());
      has_performed_uploads_since_last_flush_ = true;
    }
  }

  // Release shared memory and move tasks with completed uploads
  // to |completed_tasks_|.
  while (!tasks_with_completed_uploads.empty()) {
    internal::RasterWorkerPoolTask* task =
        tasks_with_completed_uploads.front().get();

    // It's now safe to release the pixel buffer and the shared memory.
    resource_provider()->ReleasePixelBuffer(task->resource()->id());

    bytes_pending_upload_ -= task->resource()->bytes();

    task->DidRun(false);

    DCHECK(std::find(completed_tasks_.begin(),
                     completed_tasks_.end(),
                     task) == completed_tasks_.end());
    completed_tasks_.push_back(task);

    tasks_required_for_activation_.erase(task);

    tasks_with_completed_uploads.pop_front();
  }
}

void PixelBufferRasterWorkerPool::ScheduleCheckForCompletedRasterTasks() {
  if (check_for_completed_raster_tasks_pending_)
    return;

  check_for_completed_raster_tasks_callback_.Reset(
      base::Bind(&PixelBufferRasterWorkerPool::CheckForCompletedRasterTasks,
                 base::Unretained(this)));
  base::MessageLoopProxy::current()->PostDelayedTask(
      FROM_HERE,
      check_for_completed_raster_tasks_callback_.callback(),
      base::TimeDelta::FromMilliseconds(kCheckForCompletedRasterTasksDelayMs));
  check_for_completed_raster_tasks_pending_ = true;
}

void PixelBufferRasterWorkerPool::CheckForCompletedRasterTasks() {
  TRACE_EVENT0(
      "cc", "PixelBufferRasterWorkerPool::CheckForCompletedRasterTasks");

  DCHECK(should_notify_client_if_no_tasks_are_pending_);

  check_for_completed_raster_tasks_callback_.Cancel();
  check_for_completed_raster_tasks_pending_ = false;

  RasterWorkerPool::CheckForCompletedTasks();
  CheckForCompletedUploads();
  FlushUploads();

  // Determine what client notifications to generate.
  bool will_notify_client_that_no_tasks_required_for_activation_are_pending =
      (should_notify_client_if_no_tasks_required_for_activation_are_pending_ &&
       !HasPendingTasksRequiredForActivation());
  bool will_notify_client_that_no_tasks_are_pending =
      (should_notify_client_if_no_tasks_are_pending_ &&
       !HasPendingTasks());

  // Adjust the need to generate notifications before scheduling more tasks.
  should_notify_client_if_no_tasks_required_for_activation_are_pending_ &=
      !will_notify_client_that_no_tasks_required_for_activation_are_pending;
  should_notify_client_if_no_tasks_are_pending_ &=
      !will_notify_client_that_no_tasks_are_pending;

  scheduled_raster_task_count_ = 0;
  if (PendingRasterTaskCount())
    ScheduleMoreTasks();

  TRACE_EVENT_ASYNC_STEP1(
      "cc", "ScheduledTasks", this, StateName(),
      "state", TracedValue::FromValue(StateAsValue().release()));

  // Schedule another check for completed raster tasks while there are
  // pending raster tasks or pending uploads.
  if (HasPendingTasks())
    ScheduleCheckForCompletedRasterTasks();

  // Generate client notifications.
  if (will_notify_client_that_no_tasks_required_for_activation_are_pending) {
    DCHECK(std::find_if(raster_tasks_required_for_activation().begin(),
                        raster_tasks_required_for_activation().end(),
                        WasCanceled) ==
          raster_tasks_required_for_activation().end());
    client()->DidFinishRunningTasksRequiredForActivation();
  }
  if (will_notify_client_that_no_tasks_are_pending) {
    TRACE_EVENT_ASYNC_END0("cc", "ScheduledTasks", this);
    DCHECK(!HasPendingTasksRequiredForActivation());
    client()->DidFinishRunningTasks();
  }
}

void PixelBufferRasterWorkerPool::ScheduleMoreTasks() {
  TRACE_EVENT0("cc", "PixelBufferRasterWorkerPool::ScheduleMoreTasks");

  enum RasterTaskType {
    PREPAINT_TYPE = 0,
    REQUIRED_FOR_ACTIVATION_TYPE = 1,
    NUM_TYPES = 2
  };
  NodeVector tasks[NUM_TYPES];
  unsigned priority = 2u;  // 0-1 reserved for RasterFinished tasks.
  TaskGraph graph;

  size_t bytes_pending_upload = bytes_pending_upload_;

  for (RasterTaskVector::const_iterator it = raster_tasks().begin();
       it != raster_tasks().end(); ++it) {
    internal::RasterWorkerPoolTask* task = it->get();

    // |pixel_buffer_tasks_| contains all tasks that have not yet completed.
    TaskMap::iterator pixel_buffer_it = pixel_buffer_tasks_.find(task);
    if (pixel_buffer_it == pixel_buffer_tasks_.end())
      continue;

    // HasFinishedRunning() will return true when set pixels has completed.
    if (task->HasFinishedRunning()) {
      DCHECK(std::find(completed_tasks_.begin(),
                       completed_tasks_.end(),
                       task) != completed_tasks_.end());
      continue;
    }

    // All raster tasks need to be throttled by bytes of pending uploads.
    size_t new_bytes_pending_upload = bytes_pending_upload;
    new_bytes_pending_upload += task->resource()->bytes();
    if (new_bytes_pending_upload > kMaxPendingUploadBytes)
      break;

    internal::WorkerPoolTask* pixel_buffer_task = pixel_buffer_it->second.get();

    // If raster has finished, just update |bytes_pending_upload|.
    if (pixel_buffer_task && pixel_buffer_task->HasCompleted()) {
      bytes_pending_upload = new_bytes_pending_upload;
      continue;
    }

    // Throttle raster tasks based on kMaxScheduledRasterTasks.
    size_t scheduled_raster_task_count =
        tasks[PREPAINT_TYPE].container().size() +
        tasks[REQUIRED_FOR_ACTIVATION_TYPE].container().size();
    if (scheduled_raster_task_count >= kMaxScheduledRasterTasks)
      break;

    // Update |bytes_pending_upload| now that task has cleared all
    // throttling limits.
    bytes_pending_upload = new_bytes_pending_upload;

    RasterTaskType type = IsRasterTaskRequiredForActivation(task) ?
        REQUIRED_FOR_ACTIVATION_TYPE :
        PREPAINT_TYPE;

    // Use existing pixel buffer task if available.
    if (pixel_buffer_task) {
      tasks[type].container().push_back(
          CreateGraphNodeForRasterTask(pixel_buffer_task,
                                       task->dependencies(),
                                       priority++,
                                       &graph));
      continue;
    }

    // Request a pixel buffer. This will reserve shared memory.
    resource_provider()->AcquirePixelBuffer(task->resource()->id());

    // MapPixelBuffer() returns NULL if context was lost at the time
    // AcquirePixelBuffer() was called. For simplicity we still post
    // a raster task that is essentially a noop in these situations.
    uint8* buffer = resource_provider()->MapPixelBuffer(
        task->resource()->id());

    scoped_refptr<internal::WorkerPoolTask> new_pixel_buffer_task(
        new PixelBufferWorkerPoolTaskImpl(
            task,
            buffer,
            base::Bind(&PixelBufferRasterWorkerPool::OnRasterTaskCompleted,
                       base::Unretained(this),
                       make_scoped_refptr(task))));
    pixel_buffer_tasks_[task] = new_pixel_buffer_task;
    tasks[type].container().push_back(
        CreateGraphNodeForRasterTask(new_pixel_buffer_task.get(),
                                     task->dependencies(),
                                     priority++,
                                     &graph));
  }

  scoped_refptr<internal::WorkerPoolTask>
      new_raster_required_for_activation_finished_task;

  size_t scheduled_raster_task_required_for_activation_count =
        tasks[REQUIRED_FOR_ACTIVATION_TYPE].container().size();
  DCHECK_LE(scheduled_raster_task_required_for_activation_count,
            tasks_required_for_activation_.size());
  // Schedule OnRasterTasksRequiredForActivationFinished call only when
  // notification is pending and throttling is not preventing all pending
  // tasks required for activation from being scheduled.
  if (scheduled_raster_task_required_for_activation_count ==
      tasks_required_for_activation_.size() &&
      should_notify_client_if_no_tasks_required_for_activation_are_pending_) {
    new_raster_required_for_activation_finished_task =
        CreateRasterRequiredForActivationFinishedTask();
    internal::GraphNode* raster_required_for_activation_finished_node =
        CreateGraphNodeForTask(
            new_raster_required_for_activation_finished_task.get(),
            0u,  // Priority 0
            &graph);
    AddDependenciesToGraphNode(
        raster_required_for_activation_finished_node,
        tasks[REQUIRED_FOR_ACTIVATION_TYPE].container());
  }

  scoped_refptr<internal::WorkerPoolTask> new_raster_finished_task;

  size_t scheduled_raster_task_count =
      tasks[PREPAINT_TYPE].container().size() +
      tasks[REQUIRED_FOR_ACTIVATION_TYPE].container().size();
  DCHECK_LE(scheduled_raster_task_count, PendingRasterTaskCount());
  // Schedule OnRasterTasksFinished call only when notification is pending
  // and throttling is not preventing all pending tasks from being scheduled.
  if (scheduled_raster_task_count == PendingRasterTaskCount() &&
      should_notify_client_if_no_tasks_are_pending_) {
    new_raster_finished_task = CreateRasterFinishedTask();
    internal::GraphNode* raster_finished_node =
        CreateGraphNodeForTask(new_raster_finished_task.get(),
                               1u,  // Priority 1
                               &graph);
    for (unsigned type = 0; type < NUM_TYPES; ++type) {
      AddDependenciesToGraphNode(
          raster_finished_node,
          tasks[type].container());
    }
  }

  SetTaskGraph(&graph);

  scheduled_raster_task_count_ = scheduled_raster_task_count;

  set_raster_finished_task(new_raster_finished_task);
  set_raster_required_for_activation_finished_task(
      new_raster_required_for_activation_finished_task);
}

void PixelBufferRasterWorkerPool::OnRasterTaskCompleted(
    scoped_refptr<internal::RasterWorkerPoolTask> task,
    bool was_canceled,
    bool needs_upload) {
  DCHECK(pixel_buffer_tasks_.find(task.get()) != pixel_buffer_tasks_.end());

  // Balanced with MapPixelBuffer() call in ScheduleMoreTasks().
  resource_provider()->UnmapPixelBuffer(task->resource()->id());

  if (!needs_upload) {
    resource_provider()->ReleasePixelBuffer(task->resource()->id());

    if (was_canceled) {
      // When priorites change, a raster task can be canceled as a result of
      // no longer being of high enough priority to fit in our throttled
      // raster task budget. The task has not yet completed in this case.
      RasterTaskVector::const_iterator it = std::find(raster_tasks().begin(),
                                                      raster_tasks().end(),
                                                      task);
      if (it != raster_tasks().end()) {
        pixel_buffer_tasks_[task.get()] = NULL;
        return;
      }
    }

    task->DidRun(was_canceled);
    DCHECK(std::find(completed_tasks_.begin(),
                     completed_tasks_.end(),
                     task) == completed_tasks_.end());
    completed_tasks_.push_back(task);
    tasks_required_for_activation_.erase(task);
    return;
  }

  DCHECK(!was_canceled);

  resource_provider()->BeginSetPixels(task->resource()->id());
  has_performed_uploads_since_last_flush_ = true;

  bytes_pending_upload_ += task->resource()->bytes();
  tasks_with_pending_upload_.push_back(task);
}

unsigned PixelBufferRasterWorkerPool::PendingRasterTaskCount() const {
  unsigned num_completed_raster_tasks =
      tasks_with_pending_upload_.size() + completed_tasks_.size();
  DCHECK_GE(pixel_buffer_tasks_.size(), num_completed_raster_tasks);
  return pixel_buffer_tasks_.size() - num_completed_raster_tasks;
}

bool PixelBufferRasterWorkerPool::HasPendingTasks() const {
  return PendingRasterTaskCount() || !tasks_with_pending_upload_.empty();
}

bool PixelBufferRasterWorkerPool::HasPendingTasksRequiredForActivation() const {
  return !tasks_required_for_activation_.empty();
}

const char* PixelBufferRasterWorkerPool::StateName() const {
  if (scheduled_raster_task_count_)
    return "rasterizing";
  if (PendingRasterTaskCount())
    return "throttled";
  if (!tasks_with_pending_upload_.empty())
    return "waiting_for_uploads";

  return "finishing";
}

scoped_ptr<base::Value> PixelBufferRasterWorkerPool::StateAsValue() const {
  scoped_ptr<base::DictionaryValue> state(new base::DictionaryValue);

  state->SetInteger("completed_count", completed_tasks_.size());
  state->SetInteger("pending_count", pixel_buffer_tasks_.size());
  state->SetInteger("pending_upload_count", tasks_with_pending_upload_.size());
  state->SetInteger("required_for_activation_count",
                    tasks_required_for_activation_.size());
  state->Set("scheduled_state", ScheduledStateAsValue().release());
  state->Set("throttle_state", ThrottleStateAsValue().release());
  return state.PassAs<base::Value>();
}

scoped_ptr<base::Value> PixelBufferRasterWorkerPool::ThrottleStateAsValue()
    const {
  scoped_ptr<base::DictionaryValue> throttle_state(new base::DictionaryValue);

  throttle_state->SetInteger("bytes_available_for_upload",
                             kMaxPendingUploadBytes - bytes_pending_upload_);
  throttle_state->SetInteger("bytes_pending_upload", bytes_pending_upload_);
  throttle_state->SetInteger("scheduled_raster_task_count",
                             scheduled_raster_task_count_);
  return throttle_state.PassAs<base::Value>();
}

}  // namespace cc


text:
#ifndef __STDLIB_H__
#define __STDLIB_H__

#include <libcgc.h>

#define RAND_MAX	2147483647
#define MAGIC_PAGE 0x4347c000

int rand( void );
void srand( unsigned int seed );

int atoi( const char *pStr );
double atof( char *pStr );

char *strcpy( char *pDest, const char *pSource );
char *strncpy( char *pDest, const char *pSource, size_t maxlen );
void *cgc_memcpy( void *pDest, const void *pSrc, size_t nbytes );

long int strtol( const char *str, char **endptr, int base );

#endif // STDLIB_H__

redpajama_set_name: RedPajamaGithub


text:
/*
Class: Graphic.Rectangle
	Shape implementation of a rectangle. A Rectangle can have rounded corners

  Author:
  	Sébastien Gruhier, <http://www.xilinus.com>

  License:
  	MIT-style license.
*/
Graphic.Rectangle = Class.create();
Object.extend(Graphic.Rectangle.prototype, Graphic.Shape.prototype);

// Keep parent initialize
Graphic.Rectangle.prototype._shapeInitialize = Graphic.Shape.prototype.initialize;

Object.extend(Graphic.Rectangle.prototype, {
  // Group: Shape functions
  // See Also:
  // <Shape>
  initialize: function(renderer) {
    this._shapeInitialize(renderer, "rect");
    Object.extend(this.attributes, {x:0, y:0, w:0, h:0, rx: 0, ry: 0});
    return this;
  },

  getSize: function() {
    return {w: this.attributes.width, h: this.attributes.height}
  },

  setSize: function(width, height) {
    this._setAttributes({width: width, height: height});
    return this;
  },

  getLocation: function() {
    return {x: this.attributes.x, y: this.attributes.y}
  },

  setLocation: function(x, y) {
    this._setAttributes({x: x, y: y});
    return this;
  },

  // Group: Specific Rectangle Functions
  /*
    Function: setRoundCorner
      Sets round corners values in pixel

    Parameters:
      rx - round X value
      ry - round Y value

    Returns:
      this
  */
  setRoundCorner: function(rx, ry) {
    rx = Math.max(0, rx);
    ry = Math.max(0, ry);
    if (! ry)
      ry = rx;
    this._setAttributes({rx: rx, ry: ry});
    return this;
  },

  /*
    Function: getRoundCorner
      Gets round corners values in pixel

    Returns:
      An hash table {rx:, ry:}
  */
  getRoundCorner: function(rx, ry) {
    return  {rx: this.attributes.rx, ry: this.attributes.ry}
  }
})


text:
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/1999/REC-html401-19991224/loose.dtd">

    <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
    <title>toneBurst :: Functions (k-Wave)</title>
    <link rel="stylesheet" href="docstyle.css" type="text/css">

            k-Wave Toolbox

toneBurst

Create an enveloped single frequency tone burst

Syntax

signal = toneBurst(sample_freq, signal_freq, num_cycles)
signal = toneBurst(sample_freq, signal_freq, num_cycles, ...)

Description

toneBurst creates an enveloped single frequency tone burst for use in ultrasound simulations. If an array is given for the optional input 'SignalOffset', a matrix of tone bursts is created where each row corresponds to a tone burst for particular value of the 'SignalOffset'. If a value for the optional input 'SignalLength' is given, the tone burst/s are zero padded to this length (in samples). For example, running

toneBurst(20e6, 1e6, 10, 'Plot', true);

will return and plot a 1 MHz tone burst with 10 cycles and a Gaussian envelope sampled at 20 MHz.

Inputs

sample_freq

sampling frequency [Hz]

signal_freq

signal frequency [Hz]

num_cycles

number of sinusoidal oscillations

Optional Inputs

Optional 'string', value pairs that may be used to modify the default computational settings.

    <colgroup>
        <col width="18%"><col width="18%"><col width="18%"><col width="46%">
    </colgroup>

            Input
            Valid Settings
            Default
            Description

'Envelope'

'Gaussian'
'Rectangular'

'Gaussian'

Envelope used to taper the tone burst.

'Plot'

(Boolean scalar)

false

Boolean controlling whether the created tone burst is plotted.

'SignalLength'

(integer)

'auto'

Signal length in number of samples. If longer than the tone burst length, the signal is appended with zeros.

'SignalOffset'

(integer)

0

Signal offset before the tone burst starts in number of samples.

Outputs

signal

created tone burst

Examples

Steering A Linear Array

Snell's Law And Critical Angle Reflection

See Also

gaussian

        timeShift

        unmaskSensorData

© 2009-2014 Bradley Treeby and Ben Cox.


text:
namespace arangodb {
namespace aql {

std::ostream& operator<<(std::ostream& ostream, ExecutionState state) {
  switch (state) {
    case ExecutionState::DONE:
      ostream << "DONE";
      break;
    case ExecutionState::HASMORE:
      ostream << "HASMORE";
      break;
    case ExecutionState::WAITING:
      ostream << "WAITING";
      break;
  }
  return ostream;
}

}  // namespace aql
}  // namespace arangodb


text:
MQTT tutorials source codes
==============

Example of MQTT application for web
mqttSim - MQTT simulator which sends random data to a broker
mqttClient - web client which connects to a broker and gets data from it, also can send some managing mesages.


text:
This page describes the process of developing extra components.

# Apps

## Extending app with Colabo features

Added `colabo.config.js` configiration file in the frontend root

Updated `tsconfig.json` with include to puzzles (although it didn't complain?!)

TODO:

+ Instructions on
    + adding Colabo.Space repo to the system
        + maybe avoid it, just put in npm dependencies external built npm packages
    + adding colabo.tools globally
        + maybe not necessary, only for development
        + and even then it can be just global build, same as ng, etc
    + external puzzles from Colabo.Space
        + probably not necessary
        + maybe avoid it, just put in npm dependencies external built npm packages

## Creating a new App (Frontend)

- duplicate the folder of an old existing app
-  **package.json** file
  - give the new value for the app-name: **name** parameter
  - in the **scripts** node, we should give the new port for the `"start": "npx ng serve -o --port 8887"` to prevent  their overlapping. Look for a free next port at the lower paragraph **Apps Ports**
-  in the **angular.json** file rename the project name. Under the node "**projects**", you will see an entry with name resembling name of the app (e.g."collective_sustainable_activism") you should rename in whole the file that name with the new desired project name
- **IMPORTANT**: we depends on symbolic links!
  - we are in the development mode
  - therefore it is very important to have the parameter `preserveSymlinks` in `angular.json` set to `true`
  - by default `angular-cli` do not set it

```json
{
    "projects": {
        "play-sound": {
            "architect": {
                "build": {
                    "options": {
                        "preserveSymlinks": true,
// ...
```

- colabo.config.js
  - rename **puzzles/name** node and the **puzzles/description** node

## Apps Ports

- NCA (Networking for Collective Activism i.e. CoLaboArthon-Collective-Sustainable-Activism): **8887**
- Performing Sustainable CoEvolution (PSC): **8891**
-

# Linked puzzles / components

If you want to develop all components, you should remove some of npm packages, that can be linked instead from local folders containing them. Please see in the [DEVELOPMENT CHEATSHEET](DEVELOPMENT_CHEATSHEET.md) document.

## Branching

If you want to develop additional feature, the safest procedure is to create a separate git branch. **NOTE**: This requires developer write access to the CF project.

References:
+ [3.2 Git Branching - Basic Branching and Merging](https://git-scm.com/book/en/v2/Git-Branching-Basic-Branching-and-Merging)
+ [Create a new branch with git and manage branches](https://github.com/Kunena/Kunena-Forum/wiki/Create-a-new-branch-with-git-and-manage-branches)
+ [Using Branches](https://www.atlassian.com/git/tutorials/using-branches/)
+ [SO - Git create branch from current checked out master?](http://stackoverflow.com/questions/1453129/git-create-branch-from-current-checked-out-master)

### creating

You should create a new branch, let's call it `cf-puzzle-ibis`. This will be our new branch where we will create a new CF puzzle,

To create a branch and switch to it at the same time, you can run the git checkout command with the -b switch:

```sh
git checkout -b cf-puzzle-ibis
```

NOTE: This is shorthand for:

```sh
git branch cf-puzzle-ibis
git checkout cf-puzzle-ibis
```

Push the dev branch on the github:

```sh
git push origin cf-puzzle-ibis
```

You can see all branches created by using :

```sh
git branch
```

You can rename branch with:

```sh
git branch -m <new-branch-name>
```

### Updating dev branch(es)

While developing in other development branches, you should constantly update them with master branch. This will help later merging back easier and with less conflicts.

You do that by being in dev branch (switch to `git checkout cf-puzzle-ibis`) and issuing the following command in the git folder in order to merge all updates from master into our dev branch:

```sh
git merge master
```

NOTE: We might need to fix some conflicts. To see the merging status and conflicts you can run:

```sh
git status
```

You can merge them with editor or run visual tool:

```sh
git mergetool
```

After fixing all conflicts you should commit again:

```sh
git commit
```

# Merging dev-branch into master

After you achieved stable functionality in your dev branch, you should merge it back to the master branch and share with the master code and other developers and users :)

We need to be in (switch to `git checkout master`) the master branch and work from
there.

Now we can merge our dev branch back to the master branch:

```sh
git merge cf-puzzle-ibis
```

To merge the specified branch into the current branch, but always generate a merge commit (even if it was a `fast-forward` merge). This is useful for *documenting all merges* that occur in your repository:

```sh
git merge --no-ff cf-puzzle-ibis
```

Then we should pull latest changes from the server:

```sh
git pull origin master
```

and we should we push it back to the server

```sh
git push origin master
```

Delete local developer branch

After we are finished with dev branch and merged it into master, then we can delete the local dev branch:

```sh
git branch -d cf-puzzle-ibis
```

If there is some "garbage" in the dev branch that you didn't want to commit and merge you need to do forced deleting:

```sh
git branch -D cf-puzzle-ibis
```

# Install Virtual Box with Ubuntu on OSX

- Some of [extra tips](https://www.lifewire.com/run-ubuntu-within-windows-virtualbox-2202098)
- Download and install [VirtualBox](https://www.virtualbox.org/wiki/Downloads)
- Download [Server Ubuntu](https://www.ubuntu.com/download/server)

Settings

- devices > shared clipboard > bidirectional
- devices > drag and drop > bidirectional

```sh
sudo updatedb
locate development
```

Tests

```sh
uname -a
sudo apt-get update
sudo apt-get install joe
```

## Mounting

Install guest tools

copy from the Applications/VirtualBox.app/Contents/MacOS the file **VBoxGuestAdditions.iso** somewhere else where it is accessible

mount it in the optical disk

```sh
sudo mount /dev/cdrom /media/cdrom
```

install build support

```sh
sudo apt-get install -y dkms build-essential linux-headers-generic linux-headers-$(uname -r)
```

install guest tools

```sh
sudo /media/cdrom/VBoxLinuxAdditions.ru
sudo adduser colabo vboxsf
logout
```

Add shared folder inside the VirtualBox:

- go to settings > Shared Folders , ad add the folder (make it auto-mount ad permanent)
- for example: development

Locate shared folder inside the virtual guest system

```sh
cd /media/sf_development
```

## Node

- https://nodejs.org/en/download/package-manager/#debian-and-ubuntu-based-linux-distributions

``````sh
curl -sL https://deb.nodesource.com/setup_5.x | sudo -E bash -
sudo apt-get install -y nodejs
``````

## Git

```sh
sudo apt-get install git
```

## Mongodb

```sh
sudo apt-get install -y mongodb
```

Start MongoDB:

```sh
sudo service mongod start
```

Verify that MongoDB has started successfully:

```sh
grep "waiting for connections" /var/log/mongodb/mongod.log
```

Logs: `/var/log/mongodb`
**Databases**: `/var/lib/mongodb`

## Node

- https://nodejs.org/en/download/package-manager/#debian-and-ubuntu-based-linux-distributions

```sh
curl -sL https://deb.nodesource.com/setup_6.x | sudo -E bash -
sudo apt-get install -y nodejs
node -v
```

## Frontend

```sh
sudo npm install gulp -g
sudo npm i typings -g
sudo npm install -g bower
```

# Installing SASS support

```sh
sudo apt-get install -y ruby
sudo apt-get install -y ruby-all-dev
ruby -v
sudo gem install sass
sudo gem install compass
sudo gem install susy
sudo gem install breakpoint
sudo gem install normalize-scss
sudo gem install font-awesome-sass -v 4.3.2.1
```

## Zhenia

+ highlight node/text


text:
import sys
import os
import math
import shutil

resultDir = os.environ.get('RESULTS')
if resultDir == None :
    print ("WARNING! $RESULTS not set! Attempt to write results will fail!\n")

# Expecting input botConc, topConc, rateConstFull, sysSize, analInterval, numStepsEquilib, numStepsSnapshot, numStepsAnal, numStepsReq, numPasses, timeInterval,  fileCode

from KMCLib import *
from KMCLib.Backend import Backend
import numpy
from RateCalc import *
from DensHist import *

botConc = float(sys.argv[1])
topConc = float(sys.argv[2])
rateConstFull = float(sys.argv[3])
sysWidth = int(sys.argv[4])
sysLength = int(sys.argv[5])
analInterval = int(sys.argv[6])
numStepsEquilib = int(sys.argv[7])
numStepsSnapshot = int(sys.argv[8])
numStepsAnal = int(sys.argv[9])
numStepsReq = int(sys.argv[10])
numPasses = int(sys.argv[11])
timeInterval = float(sys.argv[12])
fileInfo = sys.argv[13]

resultsPlace = resultDir+"/"+fileInfo+"/"

if not os.path.exists(resultsPlace):
    os.makedirs(resultsPlace)

with open(resultsPlace+'settings', 'w') as f:
    f.write('BotConcentration = ' + str(botConc) +'\n')
    f.write('TopConcentration = ' + str(topConc) +'\n')
    f.write('FullRate = ' + str(rateConstFull) +'\n')
    f.write('SysWidth = ' + str(sysWidth) +'\n')
    f.write('SysLength = ' + str(sysLength) +'\n')
    f.write('TimeInterval = ' + str(timeInterval) +'\n')
    f.write('AnalInterval = ' +str(analInterval) + '\n')
    f.write('NumStepsEquilib = '+str(numStepsEquilib) +'\n')
    f.write('NumStepsSnapshot = '+str(numStepsSnapshot)+'\n')
    f.write('NumStepsAnal = '+str(numStepsAnal) +'\n')

"""I've put this in the file to make command line input easier"""
# Load the configuration and interactions.
# We're in 2d
cell_vectors = [[1.0,0.0,0.0],
                [0.0,1.0,0.0],
                [0.0,0.0,1.0]]

# Only bothering with one set
basis_points = [[0.0, 0.0, 0.0]]

unit_cell = KMCUnitCell(cell_vectors=cell_vectors,
                        basis_points=basis_points)

# Define the lattice.
xRep = sysWidth
yRep = sysLength + 4
zRep = 1
numPoints = xRep*zRep*yRep
lattice = KMCLattice(unit_cell=unit_cell,
                     repetitions=(xRep,yRep,zRep),
                     periodic=(True, True, False))

# Generate the initial types. There's double-layered section of "To" at the top and "Bo" at the bottom
avConc = 0.5*(botConc+topConc)

types = []

for yIndex in range(0, 2):
    for xIndex in range(0, xRep):
        random = numpy.random.rand()
        if random < botConc:
            types.append((xIndex, yIndex, 0, 0, "BoO"))
        else:
            types.append((xIndex, yIndex, 0, 0, "BoV"))

for yIndex in range(2, yRep-2):
    for xIndex in range(0, xRep):
        random = numpy.random.rand()
        if random < avConc:
            types.append((xIndex, yIndex, 0, 0, "O"))
        else:
            types.append((xIndex, yIndex, 0, 0, "V"))
for yIndex in range(yRep-2, yRep):
    for xIndex in range(0, xRep):
        random = numpy.random.rand()
        if random < topConc:
            types.append((xIndex, yIndex, 0, 0, "ToO"))
        else:
            types.append((xIndex, yIndex, 0, 0, "ToV"))

# Setup the configuration.
configuration = KMCConfiguration(lattice=lattice,
                                 types=types,
                                 possible_types=["O","V","ToV","BoV", "ToO", "BoO"], default_type="V")

# Rates.
rateConstEmpty        	= 1.0
topSpawn = rateConstFull*rateConstFull*math.sqrt(topConc/(1.0-topConc))
botSpawn = rateConstFull*rateConstFull*math.sqrt(botConc/(1.0-botConc))
topDespawn = (rateConstFull**4)/topSpawn
botDespawn = (rateConstFull**4)/botSpawn

#
##
###
"""I've put the processes in here to make it easier to adjust them via command line arguments."""

# Fill the list of processes.
processes = []

# Only on the first set of basis_points for O/V
basis_sites     = [0]

# Bulk processes

# Up
#0
elements_before = ["O", "V"]
elements_after  = ["V", "O"]
coordinates = [[0.0, 0.0,  0.0], [0.0, 1.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))
# Will customise

# Down
#1
elements_before = ["O", "V"]
elements_after  = ["V", "O"]
coordinates = [[0.0, 0.0, 0.0], [0.0, -1.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))
# Will customise

# Left
#2
elements_before = ["O", "V"]
elements_after  = ["V", "O"]
coordinates = [[0.0, 0.0,  0.0], [-1.0, 0.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))
# Will customise

# Right
#3
elements_before = ["O", "V"]
elements_after  = ["V", "O"]
coordinates = [[0.0, 0.0, 0.0], [1.0, 0.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))
# Will customise

# Oxygen annihilation at the top boundary
#4
elements_before = ["O", "ToV"]
elements_after  = ["V", "ToV"]
coordinates = [[0.0, 0.0, 0.0], [0.0, 1.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Oxygen creation at the top boundary
#5
elements_before = ["ToO", "V"]
elements_after  = ["ToO", "O"]
coordinates = [[0.0, 0.0, 0.0], [0.0, -1.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Now for Oxygen annihilation at the bottom boundary
#6
elements_before = ["O", "BoV"]
elements_after  = ["V", "BoV"]
coordinates = [[0.0, 0.0, 0.0], [0.0, -1.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Oxygen creation at the bottom boundary
#7
elements_before = ["BoO", "V"]
elements_after  = ["BoO", "O"]
coordinates = [[0.0, 0.0, 0.0], [0.0, 1.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Boundary Oxygen creation at the bottom boundary
#8
elements_before = ["BoV"]
elements_after  = ["BoO"]
coordinates = [[0.0, 0.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Boundary Oxygen annihilation at the bottom boundary
#9
elements_before = ["BoO"]
elements_after  = ["BoV"]
coordinates = [[0.0, 0.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Boundary Oxygen creation at the top boundary
#10
elements_before = ["ToV"]
elements_after  = ["ToO"]
coordinates = [[0.0, 0.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Boundary Oxygen annihilation at the top boundary
#11
elements_before = ["ToO"]
elements_after  = ["ToV"]
coordinates = [[0.0, 0.0, 0.0]]
processes.append( KMCProcess(coordinates=coordinates,
                             elements_before=elements_before,
                             elements_after=elements_after,
                             basis_sites=basis_sites,
                             rate_constant=1.0))

# Create the interactions object.
interactions = KMCInteractions(processes, implicit_wildcards=True)

# Define the custom rates calculator, using the lol model as a template
class modelRates2d(KMCRateCalculatorPlugin):
    # Class for defining the custom rates function for the KMCLib paper.
    def rate(self, geometry, elements_before, elements_after, rate_constant, process_number, global_coordinate):
        if process_number == 8:
            return botSpawn

        if process_number == 9:
            return botDespawn

        if process_number == 10:
            return topSpawn

        if process_number == 11:
            return topDespawn

        numNeighbours = len([e for e in elements_before if e == "O"]) + len([e for e in elements_before if e == "ToO"]) + len([e for e in elements_before if e == "BoO"])

        return math.pow(rateConstFull, numNeighbours-1)

    def cutoff(self):
        # Overloaded base class API function
        return 1.0

interactions.setRateCalculator(rate_calculator=modelRates2d)
"""End of processes"""
###
##
#

# Create the model.
model = KMCLatticeModel(configuration, interactions)

compositionTracker = Composition(time_interval=timeInterval)

# Define the parameters; not entirely sure if these are sensible or not...
control_parameters_equilib = KMCControlParameters(number_of_steps=numStepsEquilib, analysis_interval=numStepsEquilib/100,
                                          dump_interval=numStepsEquilib/10)

control_parameters_req = KMCControlParameters(number_of_steps=numStepsReq, analysis_interval=numStepsReq/100,
                                          dump_interval=numStepsReq/10)

control_parameters_anal = KMCControlParameters(number_of_steps=numStepsAnal, analysis_interval=1,
                                          dump_interval=numStepsAnal/10)

# Run the simulation - save trajectory to resultsPlace, which should by now exist

model.run(control_parameters_equilib, trajectory_filename=(resultsPlace+"equilib.traj"))

with open(resultsPlace+"inBot.dat", 'w') as f:
    pass
with open(resultsPlace+"outBot.dat", 'w') as f:
    pass
with open(resultsPlace+"inTop.dat", 'w') as f:
    pass
with open(resultsPlace+"outTop.dat", 'w') as f:
    pass

if not os.path.exists(resultsPlace+"numHists"):
    os.makedirs(resultsPlace+"numHists")

ovNumHist = []
for index in range(0, numPoints):
    ovNumHist.append(0.0)

for passNum in range(0, numPasses):
    processStatsOxInBot = RateCalc(processes=[7])
    processStatsOxOutBot = RateCalc(processes=[6])
    processStatsOxInTop = RateCalc(processes=[5])
    processStatsOxOutTop = RateCalc(processes=[4])
    numHist = DensHist(spec=["O"], inProc=[7, 5], outProc=[6, 4])
    model.run(control_parameters_req, trajectory_filename=("/dev/null"))
    model.run(control_parameters_anal, trajectory_filename=("/dev/null"), analysis=[processStatsOxInBot, processStatsOxOutBot, processStatsOxInTop, processStatsOxOutTop, numHist])

    with open(resultsPlace+"inBot.dat", 'a') as f:
        processStatsOxInBot.printResults(f)
    with open(resultsPlace+"outBot.dat", 'a') as f:
        processStatsOxOutBot.printResults(f)
    with open(resultsPlace+"inTop.dat", 'a') as f:
        processStatsOxInTop.printResults(f)
    with open(resultsPlace+"outTop.dat", 'a') as f:
        processStatsOxOutTop.printResults(f)
    with open(resultsPlace+"numHists/numHist"+str(passNum)+".dat", 'w') as f:
        pass
    with open(resultsPlace+"numHists/numHist"+str(passNum)+".dat", 'a') as f:
        numHist.printResults(f)
    with open(resultsPlace+"numHists/numHist"+str(passNum)+".dat", 'r') as f:
        lines = f.readlines()
        for index in range(0, numPoints):
            words = lines[index].split()
            ovNumHist[index] += float(words[1])
    os.remove(resultsPlace+"numHists/numHist"+str(passNum)+".dat")

with open(resultsPlace+"ovNumHist.dat", 'w') as f:
    for index in range(0, numPoints):
        f.write(str(index)+" "+str(ovNumHist[index])+"\n")

shutil.rmtree(resultsPlace+"numHists", ignore_errors=True)

print("Process would appear to have succesfully terminated! How very suspicious...")


text:
from setuptools import setup, find_packages

setup(
    name='alarm_disk_usage',
    version='0.1dev',
    packages=find_packages(),
    entry_points = {
        'contrail.analytics.alarms': [
            'ObjectDatabaseInfo = alarm_disk_usage.main:DiskUsage',
            'ObjectVRouter = alarm_disk_usage.main:DiskUsage',
            'ObjectConfigNode = alarm_disk_usage.main:DiskUsage',
            'ObjectCollectorInfo = alarm_disk_usage.main:DiskUsage',
            'ObjectBgpRouter = alarm_disk_usage.main:DiskUsage',
        ],
    },
    zip_safe=False,
    long_description="DiskUsage Alarm"
)


text:
from __future__ import absolute_import, division, print_function
__metaclass__ = type

ANSIBLE_METADATA = {'metadata_version': '1.1',
                    'status': ['preview'],
                    'supported_by': 'community'}

DOCUMENTATION = '''
---
module: os_quota
short_description: Manage OpenStack Quotas
extends_documentation_fragment: openstack
version_added: "2.3"
author: "Michael Gale (@mgale) <gale.michael@gmail.com>"
description:
    - Manage OpenStack Quotas. Quotas can be created,
      updated or deleted using this module. A quota will be updated
      if matches an existing project and is present.
options:
    name:
        description:
            - Name of the OpenStack Project to manage.
        required: true
    state:
        description:
            - A value of present sets the quota and a value of absent resets the quota to system defaults.
        default: present
    backup_gigabytes:
        description: Maximum size of backups in GB's.
    backups:
        description: Maximum number of backups allowed.
    cores:
        description: Maximum number of CPU's per project.
    fixed_ips:
        description: Number of fixed IP's to allow.
    floating_ips:
        description: Number of floating IP's to allow in Compute.
        aliases: ['compute_floating_ips']
    floatingip:
        description: Number of floating IP's to allow in Network.
        aliases: ['network_floating_ips']
    gigabytes:
        description: Maximum volume storage allowed for project.
    gigabytes_lvm:
        description: Maximum size in GB's of individual lvm volumes.
    injected_file_size:
        description: Maximum file size in bytes.
    injected_files:
        description: Number of injected files to allow.
    injected_path_size:
        description: Maximum path size.
    instances:
        description: Maximum number of instances allowed.
    key_pairs:
        description: Number of key pairs to allow.
    loadbalancer:
        description: Number of load balancers to allow.
        version_added: "2.4"
    network:
        description: Number of networks to allow.
    per_volume_gigabytes:
        description: Maximum size in GB's of individual volumes.
    pool:
        description: Number of load balancer pools to allow.
        version_added: "2.4"
    port:
        description: Number of Network ports to allow, this needs to be greater than the instances limit.
    properties:
        description: Number of properties to allow.
    ram:
        description: Maximum amount of ram in MB to allow.
    rbac_policy:
        description: Number of policies to allow.
    router:
        description: Number of routers to allow.
    security_group_rule:
        description: Number of rules per security group to allow.
    security_group:
        description: Number of security groups to allow.
    server_group_members:
        description: Number of server group members to allow.
    server_groups:
        description: Number of server groups to allow.
    snapshots:
        description: Number of snapshots to allow.
    snapshots_lvm:
        description: Number of LVM snapshots to allow.
    subnet:
        description: Number of subnets to allow.
    subnetpool:
        description: Number of subnet pools to allow.
    volumes:
        description: Number of volumes to allow.
    volumes_lvm:
        description: Number of LVM volumes to allow.
    availability_zone:
      description:
        - Ignored. Present for backwards compatibility

requirements:
    - "python >= 2.7"
    - "openstacksdk >= 0.13.0"
    - "keystoneauth1 >= 3.4.0"
'''

EXAMPLES = '''
# List a Project Quota
- os_quota:
    cloud: mycloud
    name: demoproject

# Set a Project back to the defaults
- os_quota:
    cloud: mycloud
    name: demoproject
    state: absent

# Update a Project Quota for cores
- os_quota:
    cloud: mycloud
    name: demoproject
    cores: 100

# Update a Project Quota
- os_quota:
    name: demoproject
    cores: 1000
    volumes: 20
    volumes_type:
      - volume_lvm: 10

# Complete example based on list of projects
- name: Update quotas
  os_quota:
    name: "{{ item.name }}"
    backup_gigabytes: "{{ item.backup_gigabytes }}"
    backups: "{{ item.backups }}"
    cores: "{{ item.cores }}"
    fixed_ips: "{{ item.fixed_ips }}"
    floating_ips: "{{ item.floating_ips }}"
    floatingip: "{{ item.floatingip }}"
    gigabytes: "{{ item.gigabytes }}"
    injected_file_size: "{{ item.injected_file_size }}"
    injected_files: "{{ item.injected_files }}"
    injected_path_size: "{{ item.injected_path_size }}"
    instances: "{{ item.instances }}"
    key_pairs: "{{ item.key_pairs }}"
    loadbalancer: "{{ item.loadbalancer }}"
    per_volume_gigabytes: "{{ item.per_volume_gigabytes }}"
    pool: "{{ item.pool }}"
    port: "{{ item.port }}"
    properties: "{{ item.properties }}"
    ram: "{{ item.ram }}"
    security_group_rule: "{{ item.security_group_rule }}"
    security_group: "{{ item.security_group }}"
    server_group_members: "{{ item.server_group_members }}"
    server_groups: "{{ item.server_groups }}"
    snapshots: "{{ item.snapshots }}"
    volumes: "{{ item.volumes }}"
    volumes_types:
      volumes_lvm: "{{ item.volumes_lvm }}"
    snapshots_types:
      snapshots_lvm: "{{ item.snapshots_lvm }}"
    gigabytes_types:
      gigabytes_lvm: "{{ item.gigabytes_lvm }}"
  with_items:
    - "{{ projects }}"
  when: item.state == "present"
'''

RETURN = '''
openstack_quotas:
    description: Dictionary describing the project quota.
    returned: Regardless if changes where made or not
    type: complex
    contains:
        openstack_quotas: {
            compute: {
                cores: 150,
                fixed_ips: -1,
                floating_ips: 10,
                injected_file_content_bytes: 10240,
                injected_file_path_bytes: 255,
                injected_files: 5,
                instances: 100,
                key_pairs: 100,
                metadata_items: 128,
                ram: 153600,
                security_group_rules: 20,
                security_groups: 10,
                server_group_members: 10,
                server_groups: 10
            },
            network: {
                floatingip: 50,
                loadbalancer: 10,
                network: 10,
                pool: 10,
                port: 160,
                rbac_policy: 10,
                router: 10,
                security_group: 10,
                security_group_rule: 100,
                subnet: 10,
                subnetpool: -1
            },
            volume: {
                backup_gigabytes: 1000,
                backups: 10,
                gigabytes: 1000,
                gigabytes_lvm: -1,
                per_volume_gigabytes: -1,
                snapshots: 10,
                snapshots_lvm: -1,
                volumes: 10,
                volumes_lvm: -1
            }
        }

'''

import traceback

KEYSTONEAUTH1_IMP_ERR = None
try:
    from keystoneauth1 import exceptions as ksa_exceptions
    HAS_KEYSTONEAUTH1 = True
except ImportError:
    KEYSTONEAUTH1_IMP_ERR = traceback.format_exc()
    HAS_KEYSTONEAUTH1 = False

from ansible.module_utils.basic import AnsibleModule, missing_required_lib
from ansible.module_utils.openstack import openstack_full_argument_spec, openstack_module_kwargs, openstack_cloud_from_module

def _get_volume_quotas(cloud, project):

    return cloud.get_volume_quotas(project)

def _get_network_quotas(cloud, project):

    return cloud.get_network_quotas(project)

def _get_compute_quotas(cloud, project):

    return cloud.get_compute_quotas(project)

def _get_quotas(sdk, module, cloud, project):

    quota = {}
    try:
        quota['volume'] = _get_volume_quotas(cloud, project)
    except ksa_exceptions.EndpointNotFound:
        module.warn("No public endpoint for volumev2 service was found. Ignoring volume quotas.")

    try:
        quota['network'] = _get_network_quotas(cloud, project)
    except ksa_exceptions.EndpointNotFound:
        module.warn("No public endpoint for network service was found. Ignoring network quotas.")

    quota['compute'] = _get_compute_quotas(cloud, project)

    for quota_type in quota.keys():
        quota[quota_type] = _scrub_results(quota[quota_type])

    return quota

def _scrub_results(quota):

    filter_attr = [
        'HUMAN_ID',
        'NAME_ATTR',
        'human_id',
        'request_ids',
        'x_openstack_request_ids',
    ]

    for attr in filter_attr:
        if attr in quota:
            del quota[attr]

    return quota

def _system_state_change_details(module, project_quota_output):

    quota_change_request = {}
    changes_required = False

    for quota_type in project_quota_output.keys():
        for quota_option in project_quota_output[quota_type].keys():
            if quota_option in module.params and module.params[quota_option] is not None:
                if project_quota_output[quota_type][quota_option] != module.params[quota_option]:
                    changes_required = True

                    if quota_type not in quota_change_request:
                        quota_change_request[quota_type] = {}

                    quota_change_request[quota_type][quota_option] = module.params[quota_option]

    return (changes_required, quota_change_request)

def _system_state_change(module, project_quota_output):
    """
    Determine if changes are required to the current project quota.

    This is done by comparing the current project_quota_output against
    the desired quota settings set on the module params.
    """

    changes_required, quota_change_request = _system_state_change_details(
        module,
        project_quota_output
    )

    if changes_required:
        return True
    else:
        return False

def main():

    argument_spec = openstack_full_argument_spec(
        name=dict(required=True),
        state=dict(default='present', choices=['absent', 'present']),
        backup_gigabytes=dict(required=False, type='int', default=None),
        backups=dict(required=False, type='int', default=None),
        cores=dict(required=False, type='int', default=None),
        fixed_ips=dict(required=False, type='int', default=None),
        floating_ips=dict(required=False, type='int', default=None, aliases=['compute_floating_ips']),
        floatingip=dict(required=False, type='int', default=None, aliases=['network_floating_ips']),
        gigabytes=dict(required=False, type='int', default=None),
        gigabytes_types=dict(required=False, type='dict', default={}),
        injected_file_size=dict(required=False, type='int', default=None),
        injected_files=dict(required=False, type='int', default=None),
        injected_path_size=dict(required=False, type='int', default=None),
        instances=dict(required=False, type='int', default=None),
        key_pairs=dict(required=False, type='int', default=None),
        loadbalancer=dict(required=False, type='int', default=None),
        network=dict(required=False, type='int', default=None),
        per_volume_gigabytes=dict(required=False, type='int', default=None),
        pool=dict(required=False, type='int', default=None),
        port=dict(required=False, type='int', default=None),
        project=dict(required=False, type='int', default=None),
        properties=dict(required=False, type='int', default=None),
        ram=dict(required=False, type='int', default=None),
        rbac_policy=dict(required=False, type='int', default=None),
        router=dict(required=False, type='int', default=None),
        security_group_rule=dict(required=False, type='int', default=None),
        security_group=dict(required=False, type='int', default=None),
        server_group_members=dict(required=False, type='int', default=None),
        server_groups=dict(required=False, type='int', default=None),
        snapshots=dict(required=False, type='int', default=None),
        snapshots_types=dict(required=False, type='dict', default={}),
        subnet=dict(required=False, type='int', default=None),
        subnetpool=dict(required=False, type='int', default=None),
        volumes=dict(required=False, type='int', default=None),
        volumes_types=dict(required=False, type='dict', default={})
    )

    module = AnsibleModule(argument_spec,
                           supports_check_mode=True
                           )

    if not HAS_KEYSTONEAUTH1:
        module.fail_json(msg=missing_required_lib("keystoneauth1"), exception=KEYSTONEAUTH1_IMP_ERR)

    sdk, cloud = openstack_cloud_from_module(module)
    try:
        cloud_params = dict(module.params)

        # In order to handle the different volume types we update module params after.
        dynamic_types = [
            'gigabytes_types',
            'snapshots_types',
            'volumes_types',
        ]

        for dynamic_type in dynamic_types:
            for k, v in module.params[dynamic_type].items():
                module.params[k] = int(v)

        # Get current quota values
        project_quota_output = _get_quotas(
            sdk, module, cloud, cloud_params['name'])
        changes_required = False

        if module.params['state'] == "absent":
            # If a quota state is set to absent we should assume there will be changes.
            # The default quota values are not accessible so we can not determine if
            # no changes will occur or not.
            if module.check_mode:
                module.exit_json(changed=True)

            # Calling delete_network_quotas when a quota has not been set results
            # in an error, according to the sdk docs it should return the
            # current quota.
            # The following error string is returned:
            # network client call failed: Quota for tenant 69dd91d217e949f1a0b35a4b901741dc could not be found.
            neutron_msg1 = "network client call failed: Quota for tenant"
            neutron_msg2 = "could not be found"

            for quota_type in project_quota_output.keys():
                quota_call = getattr(cloud, 'delete_%s_quotas' % (quota_type))
                try:
                    quota_call(cloud_params['name'])
                except sdk.exceptions.OpenStackCloudException as e:
                    error_msg = str(e)
                    if error_msg.find(neutron_msg1) > -1 and error_msg.find(neutron_msg2) > -1:
                        pass
                    else:
                        module.fail_json(msg=str(e), extra_data=e.extra_data)

            project_quota_output = _get_quotas(
                sdk, module, cloud, cloud_params['name'])
            changes_required = True

        elif module.params['state'] == "present":
            if module.check_mode:
                module.exit_json(changed=_system_state_change(module, project_quota_output))

            changes_required, quota_change_request = _system_state_change_details(
                module,
                project_quota_output
            )

            if changes_required:
                for quota_type in quota_change_request.keys():
                    quota_call = getattr(cloud, 'set_%s_quotas' % (quota_type))
                    quota_call(cloud_params['name'], **quota_change_request[quota_type])

                # Get quota state post changes for validation
                project_quota_update = _get_quotas(
                    sdk, module, cloud, cloud_params['name'])

                if project_quota_output == project_quota_update:
                    module.fail_json(msg='Could not apply quota update')

                project_quota_output = project_quota_update

        module.exit_json(changed=changes_required,
                         openstack_quotas=project_quota_output
                         )

    except sdk.exceptions.OpenStackCloudException as e:
        module.fail_json(msg=str(e), extra_data=e.extra_data)

if __name__ == '__main__':
    main()


text:
title: "Remote Control"
description: "Remote controlling rclone"
date: "2018-03-05"
---

# Remote controlling rclone #

If rclone is run with the `--rc` flag then it starts an http server
which can be used to remote control rclone.

**NB** this is experimental and everything here is subject to change!

## Supported parameters

#### --rc ####
Flag to start the http server listen on remote requests

#### --rc-addr=IP ####
IPaddress:Port or :Port to bind server to. (default "localhost:5572")

#### --rc-cert=KEY ####
SSL PEM key (concatenation of certificate and CA certificate)

#### --rc-client-ca=PATH ####
Client certificate authority to verify clients with

#### --rc-htpasswd=PATH ####
htpasswd file - if not provided no authentication is done

#### --rc-key=PATH ####
SSL PEM Private key

#### --rc-max-header-bytes=VALUE ####
Maximum size of request header (default 4096)

#### --rc-user=VALUE ####
User name for authentication.

#### --rc-pass=VALUE ####
Password for authentication.

#### --rc-realm=VALUE ####
Realm for authentication (default "rclone")

#### --rc-server-read-timeout=DURATION ####
Timeout for server reading data (default 1h0m0s)

#### --rc-server-write-timeout=DURATION ####
Timeout for server writing data (default 1h0m0s)

## Accessing the remote control via the rclone rc command

Rclone itself implements the remote control protocol in its `rclone
rc` command.

You can use it like this

```
$ rclone rc rc/noop param1=one param2=two
{
	"param1": "one",
	"param2": "two"
}
```

Run `rclone rc` on its own to see the help for the installed remote
control commands.

## Supported commands
<!--- autogenerated start - run make rcdocs - don't edit here -->
### cache/expire: Purge a remote from cache

Purge a remote from the cache backend. Supports either a directory or a file.
Params:
  - remote = path to remote (required)
  - withData = true/false to delete cached data (chunks) as well (optional)

Eg

    rclone rc cache/expire remote=path/to/sub/folder/
    rclone rc cache/expire remote=/ withData=true

### cache/stats: Get cache stats

Show statistics for the cache remote.

### core/bwlimit: Set the bandwidth limit.

This sets the bandwidth limit to that passed in.

Eg

    rclone rc core/bwlimit rate=1M
    rclone rc core/bwlimit rate=off

The format of the parameter is exactly the same as passed to --bwlimit
except only one bandwidth may be specified.

### core/memstats: Returns the memory statistics

This returns the memory statistics of the running program.  What the values mean
are explained in the go docs: https://golang.org/pkg/runtime/#MemStats

The most interesting values for most people are:

* HeapAlloc: This is the amount of memory rclone is actually using
* HeapSys: This is the amount of memory rclone has obtained from the OS
* Sys: this is the total amount of memory requested from the OS
  * It is virtual memory so may include unused memory

### core/pid: Return PID of current process

This returns PID of current process.
Useful for stopping rclone process.

### rc/error: This returns an error

This returns an error with the input as part of its error string.
Useful for testing error handling.

### rc/list: List all the registered remote control commands

This lists all the registered remote control commands as a JSON map in
the commands response.

### rc/noop: Echo the input to the output parameters

This echoes the input parameters to the output parameters for testing
purposes.  It can be used to check that rclone is still alive and to
check that parameter passing is working properly.

### vfs/forget: Forget files or directories in the directory cache.

This forgets the paths in the directory cache causing them to be
re-read from the remote when needed.

If no paths are passed in then it will forget all the paths in the
directory cache.

    rclone rc vfs/forget

Otherwise pass files or dirs in as file=path or dir=path.  Any
parameter key starting with file will forget that file and any
starting with dir will forget that dir, eg

    rclone rc vfs/forget file=hello file2=goodbye dir=home/junk

<!--- autogenerated stop -->

## Accessing the remote control via HTTP

Rclone implements a simple HTTP based protocol.

Each endpoint takes an JSON object and returns a JSON object or an
error.  The JSON objects are essentially a map of string names to
values.

All calls must made using POST.

The input objects can be supplied using URL parameters, POST
parameters or by supplying "Content-Type: application/json" and a JSON
blob in the body.  There are examples of these below using `curl`.

The response will be a JSON blob in the body of the response.  This is
formatted to be reasonably human readable.

If an error occurs then there will be an HTTP error status (usually
400) and the body of the response will contain a JSON encoded error
object.

### Using POST with URL parameters only

```
curl -X POST 'http://localhost:5572/rc/noop/?potato=1&sausage=2'
```

Response

```
{
	"potato": "1",
	"sausage": "2"
}
```

Here is what an error response looks like:

```
curl -X POST 'http://localhost:5572/rc/error/?potato=1&sausage=2'
```

```
{
	"error": "arbitrary error on input map[potato:1 sausage:2]",
	"input": {
		"potato": "1",
		"sausage": "2"
	}
}
```

Note that curl doesn't return errors to the shell unless you use the `-f` option

```
$ curl -f -X POST 'http://localhost:5572/rc/error/?potato=1&sausage=2'
curl: (22) The requested URL returned error: 400 Bad Request
$ echo $?
22
```

### Using POST with a form

```
curl --data "potato=1" --data "sausage=2" http://localhost:5572/rc/noop/
```

Response

```
{
	"potato": "1",
	"sausage": "2"
}
```

Note that you can combine these with URL parameters too with the POST
parameters taking precedence.

```
curl --data "potato=1" --data "sausage=2" "http://localhost:5572/rc/noop/?rutabaga=3&sausage=4"
```

Response

```
{
	"potato": "1",
	"rutabaga": "3",
	"sausage": "4"
}

```

### Using POST with a JSON blob

```
curl -H "Content-Type: application/json" -X POST -d '{"potato":2,"sausage":1}' http://localhost:5572/rc/noop/
```

response

```
{
	"password": "xyz",
	"username": "xyz"
}
```

This can be combined with URL parameters too if required.  The JSON
blob takes precedence.

```
curl -H "Content-Type: application/json" -X POST -d '{"potato":2,"sausage":1}' 'http://localhost:5572/rc/noop/?rutabaga=3&potato=4'
```

```
{
	"potato": 2,
	"rutabaga": "3",
	"sausage": 1
}
```


text:
require File.expand_path('../application', __FILE__)

# Initialize the rails application
NeoInnovate::Application.initialize!


text:
package com.jetbrains.commandInterface.console;

import com.intellij.codeInsight.template.impl.TemplateColors;
import com.intellij.execution.console.LanguageConsoleImpl;
import com.intellij.execution.process.ConsoleHighlighter;
import com.intellij.openapi.Disposable;
import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.editor.colors.EditorColorsManager;
import com.intellij.openapi.editor.colors.EditorColorsScheme;
import com.intellij.openapi.editor.ex.util.EditorUtil;
import com.intellij.openapi.editor.impl.EditorImpl;
import com.intellij.openapi.editor.impl.EditorImpl.CaretRectangle;
import com.intellij.openapi.util.Disposer;
import com.intellij.openapi.util.Pair;
import com.intellij.openapi.util.text.StringUtil;
import com.intellij.psi.PsiFile;
import com.intellij.psi.util.PsiModificationTracker;
import com.intellij.psi.util.PsiModificationTracker.Listener;
import com.intellij.util.messages.MessageBusConnection;
import com.jetbrains.commandInterface.command.Argument;
import com.jetbrains.commandInterface.commandLine.ValidationResult;
import com.jetbrains.commandInterface.commandLine.psi.CommandLineFile;
import com.jetbrains.python.PyBundle;
import com.jetbrains.python.psi.PyUtil;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;

import javax.swing.*;
import java.awt.*;

/**
 * Displays argument hint (if required).
 * It tracks PSI changes, obtains validation info, and draws itself.
 * Will be added as {@link LanguageConsoleImpl#addLayerToPane(JComponent) layer}
 *
 * @author Ilya.Kazakevich
 */
@SuppressWarnings({"InstanceVariableMayNotBeInitialized", "NonSerializableFieldInSerializableClass", "DeserializableClassInSecureContext",
  "SerializableClassInSecureContext"}) // Nobody would serialize this class
final class ArgumentHintLayer extends JPanel implements Listener, Runnable { // Runnable to hide on console state changes

  /**
   * Braces for mandatory args are [] according to GNU/POSIX recommendations
   */
  @NotNull
  private static final Pair<String, String> MANDATORY_ARG_BRACES = Pair.create("<", ">");
  /**
   * Braces for optional args are <> according to GNU/POSIX recommendations
   */
  @NotNull
  private static final Pair<String, String> OPTIONAL_ARG_BRACES = Pair.create("[", "]");

  @NotNull
  private final LanguageConsoleImpl myConsole;
  /**
   * Color to be used for required arguments
   */
  @NotNull
  private final Color myRequiredColor;
  /**
   * Color to be used for optional arguments
   */
  @NotNull
  private final Color myOptionalColor;
  /**
   * Next argument to display (or null if nothing to display)
   */
  @Nullable
  private volatile Pair<Boolean, Argument> myNextArg;
  /**
   * Text console had last time (for cache purposes: no need to repaint argument if text did not changed)
   */
  @NotNull
  private volatile String myLastText = "";
  /**
   * Current position of caret in {@link CommandConsole#getConsoleEditor()}
   */
  private int myCaretPositionPx;

  /**
   * @param console console to wrap
   */
  private ArgumentHintLayer(@NotNull final LanguageConsoleImpl console) {
    myConsole = console;
    myLastText = console.getFile().getText();
    final EditorColorsScheme scheme = EditorColorsManager.getInstance().getGlobalScheme();
    myOptionalColor = scheme.getAttributes(ConsoleHighlighter.GRAY).getForegroundColor();
    myRequiredColor = scheme.getAttributes(TemplateColors.TEMPLATE_VARIABLE_ATTRIBUTES).getForegroundColor();
  }

  @Override
  public void modificationCountChanged() {
    ApplicationManager.getApplication().assertIsDispatchThread();
    final String newText = myConsole.getFile().getText();
    if (newText.equals(myLastText)) { // If text did not changed from last time, we do nothing
      return;
    }
    myLastText = newText; // Store text for next time check

    myNextArg = null; // Reset current argument

    final PsiFile consoleFile = myConsole.getFile();
    // Get next arg from file
    if (consoleFile instanceof CommandLineFile) {
      final ValidationResult result = ((CommandLineFile)consoleFile).getValidationResult();
      myNextArg = result != null ? result.getNextArg() : null;
      repaint(); // We need to repaint us if argument changed
    }
  }

  @Override
  protected void paintComponent(final Graphics g) {
    super.paintComponent(g);

    final Pair<Boolean, Argument> nextArg = myNextArg;
    if (nextArg == null) {
      return; // Nothing to show
    }
    /**
     *
     * We should display argument right after trimmed (spaces removed) document end or cursor position what ever comes first.
     *
     * We also need to add prompt length.
     */

    final EditorImpl consoleEditor = PyUtil.as(myConsole.getConsoleEditor(), EditorImpl.class);
    if (consoleEditor == null) {
      /**
       * We can't calculate anything if editor is not {@link EditorImpl})
       */
      Logger.getInstance(ArgumentHintLayer.class).warn("Bad editor: " + myConsole.getConsoleEditor());
      return;
    }
    final int consoleFontType = consoleEditor.getCaretModel().getTextAttributes().getFontType();
    final FontMetrics consoleFontMetrics = consoleEditor.getFontMetrics(consoleFontType);
    final Font consoleFont = consoleFontMetrics.getFont();

    // Copy rendering hints
    final Graphics2D sourceGraphics2 = PyUtil.as(consoleEditor.getComponent().getGraphics(), Graphics2D.class);
    if (sourceGraphics2 != null && g instanceof Graphics2D) {
      ((Graphics2D)g).setRenderingHints(sourceGraphics2.getRenderingHints());
    }

    final boolean argumentRequired = nextArg.first;
    final String argumentText = nextArg.second.getHelp().getHelpString();

    g.setFont(consoleFont);
    g.setColor(argumentRequired ? myRequiredColor : myOptionalColor);

    final String textToShow = wrapBracesIfNeeded(argumentRequired, StringUtil.isEmpty(argumentText)
                                                                   ? PyBundle.message("commandLine.argumentHint.defaultName")
                                                                   : argumentText);

    // Update caret position (if known)
    final CaretRectangle[] locations = consoleEditor.getCaretLocations();
    if (locations != null) {
      final CaretRectangle rectangle = locations[0];
      myCaretPositionPx = rectangle.myPoint.x;
    }

    final int consoleEditorTop = consoleEditor.getComponent().getLocation().y;
    final double textHeight = Math.floor(consoleFont.getStringBounds(textToShow, consoleFontMetrics.getFontRenderContext()).getY());

    @SuppressWarnings("NumericCastThatLosesPrecision") // pixels in position should be integer, anyway
    final int y = (int)(consoleEditorTop - textHeight);
    // We should take scrolling into account to prevent argument "flying" over text when user scrolls it, like "position:fixed" in css
    final Point scrollLocation = consoleEditor.getContentComponent().getLocation();
    final int spaceWidth = EditorUtil.getSpaceWidth(consoleFontType, consoleEditor);

    // Remove whitespaces on the end of document
    /**
     * TODO: This is actually copy/paste with {@link com.intellij.openapi.editor.actions.EditorActionUtil#moveCaretToLineEnd}.
     * Need to merge somehow.
     */
    final String trimmedDocument = StringUtil.trimTrailing(consoleEditor.getDocument().getText());
    final double trimmedDocumentWidth = consoleFont.getStringBounds(trimmedDocument, consoleFontMetrics.getFontRenderContext()).getWidth();
    @SuppressWarnings("NumericCastThatLosesPrecision") // pixels in position should be integer, anyway
    final int contentWidth = (int)Math.ceil(trimmedDocumentWidth + consoleEditor.getPrefixTextWidthInPixels());

    g.drawString(textToShow, Math.max(myCaretPositionPx, contentWidth) + scrollLocation.x + spaceWidth, y + scrollLocation.y);
  }

  /**
   * Adds appropriate braces to argument help text if needed
   *
   * @param required   is argument required
   * @param textToShow arg help text
   * @return text to show
   */
  @NotNull
  private static String wrapBracesIfNeeded(final boolean required, @NotNull final String textToShow) {
    if (textToShow.startsWith(MANDATORY_ARG_BRACES.first) || textToShow.startsWith(OPTIONAL_ARG_BRACES.first)) {
      return textToShow;
    }
    final Pair<String, String> braces = (required ? MANDATORY_ARG_BRACES : OPTIONAL_ARG_BRACES);
    return String.format("%s%s%s", braces.first, textToShow, braces.second);
  }

  @Override
  public void run() {
    // Console state changed! Hide...
    myNextArg = null;
    repaint();
  }

  /**
   * Attaches argument displaying layer to console. Be sure your console has commands.
   * For now, only {@link CommandLineFile} is supported for now!
   *
   * @param console console to attach
   * @throws IllegalArgumentException is passed argument is not {@link CommandLineFile}
   */

  static void attach(@NotNull final CommandConsole console) {
    final PsiFile consoleFile = console.getFile();
    if (!(consoleFile instanceof CommandLineFile)) {
      throw new IllegalArgumentException(
        String.format("Passed argument is %s, but has to be %s", consoleFile.getClass(), CommandLineFile.class));
    }
    final ArgumentHintLayer argumentHintLayer = new ArgumentHintLayer(console);
    console.addStateChangeListener(argumentHintLayer);
    final MessageBusConnection connection = console.getProject().getMessageBus().connect();
    connection.subscribe(PsiModificationTracker.TOPIC, argumentHintLayer);
    console.addLayerToPane(argumentHintLayer);
    Disposer.register(console, new Disconnector(connection)); // Registered to disconnect on disposal
  }

  /**
   * Disconnects connect on {@link #dispose()}
   */
  private static final class Disconnector implements Disposable {
    @NotNull
    private final MessageBusConnection myConnection;

    /**
     * @param connection connection to disconnect on {@link #dispose()}
     */
    private Disconnector(@NotNull final MessageBusConnection connection) {
      myConnection = connection;
    }

    @Override
    public void dispose() {
      myConnection.disconnect();
    }
  }
}


text:
#include "routing/transit_world_graph.hpp"

#include "routing/index_graph.hpp"
#include "routing/transit_graph.hpp"

#include <memory>
#include <utility>

namespace routing
{
using namespace std;

TransitWorldGraph::TransitWorldGraph(unique_ptr<CrossMwmGraph> crossMwmGraph,
                                     unique_ptr<IndexGraphLoader> indexLoader,
                                     unique_ptr<TransitGraphLoader> transitLoader,
                                     shared_ptr<EdgeEstimator> estimator)
  : m_crossMwmGraph(move(crossMwmGraph))
  , m_indexLoader(move(indexLoader))
  , m_transitLoader(move(transitLoader))
  , m_estimator(estimator)
{
  CHECK(m_indexLoader, ());
  CHECK(m_transitLoader, ());
  CHECK(m_estimator, ());
}

void TransitWorldGraph::GetEdgeList(Segment const & segment, bool isOutgoing, bool useRoutingOptions,
                                    vector<SegmentEdge> & edges)
{
  auto & transitGraph = GetTransitGraph(segment.GetMwmId());

  if (TransitGraph::IsTransitSegment(segment))
  {
    transitGraph.GetTransitEdges(segment, isOutgoing, edges);

    Segment real;
    if (transitGraph.FindReal(segment, real))
    {
      bool const haveSameFront = GetJunction(segment, true /* front */) == GetJunction(real, true);
      bool const haveSameBack = GetJunction(segment, false /* front */) == GetJunction(real, false);
      if ((isOutgoing && haveSameFront) || (!isOutgoing && haveSameBack))
        AddRealEdges(real, isOutgoing, useRoutingOptions, edges);
    }

    GetTwins(segment, isOutgoing, useRoutingOptions, edges);
  }
  else
  {
    AddRealEdges(segment, isOutgoing, useRoutingOptions, edges);
  }

  vector<SegmentEdge> fakeFromReal;
  for (auto const & edge : edges)
  {
    auto const & edgeSegment = edge.GetTarget();
    for (auto const & s : transitGraph.GetFake(edgeSegment))
    {
      bool const haveSameFront = GetJunction(edgeSegment, true /* front */) == GetJunction(s, true);
      bool const haveSameBack = GetJunction(edgeSegment, false /* front */) == GetJunction(s, false);
      if ((isOutgoing && haveSameBack) || (!isOutgoing && haveSameFront))
        fakeFromReal.emplace_back(s, edge.GetWeight());
    }
  }
  edges.insert(edges.end(), fakeFromReal.begin(), fakeFromReal.end());
}

void TransitWorldGraph::GetEdgeList(JointSegment const & parentJoint,
                                    Segment const & segment, bool isOutgoing,
                                    std::vector<JointEdge> & edges,
                                    std::vector<RouteWeight> & parentWeights)
{
  CHECK(false, ("TransitWorldGraph does not support Joints mode."));
}

Junction const & TransitWorldGraph::GetJunction(Segment const & segment, bool front)
{
  if (TransitGraph::IsTransitSegment(segment))
    return GetTransitGraph(segment.GetMwmId()).GetJunction(segment, front);

  return GetRealRoadGeometry(segment.GetMwmId(), segment.GetFeatureId())
      .GetJunction(segment.GetPointId(front));
}

m2::PointD const & TransitWorldGraph::GetPoint(Segment const & segment, bool front)
{
  return GetJunction(segment, front).GetPoint();
}

bool TransitWorldGraph::IsOneWay(NumMwmId mwmId, uint32_t featureId)
{
  if (TransitGraph::IsTransitFeature(featureId))
    return true;
  return GetRealRoadGeometry(mwmId, featureId).IsOneWay();
}

bool TransitWorldGraph::IsPassThroughAllowed(NumMwmId mwmId, uint32_t featureId)
{
  if (TransitGraph::IsTransitFeature(featureId))
    return true;
  return GetRealRoadGeometry(mwmId, featureId).IsPassThroughAllowed();
}

void TransitWorldGraph::ClearCachedGraphs()
{
  m_indexLoader->Clear();
  m_transitLoader->Clear();
}

void TransitWorldGraph::GetOutgoingEdgesList(Segment const & segment, vector<SegmentEdge> & edges)
{
  edges.clear();
  GetEdgeList(segment, true /* isOutgoing */, true /* useRoutingOptions */, edges);
}

void TransitWorldGraph::GetIngoingEdgesList(Segment const & segment, vector<SegmentEdge> & edges)
{
  edges.clear();
  GetEdgeList(segment, false /* isOutgoing */, true /* useRoutingOptions */, edges);
}

RouteWeight TransitWorldGraph::HeuristicCostEstimate(Segment const & from, Segment const & to)
{
  return HeuristicCostEstimate(GetPoint(from, true /* front */), GetPoint(to, true /* front */));
}

RouteWeight TransitWorldGraph::HeuristicCostEstimate(Segment const & from, m2::PointD const & to)
{
  return HeuristicCostEstimate(GetPoint(from, true /* front */), to);
}

RouteWeight TransitWorldGraph::HeuristicCostEstimate(m2::PointD const & from, m2::PointD const & to)
{
  return RouteWeight(m_estimator->CalcHeuristic(from, to));
}

RouteWeight TransitWorldGraph::CalcSegmentWeight(Segment const & segment,
                                                 EdgeEstimator::Purpose purpose)
{
  if (TransitGraph::IsTransitSegment(segment))
  {
    TransitGraph & transitGraph = GetTransitGraph(segment.GetMwmId());
    return transitGraph.CalcSegmentWeight(segment, purpose);
  }

  return RouteWeight(m_estimator->CalcSegmentWeight(
      segment, GetRealRoadGeometry(segment.GetMwmId(), segment.GetFeatureId()), purpose));
}

RouteWeight TransitWorldGraph::CalcLeapWeight(m2::PointD const & from, m2::PointD const & to) const
{
  return RouteWeight(m_estimator->CalcLeapWeight(from, to));
}

RouteWeight TransitWorldGraph::CalcOffroadWeight(m2::PointD const & from,
                                                 m2::PointD const & to,
                                                 EdgeEstimator::Purpose purpose) const
{
  return RouteWeight(m_estimator->CalcOffroad(from, to, purpose));
}

double TransitWorldGraph::CalculateETA(Segment const & from, Segment const & to)
{
  if (TransitGraph::IsTransitSegment(from))
    return CalcSegmentWeight(to, EdgeEstimator::Purpose::ETA).GetWeight();

  if (TransitGraph::IsTransitSegment(to))
    return CalcSegmentWeight(to, EdgeEstimator::Purpose::ETA).GetWeight();

  if (from.GetMwmId() != to.GetMwmId())
  {
    return m_estimator->CalcSegmentWeight(to, GetRealRoadGeometry(to.GetMwmId(), to
        .GetFeatureId()), EdgeEstimator::Purpose::ETA);
  }

  auto & indexGraph = m_indexLoader->GetIndexGraph(from.GetMwmId());
  return indexGraph
      .CalculateEdgeWeight(EdgeEstimator::Purpose::ETA, true /* isOutgoing */, from, to)
      .GetWeight();
}

double TransitWorldGraph::CalculateETAWithoutPenalty(Segment const & segment)
{
  if (TransitGraph::IsTransitSegment(segment))
    return CalcSegmentWeight(segment, EdgeEstimator::Purpose::ETA).GetWeight();

  return m_estimator->CalcSegmentWeight(
      segment, GetRealRoadGeometry(segment.GetMwmId(), segment.GetFeatureId()),
      EdgeEstimator::Purpose::ETA);
}

unique_ptr<TransitInfo> TransitWorldGraph::GetTransitInfo(Segment const & segment)
{
  if (!TransitGraph::IsTransitSegment(segment))
    return {};

  auto & transitGraph = GetTransitGraph(segment.GetMwmId());
  if (transitGraph.IsGate(segment))
    return make_unique<TransitInfo>(transitGraph.GetGate(segment));

  if (transitGraph.IsEdge(segment))
    return make_unique<TransitInfo>(transitGraph.GetEdge(segment));

  // Fake segment between pedestrian feature and gate.
  return {};
}

void TransitWorldGraph::GetTwinsInner(Segment const & segment, bool isOutgoing,
                                      vector<Segment> & twins)
{
  if (m_mode == WorldGraphMode::SingleMwm || !m_crossMwmGraph ||
      !m_crossMwmGraph->IsTransition(segment, isOutgoing))
  {
    return;
  }
  m_crossMwmGraph->GetTwins(segment, isOutgoing, twins);
}

RoadGeometry const & TransitWorldGraph::GetRealRoadGeometry(NumMwmId mwmId, uint32_t featureId)
{
  CHECK(!TransitGraph::IsTransitFeature(featureId), ("GetRealRoadGeometry not designed for transit."));
  return m_indexLoader->GetGeometry(mwmId).GetRoad(featureId);
}

void TransitWorldGraph::AddRealEdges(Segment const & segment, bool isOutgoing,
                                     bool useRoutingOptions, vector<SegmentEdge> & edges)
{
  auto & indexGraph = GetIndexGraph(segment.GetMwmId());
  indexGraph.GetEdgeList(segment, isOutgoing, useRoutingOptions, edges);
  GetTwins(segment, isOutgoing, useRoutingOptions, edges);
}

TransitGraph & TransitWorldGraph::GetTransitGraph(NumMwmId mwmId)
{
  auto & indexGraph = GetIndexGraph(mwmId);
  return m_transitLoader->GetTransitGraph(mwmId, indexGraph);
}
}  // namespace routing


text:
            {{ orgNameLong }}

Species search

Lists

Collections

Datasets

Occurrence records

Advanced search

Spatial search


text:
import React from 'react';

export function getValuePropValue(child) {
  const props = child.props;
  if ('value' in props) {
    return props.value;
  }
  if (child.key) {
    return child.key;
  }
  if (child.type && child.type.isSelectOptGroup && props.label) {
    return props.label;
  }
  throw new Error(
    `Need at least a key or a value or a label (only for OptGroup) for ${child}`
  );
}

export function getPropValue(child, prop) {
  if (prop === 'value') {
    return getValuePropValue(child);
  }
  return child.props[prop];
}

export function isMultiple(props) {
  return props.multiple;
}

export function isCombobox(props) {
  return props.combobox;
}

export function isMultipleOrTags(props) {
  return props.multiple || props.tags;
}

export function isMultipleOrTagsOrCombobox(props) {
  return isMultipleOrTags(props) || isCombobox(props);
}

export function isSingleMode(props) {
  return !isMultipleOrTagsOrCombobox(props);
}

export function toArray(value) {
  let ret = value;
  if (value === undefined) {
    ret = [];
  } else if (!Array.isArray(value)) {
    ret = [value];
  }
  return ret;
}

export function preventDefaultEvent(e) {
  e.preventDefault();
}

export function findIndexInValueByKey(value, key) {
  let index = -1;
  for (let i = 0; i < value.length; i++) {
    if (value[i].key === key) {
      index = i;
      break;
    }
  }
  return index;
}

export function findIndexInValueByLabel(value, label) {
  let index = -1;
  for (let i = 0; i < value.length; i++) {
    if (toArray(value[i].label).join('') === label) {
      index = i;
      break;
    }
  }
  return index;
}

export function getSelectKeys(menuItems, value) {
  if (value === null || value === undefined) {
    return [];
  }
  let selectedKeys = [];
  React.Children.forEach(menuItems, item => {
    if (item.type.isMenuItemGroup) {
      selectedKeys = selectedKeys.concat(
        getSelectKeys(item.props.children, value)
      );
    } else {
      const itemValue = getValuePropValue(item);
      const itemKey = item.key;
      if (findIndexInValueByKey(value, itemValue) !== -1 && itemKey) {
        selectedKeys.push(itemKey);
      }
    }
  });
  return selectedKeys;
}

export const UNSELECTABLE_STYLE = {
  userSelect: 'none',
  WebkitUserSelect: 'none',
};

export const UNSELECTABLE_ATTRIBUTE = {
  unselectable: 'unselectable',
};

export function findFirstMenuItem(children) {
  for (let i = 0; i < children.length; i++) {
    const child = children[i];
    if (child.type.isMenuItemGroup) {
      const found = findFirstMenuItem(child.props.children);
      if (found) {
        return found;
      }
    } else if (!child.props.disabled) {
      return child;
    }
  }
  return null;
}

export function includesSeparators(string, separators) {
  for (let i = 0; i < separators.length; ++i) {
    if (string.lastIndexOf(separators[i]) > 0) {
      return true;
    }
  }
  return false;
}

export function splitBySeparators(string, separators) {
  const reg = new RegExp(`[${separators.join()}]`);
  return string.split(reg).filter(token => token);
}

export function defaultFilterFn(input, child) {
  if (child.props.disabled) {
    return false;
  }
  const value = String(getPropValue(child, this.props.optionFilterProp));
  return (
    value.toLowerCase().indexOf(input.toLowerCase()) > -1
  );
}

export function validateOptionValue(value, props) {
  if (isSingleMode(props) || isMultiple(props)) {
    return;
  }
  if (typeof value !== 'string') {
    throw new Error(
      `Invalid \`value\` of type \`${typeof value}\` supplied to Option, ` +
      `expected \`string\` when \`tags/combobox\` is \`true\`.`
    );
  }
}

export function saveRef(instance, name) {
  return (node) => {
    instance[name] = node;
  };
}


text:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/content_bg"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:orientation="vertical" >

    <include layout="@layout/city_item_section" />

    <TextView
        android:id="@+id/city_name"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:paddingBottom="12.0dip"
        android:paddingLeft="29.0dip"
        android:paddingTop="12.0dip"
        android:textColor="@color/list_city_item_text"
        android:textSize="18.0sp" />

</LinearLayout>