Files
sdk/runtime/vm/message.h
T
turnidge@google.com ff26341fd6 Heartbeat implementation of dart:mirrors.
Add the skeleton for the dart:mirrors library in all the appropriate
places.  The only thing we can do right now is ask an Isolate for its
debugName.  Add a few tests.
Review URL: https://chromiumcodereview.appspot.com//9420038

git-svn-id: https://dart.googlecode.com/svn/branches/bleeding_edge/dart@5370 260f80e4-7a28-3924-810f-c04153c831b5
2012-03-12 23:51:03 +00:00

157 lines
4.1 KiB
C++

// Copyright (c) 2011, the Dart project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
#ifndef VM_MESSAGE_H_
#define VM_MESSAGE_H_
#include "vm/thread.h"
// Duplicated from dart_api.h to avoid including the whole header.
typedef int64_t Dart_Port;
namespace dart {
class Message {
public:
typedef enum {
kNormalPriority = 0, // Deliver message when idle.
kOOBPriority = 1, // Deliver message asap.
// Iteration.
kFirstPriority = 0,
kNumPriorities = 2,
} Priority;
// A port number which is never used.
static const Dart_Port kIllegalPort = 0;
// A new message to be sent between two isolates. The data handed to this
// message will be disposed by calling free() once the message object is
// being destructed (after delivery or when the receiving port is closed).
//
// If reply_port is kIllegalPort, then there is no reply port.
Message(Dart_Port dest_port, Dart_Port reply_port,
uint8_t* data, Priority priority)
: next_(NULL),
dest_port_(dest_port),
reply_port_(reply_port),
data_(data),
priority_(priority) {}
~Message() {
free(data_);
}
Dart_Port dest_port() const { return dest_port_; }
Dart_Port reply_port() const { return reply_port_; }
uint8_t* data() const { return data_; }
Priority priority() const { return priority_; }
private:
friend class MessageQueue;
Message* next_;
Dart_Port dest_port_;
Dart_Port reply_port_;
uint8_t* data_;
Priority priority_;
DISALLOW_COPY_AND_ASSIGN(Message);
};
// There is a message queue per isolate.
class MessageQueue {
public:
MessageQueue();
~MessageQueue();
void Enqueue(Message* msg);
// Gets the next message from the message queue, possibly blocking
// if no message is available. 'millis' is a timeout in
// milliseconds. If 'millis' is 0, then this means to block
// indefinitely. May block if no message is available. May return
// NULL even if 'millis' is 0 due to spurious wakeups.
Message* Dequeue(int64_t millis);
// Gets the next message from the message queue if available. Will
// not block.
Message* DequeueNoWait();
// Gets the next message of the specified priority or greater from
// the message queue if available. Will not block.
Message* DequeueNoWaitWithPriority(Message::Priority min_priority);
void Flush(Dart_Port port);
void FlushAll();
private:
friend class MessageQueueTestPeer;
Message* DequeueNoWaitHoldsLock(Message::Priority min_priority);
Monitor monitor_;
Message* head_[Message::kNumPriorities];
Message* tail_[Message::kNumPriorities];
DISALLOW_COPY_AND_ASSIGN(MessageQueue);
};
// A MessageHandler is an entity capable of accepting messages.
class MessageHandler {
protected:
MessageHandler();
// Allows subclasses to provide custom message notification.
virtual void MessageNotify(Message::Priority priority);
public:
virtual ~MessageHandler();
// Allow subclasses to provide a handler name.
virtual const char* name() const;
#if defined(DEBUG)
// Check that it is safe to access this message handler.
//
// For example, if this MessageHandler is an isolate, then it is
// only safe to access it when the MessageHandler is the current
// isolate.
virtual void CheckAccess();
#endif
void PostMessage(Message* message);
void ClosePort(Dart_Port port);
void CloseAllPorts();
// A message handler tracks how many live ports it has.
bool HasLivePorts() const { return live_ports_ > 0; }
void increment_live_ports() {
#if defined(DEBUG)
CheckAccess();
#endif
live_ports_++;
}
void decrement_live_ports() {
#if defined(DEBUG)
CheckAccess();
#endif
live_ports_--;
}
// Returns true if the handler is owned by the PortMap.
//
// This is used to delete handlers when their last live port is closed.
virtual bool OwnedByPortMap() const { return false; }
MessageQueue* queue() const { return queue_; }
private:
intptr_t live_ports_;
MessageQueue* queue_;
};
} // namespace dart
#endif // VM_MESSAGE_H_