mirror of
https://github.com/wassname/ray.git
synced 2026-08-19 12:30:27 +08:00
Treat actor creation like a regular task. (#1668)
* Treat actor creation like a regular task. * Small cleanups. * Change semantics of actor resource handling. * Bug fix. * Minor linting * Bug fix * Fix jenkins test. * Fix actor tests * Some cleanups * Bug fix * Fix bug. * Remove cached actor tasks when a driver is removed. * Add more info to taskspec in global state API. * Fix cyclic import bug in tune. * Fix * Fix linting. * Fix linting. * Don't schedule any tasks (especially actor creaiton tasks) on local schedulers with 0 CPUs. * Bug fix. * Add test for 0 CPU case * Fix linting * Address comments. * Fix typos and add comment. * Add assertion and fix test.
This commit is contained in:
committed by
Stephanie Wang
parent
3c080f4baa
commit
96913be939
@@ -29,6 +29,10 @@ table TaskInfo {
|
||||
parent_task_id: string;
|
||||
// A count of the number of tasks submitted by the parent task before this one.
|
||||
parent_counter: int;
|
||||
// The ID of the actor to create if this is an actor creation task.
|
||||
actor_creation_id: string;
|
||||
// The dummy object ID of the actor creation task if this is an actor method.
|
||||
actor_creation_dummy_object_id: string;
|
||||
// Actor ID of the task. This is the actor that this task is executed on
|
||||
// or NIL_ACTOR_ID if the task is just a normal task.
|
||||
actor_id: string;
|
||||
@@ -162,3 +166,12 @@ table DriverTableMessage {
|
||||
// The driver ID of the driver that died.
|
||||
driver_id: string;
|
||||
}
|
||||
|
||||
table ActorCreationNotification {
|
||||
// The ID of the actor that was created.
|
||||
actor_id: string;
|
||||
// The ID of the driver that created the actor.
|
||||
driver_id: string;
|
||||
// The ID of the local scheduler that created the actor.
|
||||
local_scheduler_id: string;
|
||||
}
|
||||
|
||||
@@ -272,9 +272,9 @@ static int PyTask_init(PyTask *self, PyObject *args, PyObject *kwds) {
|
||||
/* ID of the driver that this task originates from. */
|
||||
UniqueID driver_id;
|
||||
/* ID of the actor this task should run on. */
|
||||
UniqueID actor_id = UniqueID::nil();
|
||||
UniqueID actor_id = ActorID::nil();
|
||||
/* ID of the actor handle used to submit this task. */
|
||||
UniqueID actor_handle_id = UniqueID::nil();
|
||||
UniqueID actor_handle_id = ActorHandleID::nil();
|
||||
/* How many tasks have been launched on the actor so far? */
|
||||
int actor_counter = 0;
|
||||
/* True if this is an actor checkpoint task and false otherwise. */
|
||||
@@ -289,15 +289,21 @@ static int PyTask_init(PyTask *self, PyObject *args, PyObject *kwds) {
|
||||
TaskID parent_task_id;
|
||||
/* The number of tasks that the parent task has called prior to this one. */
|
||||
int parent_counter;
|
||||
// The actor creation ID.
|
||||
ActorID actor_creation_id = ActorID::nil();
|
||||
// The dummy object for the actor creation task (if this is an actor method).
|
||||
ObjectID actor_creation_dummy_object_id = ObjectID::nil();
|
||||
/* Arguments of the task that are execution-dependent. These must be
|
||||
* PyObjectIDs). */
|
||||
PyObject *execution_arguments = NULL;
|
||||
/* Dictionary of resource requirements for this task. */
|
||||
PyObject *resource_map = NULL;
|
||||
if (!PyArg_ParseTuple(args, "O&O&OiO&i|O&O&iOOO", &PyObjectToUniqueID,
|
||||
if (!PyArg_ParseTuple(args, "O&O&OiO&i|O&O&O&O&iOOO", &PyObjectToUniqueID,
|
||||
&driver_id, &PyObjectToUniqueID, &function_id,
|
||||
&arguments, &num_returns, &PyObjectToUniqueID,
|
||||
&parent_task_id, &parent_counter, &PyObjectToUniqueID,
|
||||
&actor_creation_id, &PyObjectToUniqueID,
|
||||
&actor_creation_dummy_object_id, &PyObjectToUniqueID,
|
||||
&actor_id, &PyObjectToUniqueID, &actor_handle_id,
|
||||
&actor_counter, &is_actor_checkpoint_method_object,
|
||||
&execution_arguments, &resource_map)) {
|
||||
@@ -312,10 +318,11 @@ static int PyTask_init(PyTask *self, PyObject *args, PyObject *kwds) {
|
||||
|
||||
Py_ssize_t size = PyList_Size(arguments);
|
||||
/* Construct the task specification. */
|
||||
TaskSpec_start_construct(g_task_builder, driver_id, parent_task_id,
|
||||
parent_counter, actor_id, actor_handle_id,
|
||||
actor_counter, is_actor_checkpoint_method,
|
||||
function_id, num_returns);
|
||||
TaskSpec_start_construct(
|
||||
g_task_builder, driver_id, parent_task_id, parent_counter,
|
||||
actor_creation_id, actor_creation_dummy_object_id, actor_id,
|
||||
actor_handle_id, actor_counter, is_actor_checkpoint_method, function_id,
|
||||
num_returns);
|
||||
/* Add the task arguments. */
|
||||
for (Py_ssize_t i = 0; i < size; ++i) {
|
||||
PyObject *arg = PyList_GetItem(arguments, i);
|
||||
@@ -463,6 +470,21 @@ static PyObject *PyTask_arguments(PyObject *self) {
|
||||
return arg_list;
|
||||
}
|
||||
|
||||
static PyObject *PyTask_actor_creation_id(PyObject *self) {
|
||||
ActorID actor_creation_id =
|
||||
TaskSpec_actor_creation_id(((PyTask *) self)->spec);
|
||||
return PyObjectID_make(actor_creation_id);
|
||||
}
|
||||
|
||||
static PyObject *PyTask_actor_creation_dummy_object_id(PyObject *self) {
|
||||
ActorID actor_creation_dummy_object_id = ActorID::nil();
|
||||
if (TaskSpec_is_actor_task(((PyTask *) self)->spec)) {
|
||||
actor_creation_dummy_object_id =
|
||||
TaskSpec_actor_creation_dummy_object_id(((PyTask *) self)->spec);
|
||||
}
|
||||
return PyObjectID_make(actor_creation_dummy_object_id);
|
||||
}
|
||||
|
||||
static PyObject *PyTask_required_resources(PyObject *self) {
|
||||
TaskSpec *task = ((PyTask *) self)->spec;
|
||||
PyObject *required_resources = PyDict_New();
|
||||
@@ -520,6 +542,11 @@ static PyMethodDef PyTask_methods[] = {
|
||||
"Return the task ID for this task."},
|
||||
{"arguments", (PyCFunction) PyTask_arguments, METH_NOARGS,
|
||||
"Return the arguments for the task."},
|
||||
{"actor_creation_id", (PyCFunction) PyTask_actor_creation_id, METH_NOARGS,
|
||||
"Return the actor creation ID for the task."},
|
||||
{"actor_creation_dummy_object_id",
|
||||
(PyCFunction) PyTask_actor_creation_dummy_object_id, METH_NOARGS,
|
||||
"Return the actor creation dummy object ID for the task."},
|
||||
{"required_resources", (PyCFunction) PyTask_required_resources, METH_NOARGS,
|
||||
"Return the resource vector of the task."},
|
||||
{"returns", (PyCFunction) PyTask_returns, METH_NOARGS,
|
||||
|
||||
@@ -1,6 +1,31 @@
|
||||
#include "actor_notification_table.h"
|
||||
|
||||
#include "common_protocol.h"
|
||||
#include "redis.h"
|
||||
|
||||
void publish_actor_creation_notification(DBHandle *db_handle,
|
||||
const ActorID &actor_id,
|
||||
const WorkerID &driver_id,
|
||||
const DBClientID &local_scheduler_id) {
|
||||
// Create a flatbuffer object to serialize and publish.
|
||||
flatbuffers::FlatBufferBuilder fbb;
|
||||
// Create the flatbuffers message.
|
||||
auto message = CreateActorCreationNotification(
|
||||
fbb, to_flatbuf(fbb, actor_id), to_flatbuf(fbb, driver_id),
|
||||
to_flatbuf(fbb, local_scheduler_id));
|
||||
fbb.Finish(message);
|
||||
|
||||
ActorCreationNotificationData *data =
|
||||
(ActorCreationNotificationData *) malloc(
|
||||
sizeof(ActorCreationNotificationData) + fbb.GetSize());
|
||||
data->size = fbb.GetSize();
|
||||
memcpy(&data->flatbuffer_data[0], fbb.GetBufferPointer(), fbb.GetSize());
|
||||
|
||||
init_table_callback(db_handle, UniqueID::nil(), __func__,
|
||||
new CommonCallbackData(data), NULL, NULL,
|
||||
redis_publish_actor_creation_notification, NULL);
|
||||
}
|
||||
|
||||
void actor_notification_table_subscribe(
|
||||
DBHandle *db_handle,
|
||||
actor_notification_table_subscribe_callback subscribe_callback,
|
||||
|
||||
@@ -11,12 +11,33 @@
|
||||
|
||||
/* Callback for subscribing to the local scheduler table. */
|
||||
typedef void (*actor_notification_table_subscribe_callback)(
|
||||
ActorID actor_id,
|
||||
WorkerID driver_id,
|
||||
DBClientID local_scheduler_id,
|
||||
bool reconstruct,
|
||||
const ActorID &actor_id,
|
||||
const WorkerID &driver_id,
|
||||
const DBClientID &local_scheduler_id,
|
||||
void *user_context);
|
||||
|
||||
/// Publish an actor creation notification. This is published by a local
|
||||
/// scheduler once it creates an actor.
|
||||
///
|
||||
/// \param db_handle Database handle.
|
||||
/// \param actor_id The ID of the actor that was created.
|
||||
/// \param driver_id The ID of the driver that created the actor.
|
||||
/// \param local_scheduler_id The ID of the local scheduler that created the
|
||||
/// actor.
|
||||
/// \return Void.
|
||||
void publish_actor_creation_notification(DBHandle *db_handle,
|
||||
const ActorID &actor_id,
|
||||
const WorkerID &driver_id,
|
||||
const DBClientID &local_scheduler_id);
|
||||
|
||||
/// Data that is needed to publish an actor creation notification.
|
||||
typedef struct {
|
||||
/// The size of the flatbuffer object.
|
||||
int64_t size;
|
||||
/// The information to be sent.
|
||||
uint8_t flatbuffer_data[0];
|
||||
} ActorCreationNotificationData;
|
||||
|
||||
/**
|
||||
* Register a callback to process actor notification events.
|
||||
*
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
#include "common_protocol.h"
|
||||
#include "local_scheduler_table.h"
|
||||
|
||||
#include "common_protocol.h"
|
||||
#include "redis.h"
|
||||
|
||||
void local_scheduler_table_subscribe(
|
||||
|
||||
+46
-32
@@ -1033,7 +1033,8 @@ void redis_task_table_test_and_update_callback(redisAsyncContext *c,
|
||||
* delayed when added to the task table if they are submitted to a local
|
||||
* scheduler before it receives the notification that maps the actor to a
|
||||
* local scheduler. */
|
||||
RAY_LOG(ERROR) << "No task found during task_table_test_and_update";
|
||||
RAY_LOG(ERROR) << "No task found during task_table_test_and_update for "
|
||||
<< "task with ID " << callback_data->id;
|
||||
return;
|
||||
}
|
||||
/* Determine whether the update happened. */
|
||||
@@ -1541,6 +1542,40 @@ void redis_plasma_manager_send_heartbeat(TableCallbackData *callback_data) {
|
||||
destroy_timer_callback(db->loop, callback_data);
|
||||
}
|
||||
|
||||
void redis_publish_actor_creation_notification_callback(redisAsyncContext *c,
|
||||
void *r,
|
||||
void *privdata) {
|
||||
REDIS_CALLBACK_HEADER(db, callback_data, r);
|
||||
|
||||
redisReply *reply = (redisReply *) r;
|
||||
RAY_CHECK(reply->type == REDIS_REPLY_INTEGER);
|
||||
RAY_LOG(DEBUG) << reply->integer << " subscribers received this publish.";
|
||||
// At the very least, the local scheduler that publishes this message should
|
||||
// also receive it.
|
||||
RAY_CHECK(reply->integer >= 1);
|
||||
|
||||
RAY_CHECK(callback_data->done_callback == NULL);
|
||||
// Clean up the timer and callback.
|
||||
destroy_timer_callback(db->loop, callback_data);
|
||||
}
|
||||
|
||||
void redis_publish_actor_creation_notification(
|
||||
TableCallbackData *callback_data) {
|
||||
DBHandle *db = callback_data->db_handle;
|
||||
|
||||
ActorCreationNotificationData *data =
|
||||
(ActorCreationNotificationData *) callback_data->data->Get();
|
||||
|
||||
int status = redisAsyncCommand(
|
||||
db->context, redis_publish_actor_creation_notification_callback,
|
||||
(void *) callback_data->timer_id, "PUBLISH actor_notifications %b",
|
||||
&data->flatbuffer_data[0], data->size);
|
||||
if ((status == REDIS_ERR) || db->context->err) {
|
||||
LOG_REDIS_DEBUG(db->context,
|
||||
"error in redis_publish_actor_creation_notification");
|
||||
}
|
||||
}
|
||||
|
||||
void redis_actor_notification_table_subscribe_callback(redisAsyncContext *c,
|
||||
void *r,
|
||||
void *privdata) {
|
||||
@@ -1554,43 +1589,22 @@ void redis_actor_notification_table_subscribe_callback(redisAsyncContext *c,
|
||||
<< message_type->str;
|
||||
|
||||
if (strcmp(message_type->str, "message") == 0) {
|
||||
/* Handle an actor notification message. Parse the payload and call the
|
||||
* subscribe callback. */
|
||||
// Handle an actor notification message. Parse the payload and call the
|
||||
// subscribe callback.
|
||||
redisReply *payload = reply->element[2];
|
||||
ActorNotificationTableSubscribeData *data =
|
||||
(ActorNotificationTableSubscribeData *) callback_data->data->Get();
|
||||
/* The payload should be the concatenation of three IDs. */
|
||||
ActorID actor_id;
|
||||
WorkerID driver_id;
|
||||
DBClientID local_scheduler_id;
|
||||
bool reconstruct;
|
||||
RAY_CHECK(sizeof(actor_id) + sizeof(driver_id) +
|
||||
sizeof(local_scheduler_id) + 1 ==
|
||||
payload->len);
|
||||
char *current_ptr = payload->str;
|
||||
/* Parse the actor ID. */
|
||||
memcpy(&actor_id, current_ptr, sizeof(actor_id));
|
||||
current_ptr += sizeof(actor_id);
|
||||
/* Parse the driver ID. */
|
||||
memcpy(&driver_id, current_ptr, sizeof(driver_id));
|
||||
current_ptr += sizeof(driver_id);
|
||||
/* Parse the local scheduler ID. */
|
||||
memcpy(&local_scheduler_id, current_ptr, sizeof(local_scheduler_id));
|
||||
current_ptr += sizeof(local_scheduler_id);
|
||||
/* Parse the reconstruct bit. */
|
||||
if (*current_ptr == '1') {
|
||||
reconstruct = true;
|
||||
} else if (*current_ptr == '0') {
|
||||
reconstruct = false;
|
||||
} else {
|
||||
reconstruct = false; // We set this value to avoid a compiler warning.
|
||||
RAY_LOG(FATAL) << "This code should be unreachable.";
|
||||
}
|
||||
current_ptr += 1;
|
||||
|
||||
auto message =
|
||||
flatbuffers::GetRoot<ActorCreationNotification>(payload->str);
|
||||
ActorID actor_id = from_flatbuf(*message->actor_id());
|
||||
WorkerID driver_id = from_flatbuf(*message->driver_id());
|
||||
DBClientID local_scheduler_id =
|
||||
from_flatbuf(*message->local_scheduler_id());
|
||||
|
||||
if (data->subscribe_callback) {
|
||||
data->subscribe_callback(actor_id, driver_id, local_scheduler_id,
|
||||
reconstruct, data->subscribe_context);
|
||||
data->subscribe_context);
|
||||
}
|
||||
} else if (strcmp(message_type->str, "subscribe") == 0) {
|
||||
/* The reply for the initial SUBSCRIBE command. */
|
||||
|
||||
@@ -332,6 +332,14 @@ void redis_plasma_manager_send_heartbeat(TableCallbackData *callback_data);
|
||||
*/
|
||||
void redis_actor_table_mark_removed(DBHandle *db, ActorID actor_id);
|
||||
|
||||
/// Publish an actor creation notification.
|
||||
///
|
||||
/// \param callback_data Data structure containing redis connection and timeout
|
||||
/// information.
|
||||
/// \return Void.
|
||||
void redis_publish_actor_creation_notification(
|
||||
TableCallbackData *callback_data);
|
||||
|
||||
/**
|
||||
* Subscribe to updates about newly created actors.
|
||||
*
|
||||
|
||||
+36
-4
@@ -37,8 +37,10 @@ class TaskBuilder {
|
||||
void Start(UniqueID driver_id,
|
||||
TaskID parent_task_id,
|
||||
int64_t parent_counter,
|
||||
ActorID actor_creation_id,
|
||||
ObjectID actor_creation_dummy_object_id,
|
||||
ActorID actor_id,
|
||||
ActorID actor_handle_id,
|
||||
ActorHandleID actor_handle_id,
|
||||
int64_t actor_counter,
|
||||
bool is_actor_checkpoint_method,
|
||||
FunctionID function_id,
|
||||
@@ -46,6 +48,8 @@ class TaskBuilder {
|
||||
driver_id_ = driver_id;
|
||||
parent_task_id_ = parent_task_id;
|
||||
parent_counter_ = parent_counter;
|
||||
actor_creation_id_ = actor_creation_id;
|
||||
actor_creation_dummy_object_id_ = actor_creation_dummy_object_id;
|
||||
actor_id_ = actor_id;
|
||||
actor_handle_id_ = actor_handle_id;
|
||||
actor_counter_ = actor_counter;
|
||||
@@ -58,6 +62,9 @@ class TaskBuilder {
|
||||
sha256_update(&ctx, (BYTE *) &driver_id, sizeof(driver_id));
|
||||
sha256_update(&ctx, (BYTE *) &parent_task_id, sizeof(parent_task_id));
|
||||
sha256_update(&ctx, (BYTE *) &parent_counter, sizeof(parent_counter));
|
||||
sha256_update(&ctx, (BYTE *) &actor_creation_id, sizeof(actor_creation_id));
|
||||
sha256_update(&ctx, (BYTE *) &actor_creation_dummy_object_id,
|
||||
sizeof(actor_creation_dummy_object_id));
|
||||
sha256_update(&ctx, (BYTE *) &actor_id, sizeof(actor_id));
|
||||
sha256_update(&ctx, (BYTE *) &actor_counter, sizeof(actor_counter));
|
||||
sha256_update(&ctx, (BYTE *) &is_actor_checkpoint_method,
|
||||
@@ -103,6 +110,8 @@ class TaskBuilder {
|
||||
auto message = CreateTaskInfo(
|
||||
fbb, to_flatbuf(fbb, driver_id_), to_flatbuf(fbb, task_id),
|
||||
to_flatbuf(fbb, parent_task_id_), parent_counter_,
|
||||
to_flatbuf(fbb, actor_creation_id_),
|
||||
to_flatbuf(fbb, actor_creation_dummy_object_id_),
|
||||
to_flatbuf(fbb, actor_id_), to_flatbuf(fbb, actor_handle_id_),
|
||||
actor_counter_, is_actor_checkpoint_method_,
|
||||
to_flatbuf(fbb, function_id_), arguments, fbb.CreateVector(returns),
|
||||
@@ -127,6 +136,8 @@ class TaskBuilder {
|
||||
UniqueID driver_id_;
|
||||
TaskID parent_task_id_;
|
||||
int64_t parent_counter_;
|
||||
ActorID actor_creation_id_;
|
||||
ObjectID actor_creation_dummy_object_id_;
|
||||
ActorID actor_id_;
|
||||
ActorID actor_handle_id_;
|
||||
int64_t actor_counter_;
|
||||
@@ -170,15 +181,18 @@ void TaskSpec_start_construct(TaskBuilder *builder,
|
||||
UniqueID driver_id,
|
||||
TaskID parent_task_id,
|
||||
int64_t parent_counter,
|
||||
ActorID actor_creation_id,
|
||||
ObjectID actor_creation_dummy_object_id,
|
||||
ActorID actor_id,
|
||||
ActorID actor_handle_id,
|
||||
int64_t actor_counter,
|
||||
bool is_actor_checkpoint_method,
|
||||
FunctionID function_id,
|
||||
int64_t num_returns) {
|
||||
builder->Start(driver_id, parent_task_id, parent_counter, actor_id,
|
||||
actor_handle_id, actor_counter, is_actor_checkpoint_method,
|
||||
function_id, num_returns);
|
||||
builder->Start(driver_id, parent_task_id, parent_counter, actor_creation_id,
|
||||
actor_creation_dummy_object_id, actor_id, actor_handle_id,
|
||||
actor_counter, is_actor_checkpoint_method, function_id,
|
||||
num_returns);
|
||||
}
|
||||
|
||||
TaskSpec *TaskSpec_finish_construct(TaskBuilder *builder, int64_t *size) {
|
||||
@@ -233,6 +247,24 @@ bool TaskSpec_is_actor_task(TaskSpec *spec) {
|
||||
return !TaskSpec_actor_id(spec).is_nil();
|
||||
}
|
||||
|
||||
ActorID TaskSpec_actor_creation_id(TaskSpec *spec) {
|
||||
RAY_CHECK(spec);
|
||||
auto message = flatbuffers::GetRoot<TaskInfo>(spec);
|
||||
return from_flatbuf(*message->actor_creation_id());
|
||||
}
|
||||
|
||||
ObjectID TaskSpec_actor_creation_dummy_object_id(TaskSpec *spec) {
|
||||
RAY_CHECK(spec);
|
||||
// The task must be an actor method.
|
||||
RAY_CHECK(TaskSpec_is_actor_task(spec));
|
||||
auto message = flatbuffers::GetRoot<TaskInfo>(spec);
|
||||
return from_flatbuf(*message->actor_creation_dummy_object_id());
|
||||
}
|
||||
|
||||
bool TaskSpec_is_actor_creation_task(TaskSpec *spec) {
|
||||
return !TaskSpec_actor_creation_id(spec).is_nil();
|
||||
}
|
||||
|
||||
int64_t TaskSpec_actor_counter(TaskSpec *spec) {
|
||||
RAY_CHECK(spec);
|
||||
auto message = flatbuffers::GetRoot<TaskInfo>(spec);
|
||||
|
||||
+33
-5
@@ -190,6 +190,9 @@ void free_task_builder(TaskBuilder *builder);
|
||||
* @param parent_task_id The task ID of the task that submitted this task.
|
||||
* @param parent_counter A counter indicating how many tasks were submitted by
|
||||
* the parent task prior to this one.
|
||||
* @param actor_creation_id The actor creation ID of this task.
|
||||
* @param actor_creation_dummy_object_id The dummy object for the corresponding
|
||||
* actor creation task, assuming this is an actor method.
|
||||
* @param actor_id The ID of the actor that this task is for. If it is not an
|
||||
* actor task, then this if NIL_ACTOR_ID.
|
||||
* @param actor_handle_id The ID of the actor handle that this task was
|
||||
@@ -210,8 +213,10 @@ void TaskSpec_start_construct(TaskBuilder *B,
|
||||
UniqueID driver_id,
|
||||
TaskID parent_task_id,
|
||||
int64_t parent_counter,
|
||||
UniqueID actor_id,
|
||||
UniqueID actor_handle_id,
|
||||
ActorID actor_creation_id,
|
||||
ObjectID actor_creation_dummy_object_id,
|
||||
ActorID actor_id,
|
||||
ActorHandleID actor_handle_id,
|
||||
int64_t actor_counter,
|
||||
bool is_actor_checkpoint_method,
|
||||
FunctionID function_id,
|
||||
@@ -241,7 +246,7 @@ FunctionID TaskSpec_function(TaskSpec *spec);
|
||||
* @param spec The task_spec in question.
|
||||
* @return The actor ID of the actor the task is part of.
|
||||
*/
|
||||
UniqueID TaskSpec_actor_id(TaskSpec *spec);
|
||||
ActorID TaskSpec_actor_id(TaskSpec *spec);
|
||||
|
||||
/**
|
||||
* Return the actor handle ID of the task.
|
||||
@@ -249,7 +254,7 @@ UniqueID TaskSpec_actor_id(TaskSpec *spec);
|
||||
* @param spec The task_spec in question.
|
||||
* @return The ID of the actor handle that the task was submitted through.
|
||||
*/
|
||||
UniqueID TaskSpec_actor_handle_id(TaskSpec *spec);
|
||||
ActorID TaskSpec_actor_handle_id(TaskSpec *spec);
|
||||
|
||||
/**
|
||||
* Return whether this task is for an actor.
|
||||
@@ -259,6 +264,26 @@ UniqueID TaskSpec_actor_handle_id(TaskSpec *spec);
|
||||
*/
|
||||
bool TaskSpec_is_actor_task(TaskSpec *spec);
|
||||
|
||||
/// Return whether this task is an actor creation task or not.
|
||||
///
|
||||
/// \param spec The task_spec in question.
|
||||
/// \return True if this task is an actor creation task and false otherwise.
|
||||
bool TaskSpec_is_actor_creation_task(TaskSpec *spec);
|
||||
|
||||
/// Return the actor creation ID of the task. The task must be an actor creation
|
||||
/// task.
|
||||
///
|
||||
/// \param spec The task_spec in question.
|
||||
/// \return The actor creation ID if this is an actor creation task.
|
||||
ActorID TaskSpec_actor_creation_id(TaskSpec *spec);
|
||||
|
||||
/// Return the actor creation dummy object ID of the task. The task must be an
|
||||
/// actor task.
|
||||
///
|
||||
/// \param spec The task_spec in question.
|
||||
/// \return The actor creation dummy object ID corresponding to this actor task.
|
||||
ObjectID TaskSpec_actor_creation_dummy_object_id(TaskSpec *spec);
|
||||
|
||||
/**
|
||||
* Return the actor counter of the task. This starts at 0 and increments by 1
|
||||
* every time a new task is submitted to run on the actor.
|
||||
@@ -508,7 +533,10 @@ typedef enum {
|
||||
/** The task was not able to finish. */
|
||||
TASK_STATUS_LOST = 32,
|
||||
/** The task will be submitted for reexecution. */
|
||||
TASK_STATUS_RECONSTRUCTING = 64
|
||||
TASK_STATUS_RECONSTRUCTING = 64,
|
||||
/** An actor task is cached at a local scheduler and is waiting for the
|
||||
* corresponding actor to be created. */
|
||||
TASK_STATUS_ACTOR_CACHED = 128
|
||||
} scheduling_state;
|
||||
|
||||
/** A task is an execution of a task specification. It has a state of execution
|
||||
|
||||
@@ -14,8 +14,8 @@ static inline TaskExecutionSpec example_task_execution_spec_with_args(
|
||||
TaskID parent_task_id = TaskID::from_random();
|
||||
FunctionID func_id = FunctionID::from_random();
|
||||
TaskSpec_start_construct(g_task_builder, UniqueID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
num_returns);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, num_returns);
|
||||
for (int64_t i = 0; i < num_args; ++i) {
|
||||
ObjectID arg_id;
|
||||
if (arg_ids == NULL) {
|
||||
|
||||
@@ -16,8 +16,8 @@ TEST task_test(void) {
|
||||
FunctionID func_id = FunctionID::from_random();
|
||||
TaskBuilder *builder = make_task_builder();
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
2);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 2);
|
||||
|
||||
UniqueID arg1 = UniqueID::from_random();
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
@@ -56,8 +56,8 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a first task. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 3);
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
TaskSpec_args_add_val(builder, arg2, 11);
|
||||
int64_t size1;
|
||||
@@ -65,8 +65,8 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a second identical task. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 3);
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
TaskSpec_args_add_val(builder, arg2, 11);
|
||||
int64_t size2;
|
||||
@@ -86,8 +86,8 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a task with a different parent task ID. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), TaskID::from_random(), 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 3);
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
TaskSpec_args_add_val(builder, arg2, 11);
|
||||
int64_t size3;
|
||||
@@ -95,8 +95,8 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a task with a different parent counter. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 1,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 3);
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
TaskSpec_args_add_val(builder, arg2, 11);
|
||||
int64_t size4;
|
||||
@@ -104,8 +104,9 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a task with a different function ID. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false,
|
||||
FunctionID::from_random(), 3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, FunctionID::from_random(),
|
||||
3);
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
TaskSpec_args_add_val(builder, arg2, 11);
|
||||
int64_t size5;
|
||||
@@ -113,8 +114,8 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a task with a different object ID argument. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 3);
|
||||
ObjectID object_id = ObjectID::from_random();
|
||||
TaskSpec_args_add_ref(builder, &object_id, 1);
|
||||
TaskSpec_args_add_val(builder, arg2, 11);
|
||||
@@ -123,8 +124,8 @@ TEST deterministic_ids_test(void) {
|
||||
|
||||
/* Construct a task with a different value argument. */
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
3);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 3);
|
||||
TaskSpec_args_add_ref(builder, &arg1, 1);
|
||||
TaskSpec_args_add_val(builder, (uint8_t *) "hello_world", 11);
|
||||
int64_t size7;
|
||||
@@ -168,8 +169,8 @@ TEST send_task(void) {
|
||||
TaskID parent_task_id = TaskID::from_random();
|
||||
FunctionID func_id = FunctionID::from_random();
|
||||
TaskSpec_start_construct(builder, DriverID::nil(), parent_task_id, 0,
|
||||
ActorID::nil(), ActorID::nil(), 0, false, func_id,
|
||||
2);
|
||||
ActorID::nil(), ObjectID::nil(), ActorID::nil(),
|
||||
ActorID::nil(), 0, false, func_id, 2);
|
||||
ObjectID object_id = ObjectID::from_random();
|
||||
TaskSpec_args_add_ref(builder, &object_id, 1);
|
||||
TaskSpec_args_add_val(builder, (uint8_t *) "Hello", 5);
|
||||
|
||||
Reference in New Issue
Block a user