static int get_rlist_result (zhash_t *mods, flux_mrpc_t *mrpc, uint32_t nodeid, int *ep) { JSON o = NULL; int rc = -1; const char *name, *digest; int i, len, errnum, size, idle; module_t *m; if (flux_mrpc_get_outarg_obj (mrpc, nodeid, &o) < 0) goto done; if (modctl_rlist_dec (o, &errnum, &len) < 0) goto done; for (i = 0; i < len; i++) { if (modctl_rlist_dec_nth (o, i, &name, &size, &digest, &idle) < 0) goto done; if (!(m = zhash_lookup (mods, digest))) { if (!(m = module_create (name, size, digest, idle, nodeid))) goto done; zhash_update (mods, digest, m); zhash_freefn (mods, digest, (zhash_free_fn *)module_destroy); } else if (module_update (m, idle, nodeid) < 0) goto done; } *ep = errnum; rc = 0; done: Jput (o); return rc; }
int zhash_load (zhash_t *self, char *filename) { assert (self); zhash_autofree (self); FILE *handle = fopen (filename, "r"); if (!handle) return -1; // Failed to create file char buffer [1024]; while (fgets (buffer, 1024, handle)) { // Skip lines starting with "#" if (buffer [0] == '#') continue; // Buffer may end in newline, which we don't want if (buffer [strlen (buffer) - 1] == '\n') buffer [strlen (buffer) - 1] = 0; // Split at equals, if any char *equals = strchr (buffer, '='); if (!equals) break; // Some error, stop parsing it *equals++ = 0; zhash_update (self, buffer, equals); } fclose (handle); return 0; }
int attr_add_active (attr_t *attrs, const char *name, int flags, attr_get_f get, attr_set_f set, void *arg) { struct entry *e; int rc = -1; if ((e = zhash_lookup (attrs->hash, name))) { if (!set) { errno = EEXIST; goto done; } if (set (name, e->val, arg) < 0) goto done; } e = entry_create (name, NULL, flags); e->set = set; e->get = get; e->arg = arg; e->flags |= FLUX_ATTRFLAG_ACTIVE; zhash_update (attrs->hash, name, e); zhash_freefn (attrs->hash, name, entry_destroy); rc = 0; done: return rc; }
int lsmod_hash_cb (uint32_t nodeid, const char *json_str, zhash_t *mods) { flux_modlist_t modlist; mod_t *m; int i, len; const char *name, *digest; int size, idle; int rc = -1; if (!(modlist = flux_lsmod_json_decode (json_str))) goto done; if ((len = flux_modlist_count (modlist)) == -1) goto done; for (i = 0; i < len; i++) { if (flux_modlist_get (modlist, i, &name, &size, &digest, &idle) < 0) goto done; if ((m = zhash_lookup (mods, digest))) { if (idle < m->idle) m->idle = idle; if (!nodeset_add_rank (m->nodeset, nodeid)) oom (); } else { m = mod_create (name, size, digest, idle, nodeid); zhash_update (mods, digest, m); zhash_freefn (mods, digest, (zhash_free_fn *)mod_destroy); } } rc = 0; done: if (modlist) flux_modlist_destroy (modlist); return rc; }
static int attr_set_rpc (attr_ctx_t *ctx, const char *name, const char *val) { flux_future_t *f; attr_t *attr; int rc = -1; #if JANSSON_VERSION_HEX >= 0x020800 /* $? format specifier was introduced in jansson 2.8 */ f = flux_rpc_pack (ctx->h, "attr.set", FLUX_NODEID_ANY, 0, "{s:s, s:s?}", "name", name, "value", val); #else f = flux_rpc_pack (ctx->h, "attr.set", FLUX_NODEID_ANY, 0, val ? "{s:s, s:s}" : "{s:s, s:n}", "name", name, "value", val); #endif if (!f) goto done; if (flux_future_get (f, NULL) < 0) goto done; if (val) { if (!(attr = attr_create (val, 0))) goto done; zhash_update (ctx->hash, name, attr); zhash_freefn (ctx->hash, name, attr_destroy); } else zhash_delete (ctx->hash, name); rc = 0; done: flux_future_destroy (f); return rc; }
static void server_accept (server_t *self, const char *key, const char *value) { tuple_t *tuple = (tuple_t *) zhash_lookup (self->tuples, key); if (tuple && streq (tuple->value, value)) return; // Duplicate tuple, do nothing // Create new tuple tuple = (tuple_t *) zmalloc (sizeof (tuple_t)); assert (tuple); tuple->container = self->tuples; tuple->key = strdup (key); tuple->value = strdup (value); // Store new tuple zhash_update (tuple->container, key, tuple); zhash_freefn (tuple->container, key, tuple_free); // Deliver to calling application zstr_sendx (self->pipe, "DELIVER", key, value, NULL); // Hold in server context so we can broadcast to all clients self->cur_tuple = tuple; engine_broadcast_event (self, NULL, forward_event); // Copy new tuple announcement to all remotes zsock_t *remote = (zsock_t *) zlist_first (self->remotes); while (remote) { int rc = zgossip_msg_send_publish (remote, key, value, 0); assert (rc == 0); remote = (zsock_t *) zlist_next (self->remotes); } }
static int disconnect_update (client_t *c, const flux_msg_t *msg) { char *p; char *key = NULL; char *svc = NULL; const char *topic; uint32_t nodeid; int flags; struct disconnect_notify *d; int rc = -1; if (flux_msg_get_topic (msg, &topic) < 0) goto done; if (flux_msg_get_nodeid (msg, &nodeid, &flags) < 0) goto done; svc = xstrdup (topic); if ((p = strchr (svc, '.'))) *p = '\0'; key = xasprintf ("%s:%u:%d", svc, nodeid, flags); if (!zhash_lookup (c->disconnect_notify, key)) { d = xzmalloc (sizeof (*d)); d->nodeid = nodeid; d->flags = flags; d->topic = xasprintf ("%s.disconnect", svc); zhash_update (c->disconnect_notify, key, d); } rc = 0; done: if (svc) free (svc); if (key) free (key); return rc; }
maltcp_ctx_connection_t *maltcp_ctx_connection_register_outgoing(maltcp_ctx_t *self, int socket, char *peer_uri) { maltcp_ctx_connection_t *cnx_ptr = maltcp_ctx_connection_create(socket); if (cnx_ptr != NULL) { char *uri = (char *) malloc(strlen(peer_uri) +1); strcpy(uri, peer_uri); zhash_update(self->cnx_table, uri, cnx_ptr); zhash_freefn(self->cnx_table, uri, free); } return cnx_ptr; }
static int s_kvs_put (void *arg, const char *kvsname, const char *key, const char *val) { diag ("%s: %s::%s", __FUNCTION__, kvsname, key); struct context *ctx = arg; int rc = 0; zhash_update (ctx->kvs, key, xstrdup (val)); zhash_freefn (ctx->kvs, key, (zhash_free_fn *)free); return rc; }
static agent_t * agent_new (zctx_t *ctx, void *pipe) { void *inbox = zsocket_new (ctx, ZMQ_ROUTER); if (!inbox) // Interrupted return NULL; agent_t *self = (agent_t *) zmalloc (sizeof (agent_t)); self->ctx = ctx; self->pipe = pipe; self->udp = zre_udp_new (ZRE_DISCOVERY_PORT); self->inbox = inbox; self->host = zre_udp_host (self->udp); self->port = zsocket_bind (self->inbox, "tcp://*:*"); sprintf (self->endpoint, "%s:%d", self->host, self->port); if (self->port < 0) { // Interrupted zre_udp_destroy (&self->udp); free (self); return NULL; } self->uuid = zre_uuid_new (); self->identity = strdup (zre_uuid_str (self->uuid)); self->peers = zhash_new (); self->peer_groups = zhash_new (); self->own_groups = zhash_new (); self->headers = zhash_new (); zhash_autofree (self->headers); self->log = zre_log_new (self->endpoint); // Set up content distribution network: Each server binds to an // ephemeral port and publishes a temporary directory that acts // as the outbox for this node. // sprintf (self->fmq_outbox, "%s/send/%s", s_tmpdir (), self->identity); zfile_mkdir (self->fmq_outbox); sprintf (self->fmq_inbox, "%s/recv/%s", s_tmpdir (), self->identity); zfile_mkdir (self->fmq_inbox); self->fmq_server = fmq_server_new (); self->fmq_service = fmq_server_bind (self->fmq_server, "tcp://*:*"); fmq_server_publish (self->fmq_server, self->fmq_outbox, "/"); fmq_server_set_anonymous (self->fmq_server, true); char publisher [32]; sprintf (publisher, "tcp://%s:%d", self->host, self->fmq_service); zhash_update (self->headers, "X-FILEMQ", publisher); // Client will connect as it discovers new nodes self->fmq_client = fmq_client_new (); fmq_client_set_inbox (self->fmq_client, self->fmq_inbox); fmq_client_set_resync (self->fmq_client, true); fmq_client_subscribe (self->fmq_client, "/"); return self; }
int flux_attr_fake (flux_t *h, const char *name, const char *val, int flags) { attr_ctx_t *ctx = getctx (h); attr_t *attr = attr_create (val, flags); if (!ctx || !attr) return -1; zhash_update (ctx->hash, name, attr); zhash_freefn (ctx->hash, name, attr_destroy); return 0; }
/* Proxy ping. */ void xping_request_cb (flux_t h, flux_msg_handler_t *w, const flux_msg_t *msg, void *arg) { ctx_t *ctx = arg; const char *json_str; int saved_errno; int rank, seq = ctx->ping_seq++; const char *service; char *hashkey = NULL; JSON in = Jnew (); JSON o = NULL; flux_msg_t *cpy; if (flux_request_decode (msg, NULL, &json_str) < 0) { saved_errno = errno; goto error; } if (!(o = Jfromstr (json_str)) || !Jget_int (o, "rank", &rank) || !Jget_str (o, "service", &service)) { saved_errno = errno = EPROTO; goto error; } flux_log (h, LOG_DEBUG, "Rxping rank=%d service=%s", rank, service); Jadd_int (in, "seq", seq); flux_log (h, LOG_DEBUG, "Tping seq=%d %d!%s", seq, rank, service); flux_rpc_t *rpc; if (!(rpc = flux_rpc (h, service, Jtostr (in), rank, FLUX_RPC_NORESPONSE))) { saved_errno = errno; goto error; } flux_rpc_destroy (rpc); if (!(cpy = flux_msg_copy (msg, true))) { saved_errno = errno; goto error; } hashkey = xasprintf ("%d", seq); zhash_update (ctx->ping_requests, hashkey, cpy); zhash_freefn (ctx->ping_requests, hashkey, (zhash_free_fn *)flux_msg_destroy); Jput (o); Jput (in); if (hashkey) free (hashkey); return; error: if (flux_respond (h, msg, saved_errno, NULL) < 0) flux_log_error (h, "%s: flux_respond", __FUNCTION__); Jput (o); Jput (in); }
int zhash_load (zhash_t *self, const char *filename) { assert (self); zhash_autofree (self); // Whether or not file exists, we'll track the filename and last // modification date (0 for unknown files), so that zhash_refresh () // will always work after zhash_load (), to load a newly-created // file. // Take copy of filename in case self->filename is same string. char *filename_copy = strdup (filename); if (filename_copy) { free (self->filename); self->filename = filename_copy; self->modified = zsys_file_modified (self->filename); FILE *handle = fopen (self->filename, "r"); if (handle) { char *buffer = (char *) zmalloc (1024); if (buffer) { while (fgets (buffer, 1024, handle)) { // Skip lines starting with "#" or that do not look like // name=value data. char *equals = strchr (buffer, '='); if (buffer [0] == '#' || equals == buffer || !equals) continue; // Buffer may end in newline, which we don't want if (buffer [strlen (buffer) - 1] == '\n') buffer [strlen (buffer) - 1] = 0; *equals++ = 0; zhash_update (self, buffer, equals); } free (buffer); } else { fclose (handle); return -1; // Out of memory } fclose (handle); } else return -1; // Failed to open file for reading } else return -1; // Out of memory return 0; }
int attr_add (attr_t *attrs, const char *name, const char *val, int flags) { struct entry *e; if (name == NULL || (flags & FLUX_ATTRFLAG_ACTIVE)) { errno = EINVAL; return -1; } if ((e = zhash_lookup (attrs->hash, name))) { errno = EEXIST; return -1; } e = entry_create (name, val, flags); zhash_update (attrs->hash, name, e); zhash_freefn (attrs->hash, name, entry_destroy); return 0; }
static int fetch_and_update_state (zhash_t *aj , int64_t j, int64_t ns) { int *t = NULL; char key[20] = {'\0'}; if (!aj) return J_FOR_RENT;; snprintf (key, 20, "%ld", j); if ( !(t = ((int *)zhash_lookup (aj, (const char *)key)))) return J_FOR_RENT; if (ns == J_COMPLETE) zhash_delete (aj, key); else zhash_update (aj, key, (void *)(intptr_t)ns); /* safe to convert t to int */ return (intptr_t) t; }
void zre_msg_headers_insert (zre_msg_t *self, const char *key, const char *format, ...) { // Format into newly allocated string assert (self); va_list argptr; va_start (argptr, format); char *string = zsys_vprintf (format, argptr); va_end (argptr); // Store string in hash table if (!self->headers) { self->headers = zhash_new (); zhash_autofree (self->headers); } zhash_update (self->headers, key, string); free (string); }
zhash_t *zhash_fromargv (int argc, char **argv) { zhash_t *args = zhash_new (); int i; if (args) { for (i = 0; i < argc; i++) { char *key = xstrdup (argv[i]); char *val = strchr (key, '='); if (val) { *val++ = '\0'; zhash_update (args, key, xstrdup (val)); zhash_freefn (args, key, free); } free (key); } } return args; }
void zre_msg_headers_insert (zre_msg_t *self, char *key, char *format, ...) { // Format string into buffer assert (self); va_list argptr; va_start (argptr, format); char *string = (char *) malloc (STRING_MAX + 1); assert (string); vsnprintf (string, STRING_MAX, format, argptr); va_end (argptr); // Store string in hash table if (!self->headers) { self->headers = zhash_new (); zhash_autofree (self->headers); } zhash_update (self->headers, key, string); }
static int fetch_and_update_state (zhash_t *aj , int64_t j, int64_t ns) { int *t = NULL; char *key = NULL; if (!aj) return J_FOR_RENT; key = xasprintf ("%"PRId64, j); if ( !(t = ((int *)zhash_lookup (aj, (const char *)key)))) { free (key); return J_FOR_RENT; } if (ns == J_COMPLETE || ns == J_FAILED) zhash_delete (aj, key); else zhash_update (aj, key, (void *)(intptr_t)ns); free (key); /* safe to convert t to int */ return (intptr_t) t; }
/* Proxy ping. */ static int xping_request_cb (flux_t h, int typemask, zmsg_t **zmsg, void *arg) { ctx_t *ctx = arg; int rank, seq = ctx->ping_seq++; const char *service; char *hashkey = NULL; JSON in = Jnew (); JSON o = NULL; if (flux_json_request_decode (*zmsg, &o) < 0) { if (flux_err_respond (h, errno, zmsg) < 0) flux_log (h, LOG_ERR, "%s: flux_err_respond: %s", __FUNCTION__, strerror (errno)); goto done; } if (!Jget_int (o, "rank", &rank) || !Jget_str (o, "service", &service)) { if (flux_err_respond (h, EPROTO, zmsg) < 0) flux_log (h, LOG_ERR, "%s: flux_err_respond: %s", __FUNCTION__, strerror (errno)); goto done; } flux_log (h, LOG_DEBUG, "Rxping rank=%d service=%s", rank, service); Jadd_int (in, "seq", seq); flux_log (h, LOG_DEBUG, "Tping seq=%d %d!%s", seq, rank, service); if (flux_json_request (h, rank, 0, service, in) < 0) { if (flux_err_respond (h, errno, zmsg) < 0) flux_log (h, LOG_ERR, "%s: flux_err_respond: %s", __FUNCTION__, strerror (errno)); goto done; } hashkey = xasprintf ("%d", seq); zhash_update (ctx->ping_requests, hashkey, *zmsg); *zmsg = NULL; done: Jput (o); Jput (in); if (hashkey) free (hashkey); return 0; }
static module_t *module_create (const char *path, char *argz, size_t argz_len) { module_t *m = xzmalloc (sizeof (*m)); struct stat sb; char **av = NULL; if (stat (path, &sb) < 0 || !(m->name = flux_modname (path, NULL, NULL)) || !(m->digest = digest (path))) { module_destroy (m); errno = ESRCH; return NULL; } m->size = sb.st_size; m->dso = dlopen (path, RTLD_NOW | RTLD_LOCAL); if (!m->dso || !(m->main = dlsym (m->dso, "mod_main"))) { module_destroy (m); errno = EINVAL; return NULL; } av = xzmalloc (sizeof (av[0]) * (argz_count (argz, argz_len) + 1)); argz_extract (argz, argz_len, av); if (m->main (NULL, argz_count (argz, argz_len), av) < 0) { module_destroy (m); errno = EINVAL; return NULL; } if (zhash_lookup (modules, m->name)) { module_destroy (m); errno = EEXIST; return NULL; } zhash_update (modules, m->name, m); zhash_freefn (modules, m->name, (zhash_free_fn *)module_destroy); if (av) free (av); return m; }
static int attr_get_rpc (attr_ctx_t *ctx, const char *name, attr_t **attrp) { flux_future_t *f; const char *val; int flags; attr_t *attr; int rc = -1; if (!(f = flux_rpc_pack (ctx->h, "attr.get", FLUX_NODEID_ANY, 0, "{s:s}", "name", name))) goto done; if (flux_rpc_get_unpack (f, "{s:s, s:i}", "value", &val, "flags", &flags) < 0) goto done; if (!(attr = attr_create (val, flags))) goto done; zhash_update (ctx->hash, name, attr); zhash_freefn (ctx->hash, name, attr_destroy); *attrp = attr; rc = 0; done: flux_future_destroy (f); return rc; }
static void zsync_node_recv_from_zyre (zsync_node_t *self) { zsync_peer_t *sender; char *zyre_sender; zuuid_t *sender_uuid; zmsg_t *zyre_in, *zyre_out, *fm_msg; zlist_t *fpaths, *fmetadata; zyre_event_t *event = zyre_event_recv (self->zyre); zyre_sender = zyre_event_sender (event); // get tmp uuid switch (zyre_event_type (event)) { case ZYRE_EVENT_ENTER: printf("[ND] ZS_ENTER: %s\n", zyre_sender); zhash_insert (self->zyre_peers, zyre_sender, NULL); break; case ZYRE_EVENT_JOIN: printf ("[ND] ZS_JOIN: %s\n", zyre_sender); // Obtain own current state zsync_msg_send_req_state (self->zsync_pipe); zsync_msg_t *msg_state = zsync_msg_recv (self->zsync_pipe); assert (zsync_msg_id (msg_state) == ZSYNC_MSG_RES_STATE); uint64_t state = zsync_msg_state (msg_state); // Send GREET message zyre_out = zmsg_new (); zs_msg_pack_greet (zyre_out, zuuid_data (self->own_uuid), state); zyre_whisper (self->zyre, zyre_sender, &zyre_out); break; case ZYRE_EVENT_LEAVE: break; case ZYRE_EVENT_EXIT: /* printf("[ND] ZS_EXIT %s left the house!\n", zyre_sender); sender = zhash_lookup (self->zyre_peers, zyre_sender); if (sender) { // Reset Managers zmsg_t *reset_msg = zmsg_new (); zmsg_addstr (reset_msg, zsync_peer_uuid (sender)); zmsg_addstr (reset_msg, "ABORT"); zmsg_send (&reset_msg, self->file_pipe); reset_msg = zmsg_new (); zmsg_addstr (reset_msg, zsync_peer_uuid (sender)); zmsg_addstr (reset_msg, "ABORT"); zmsg_send (&reset_msg, self->credit_pipe); // Remove Peer from active list zhash_delete (self->zyre_peers, zyre_sender); }*/ break; case ZYRE_EVENT_WHISPER: case ZYRE_EVENT_SHOUT: printf ("[ND] ZS_WHISPER: %s\n", zyre_sender); sender = zhash_lookup (self->zyre_peers, zyre_sender); zyre_in = zyre_event_msg (event); zs_msg_t *msg = zs_msg_unpack (zyre_in); switch (zs_msg_get_cmd (msg)) { case ZS_CMD_GREET: // Get perm uuid sender_uuid = zuuid_new (); zuuid_set (sender_uuid, zs_msg_uuid (msg)); sender = zsync_node_peers_lookup (self, zuuid_str (sender_uuid)); if (!sender) { sender = zsync_peer_new (zuuid_str (sender_uuid), 0x0); zlist_append (self->peers, sender); } assert (sender); zhash_update (self->zyre_peers, zyre_sender, sender); zsync_peer_set_zyre_state (sender, ZYRE_EVENT_JOIN); // Get current state for sender uint64_t remote_current_state = zs_msg_get_state (msg); printf ("[ND] current state: %"PRId64"\n", remote_current_state); // Lookup last known state uint64_t last_state_local = zsync_peer_state (sender); printf ("[ND] last known state: %"PRId64"\n", zsync_peer_state (sender)); // Send LAST_STATE if differs if (remote_current_state >= last_state_local) { zmsg_t *lmsg = zmsg_new (); zs_msg_pack_last_state (lmsg, last_state_local); zyre_whisper (self->zyre, zyre_sender, &lmsg); } break; case ZS_CMD_LAST_STATE: assert (sender); zyre_out = zmsg_new (); // Gets updates from client uint64_t last_state_remote = zs_msg_get_state (msg); zsync_msg_send_req_update (self->zsync_pipe, last_state_remote); zsync_msg_t *msg_upd = zsync_msg_recv (self->zsync_pipe); assert (zsync_msg_id (msg_upd) == ZSYNC_MSG_UPDATE); // Send UPDATE zyre_out = zsync_msg_update_msg (msg_upd); zyre_whisper (self->zyre, zyre_sender, &zyre_out); break; case ZS_CMD_UPDATE: printf ("[ND] UPDATE\n"); assert (sender); uint64_t state = zs_msg_get_state (msg); zsync_peer_set_state (sender, state); zsync_node_save_peers (self); fmetadata = zs_msg_get_fmetadata (msg); zmsg_t *zsync_msg = zmsg_new (); zs_msg_pack_update (zsync_msg, zs_msg_get_state (msg), fmetadata); zsync_msg_send_update (self->zsync_pipe, zsync_peer_uuid (sender), zsync_msg); break; case ZS_CMD_REQUEST_FILES: printf ("[ND] REQUEST FILES\n"); fpaths = zs_msg_fpaths (msg); zmsg_t *fm_msg = zmsg_new (); zmsg_addstr (fm_msg, zsync_peer_uuid (sender)); zmsg_addstr (fm_msg, "REQUEST"); char *fpath = zs_msg_fpaths_first (msg); while (fpath) { zmsg_addstr (fm_msg, fpath); printf("[ND] %s\n", fpath); fpath = zs_msg_fpaths_next (msg); } zmsg_send (&fm_msg, self->file_pipe); break; case ZS_CMD_GIVE_CREDIT: printf("[ND] GIVE CREDIT\n"); fm_msg = zmsg_new (); zmsg_addstr (fm_msg, zsync_peer_uuid (sender)); zmsg_addstr (fm_msg, "CREDIT"); zmsg_addstrf (fm_msg, "%"PRId64, zs_msg_get_credit (msg)); zmsg_send (&fm_msg, self->file_pipe); break; case ZS_CMD_SEND_CHUNK: printf("[ND] SEND_CHUNK (RCV)\n"); // Send receival to credit manager zframe_t *zframe = zs_msg_get_chunk (msg); uint64_t chunk_size = zframe_size (zframe); zsync_credit_msg_send_update (self->credit_pipe, zsync_peer_uuid (sender), chunk_size); // Pass chunk to client byte *data = zframe_data (zframe); zchunk_t *chunk = zchunk_new (data, chunk_size); char *path = zs_msg_get_file_path (msg); uint64_t seq = zs_msg_get_sequence (msg); uint64_t off = zs_msg_get_offset (msg); zsync_msg_send_chunk (self->zsync_pipe, chunk, path, seq, off); break; case ZS_CMD_ABORT: // TODO abort protocol managed file transfer printf("[ND] ABORT\n"); break; default: assert (false); break; } zs_msg_destroy (&msg); break; default: printf("[ND] Error command not found\n"); break; } zyre_event_destroy (&event); }
/// // Update item into hash table with specified key and item. // If key is already present, destroys old item and inserts new one. // Use free_fn method to ensure deallocator is properly called on item. void QZhash::update (const QString &key, void *item) { zhash_update (self, key.toUtf8().data(), item); }
static int agent_recv_from_api (agent_t *self) { // Get the whole message off the pipe in one go zmsg_t *request = zmsg_recv (self->pipe); char *command = zmsg_popstr (request); if (!command) return -1; // Interrupted if (streq (command, "WHISPER")) { // Get peer to send message to char *identity = zmsg_popstr (request); zre_peer_t *peer = (zre_peer_t *) zhash_lookup (self->peers, identity); // Send frame on out to peer's mailbox, drop message // if peer doesn't exist (may have been destroyed) if (peer) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_WHISPER); zre_msg_content_set (msg, zmsg_pop (request)); zre_peer_send (peer, &msg); } free (identity); } else if (streq (command, "SHOUT")) { // Get group to send message to char *name = zmsg_popstr (request); zre_group_t *group = (zre_group_t *) zhash_lookup (self->peer_groups, name); if (group) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_SHOUT); zre_msg_group_set (msg, name); zre_msg_content_set (msg, zmsg_pop (request)); zre_group_send (group, &msg); } free (name); } else if (streq (command, "JOIN")) { char *name = zmsg_popstr (request); zre_group_t *group = (zre_group_t *) zhash_lookup (self->own_groups, name); if (!group) { // Only send if we're not already in group group = zre_group_new (name, self->own_groups); zre_msg_t *msg = zre_msg_new (ZRE_MSG_JOIN); zre_msg_group_set (msg, name); // Update status before sending command zre_msg_status_set (msg, ++(self->status)); zhash_foreach (self->peers, s_peer_send, msg); zre_msg_destroy (&msg); zre_log_info (self->log, ZRE_LOG_MSG_EVENT_JOIN, NULL, name); } free (name); } else if (streq (command, "LEAVE")) { char *name = zmsg_popstr (request); zre_group_t *group = (zre_group_t *) zhash_lookup (self->own_groups, name); if (group) { // Only send if we are actually in group zre_msg_t *msg = zre_msg_new (ZRE_MSG_LEAVE); zre_msg_group_set (msg, name); // Update status before sending command zre_msg_status_set (msg, ++(self->status)); zhash_foreach (self->peers, s_peer_send, msg); zre_msg_destroy (&msg); zhash_delete (self->own_groups, name); zre_log_info (self->log, ZRE_LOG_MSG_EVENT_LEAVE, NULL, name); } free (name); } else if (streq (command, "SET")) { char *name = zmsg_popstr (request); char *value = zmsg_popstr (request); zhash_update (self->headers, name, value); free (name); free (value); } else if (streq (command, "PUBLISH")) { char *logical = zmsg_popstr (request); char *physical = zmsg_popstr (request); // Virtual filename must start with slash assert (logical [0] == '/'); // We create symbolic link pointing to real file char *symlink = malloc (strlen (logical) + 3); sprintf (symlink, "%s.ln", logical + 1); fmq_file_t *file = fmq_file_new (self->fmq_outbox, symlink); int rc = fmq_file_output (file); assert (rc == 0); fprintf (fmq_file_handle (file), "%s\n", physical); fmq_file_destroy (&file); free (symlink); free (logical); free (physical); } else if (streq (command, "RETRACT")) { char *logical = zmsg_popstr (request); // Logical filename must start with slash assert (logical [0] == '/'); // We create symbolic link pointing to real file char *symlink = malloc (strlen (logical) + 3); sprintf (symlink, "%s.ln", logical + 1); fmq_file_t *file = fmq_file_new (self->fmq_outbox, symlink); fmq_file_remove (file); free (symlink); free (logical); } free (command); zmsg_destroy (&request); return 0; }
static int zyre_node_recv_api (zyre_node_t *self) { // Get the whole message off the pipe in one go zmsg_t *request = zmsg_recv (self->pipe); char *command = zmsg_popstr (request); if (!command) return -1; // Interrupted if (streq (command, "SET NAME")) { free (self->name); self->name = zmsg_popstr (request); assert (self->name); } else if (streq (command, "SET HEADER")) { char *name = zmsg_popstr (request); char *value = zmsg_popstr (request); zhash_update (self->headers, name, value); zstr_free (&name); zstr_free (&value); } else if (streq (command, "SET VERBOSE")) self->verbose = true; else if (streq (command, "SET PORT")) { char *value = zmsg_popstr (request); self->beacon_port = atoi (value); zstr_free (&value); } else if (streq (command, "SET INTERVAL")) { char *value = zmsg_popstr (request); self->interval = atol (value); zstr_free (&value); } else if (streq (command, "UUID")) zstr_send (self->pipe, zuuid_str (self->uuid)); else if (streq (command, "NAME")) zstr_send (self->pipe, self->name); else if (streq (command, "BIND")) { char *endpoint = zmsg_popstr (request); zsock_signal (self->pipe, zyre_node_bind (self, endpoint)); zstr_free (&endpoint); } else if (streq (command, "CONNECT")) { char *endpoint = zmsg_popstr (request); zsock_signal (self->pipe, zyre_node_connect (self, endpoint)); zstr_free (&endpoint); } else if (streq (command, "START")) zsock_signal (self->pipe, zyre_node_start (self)); else if (streq (command, "STOP")) zsock_signal (self->pipe, zyre_node_stop (self)); else if (streq (command, "WHISPER")) { // Get peer to send message to char *identity = zmsg_popstr (request); zyre_peer_t *peer = (zyre_peer_t *) zhash_lookup (self->peers, identity); // Send frame on out to peer's mailbox, drop message // if peer doesn't exist (may have been destroyed) if (peer) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_WHISPER); zre_msg_set_content (msg, &request); zyre_peer_send (peer, &msg); } zstr_free (&identity); } else if (streq (command, "SHOUT")) { // Get group to send message to char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->peer_groups, name); if (group) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_SHOUT); zre_msg_set_group (msg, name); zre_msg_set_content (msg, &request); zyre_group_send (group, &msg); } zstr_free (&name); } else if (streq (command, "JOIN")) { char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->own_groups, name); if (!group) { // Only send if we're not already in group group = zyre_group_new (name, self->own_groups); zre_msg_t *msg = zre_msg_new (ZRE_MSG_JOIN); zre_msg_set_group (msg, name); // Update status before sending command zre_msg_set_status (msg, ++(self->status)); zhash_foreach (self->peers, zyre_node_send_peer, msg); zre_msg_destroy (&msg); if (self->verbose) zsys_info ("(%s) JOIN group=%s", self->name, name); } zstr_free (&name); } else if (streq (command, "LEAVE")) { char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->own_groups, name); if (group) { // Only send if we are actually in group zre_msg_t *msg = zre_msg_new (ZRE_MSG_LEAVE); zre_msg_set_group (msg, name); // Update status before sending command zre_msg_set_status (msg, ++(self->status)); zhash_foreach (self->peers, zyre_node_send_peer, msg); zre_msg_destroy (&msg); zhash_delete (self->own_groups, name); if (self->verbose) zsys_info ("(%s) LEAVE group=%s", self->name, name); } zstr_free (&name); } else if (streq (command, "DUMP")) zyre_node_dump (self); else if (streq (command, "$TERM")) self->terminated = true; else { zsys_error ("invalid command '%s'\n", command); assert (false); } zstr_free (&command); zmsg_destroy (&request); return 0; }
void flux_aux_set (flux_t h, const char *name, void *aux, flux_free_f destroy) { zhash_update (h->aux, name, aux); zhash_freefn (h->aux, name, destroy); }
static int zyre_node_recv_api (zyre_node_t *self) { // Get the whole message off the pipe in one go zmsg_t *request = zmsg_recv (self->pipe); char *command = zmsg_popstr (request); if (!command) return -1; // Interrupted if (streq (command, "SET")) { char *name = zmsg_popstr (request); char *value = zmsg_popstr (request); zhash_update (self->headers, name, value); zstr_free (&name); zstr_free (&value); } else if (streq (command, "START")) { zyre_node_start (self); zstr_send (self->pipe, "OK"); } else if (streq (command, "STOP")) { zyre_node_stop (self); zstr_send (self->pipe, "OK"); } else if (streq (command, "WHISPER")) { // Get peer to send message to char *identity = zmsg_popstr (request); zyre_peer_t *peer = (zyre_peer_t *) zhash_lookup (self->peers, identity); // Send frame on out to peer's mailbox, drop message // if peer doesn't exist (may have been destroyed) if (peer) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_WHISPER); zre_msg_set_content (msg, request); zyre_peer_send (peer, &msg); request = NULL; } zstr_free (&identity); } else if (streq (command, "SHOUT")) { // Get group to send message to char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->peer_groups, name); if (group) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_SHOUT); zre_msg_set_group (msg, name); zre_msg_set_content (msg, request); zyre_group_send (group, &msg); request = NULL; } zstr_free (&name); } else if (streq (command, "JOIN")) { char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->own_groups, name); if (!group) { // Only send if we're not already in group group = zyre_group_new (name, self->own_groups); zre_msg_t *msg = zre_msg_new (ZRE_MSG_JOIN); zre_msg_set_group (msg, name); // Update status before sending command zre_msg_set_status (msg, ++(self->status)); zhash_foreach (self->peers, zyre_node_send_peer, msg); zre_msg_destroy (&msg); zyre_log_info (self->log, ZRE_LOG_MSG_EVENT_JOIN, NULL, name); } zstr_free (&name); } else if (streq (command, "LEAVE")) { char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->own_groups, name); if (group) { // Only send if we are actually in group zre_msg_t *msg = zre_msg_new (ZRE_MSG_LEAVE); zre_msg_set_group (msg, name); // Update status before sending command zre_msg_set_status (msg, ++(self->status)); zhash_foreach (self->peers, zyre_node_send_peer, msg); zre_msg_destroy (&msg); zhash_delete (self->own_groups, name); zyre_log_info (self->log, ZRE_LOG_MSG_EVENT_LEAVE, NULL, name); } zstr_free (&name); } else if (streq (command, "TERMINATE")) { self->terminated = true; zstr_send (self->pipe, "OK"); } zstr_free (&command); zmsg_destroy (&request); return 0; }
static void zyre_node_recv_api (zyre_node_t *self) { // Get the whole message off the pipe in one go zmsg_t *request = zmsg_recv (self->pipe); if (!request) return; // Interrupted char *command = zmsg_popstr (request); if (streq (command, "UUID")) zstr_send (self->pipe, zuuid_str (self->uuid)); else if (streq (command, "NAME")) zstr_send (self->pipe, self->name); else if (streq (command, "SET NAME")) { free (self->name); self->name = zmsg_popstr (request); assert (self->name); } else if (streq (command, "SET HEADER")) { char *name = zmsg_popstr (request); char *value = zmsg_popstr (request); zhash_update (self->headers, name, value); zstr_free (&name); zstr_free (&value); } else if (streq (command, "SET VERBOSE")) self->verbose = true; else if (streq (command, "SET PORT")) { char *value = zmsg_popstr (request); self->beacon_port = atoi (value); zstr_free (&value); } else if (streq (command, "SET EVASIVE TIMEOUT")) { char *value = zmsg_popstr (request); self->evasive_timeout = atoi (value); zstr_free (&value); } else if (streq (command, "SET EXPIRED TIMEOUT")) { char *value = zmsg_popstr (request); self->expired_timeout = atoi (value); zstr_free (&value); } else if (streq (command, "SET INTERVAL")) { char *value = zmsg_popstr (request); self->interval = atol (value); zstr_free (&value); } else if (streq (command, "SET ENDPOINT")) { zyre_node_gossip_start (self); char *endpoint = zmsg_popstr (request); if (zsock_bind (self->inbox, "%s", endpoint) != -1) { zstr_free (&self->endpoint); self->endpoint = endpoint; zsock_signal (self->pipe, 0); } else { zstr_free (&endpoint); zsock_signal (self->pipe, 1); } } else if (streq (command, "GOSSIP BIND")) { zyre_node_gossip_start (self); zstr_free (&self->gossip_bind); self->gossip_bind = zmsg_popstr (request); zstr_sendx (self->gossip, "BIND", self->gossip_bind, NULL); } else if (streq (command, "GOSSIP CONNECT")) { zyre_node_gossip_start (self); zstr_free (&self->gossip_connect); self->gossip_connect = zmsg_popstr (request); zstr_sendx (self->gossip, "CONNECT", self->gossip_connect, NULL); } else if (streq (command, "START")) zsock_signal (self->pipe, zyre_node_start (self)); else if (streq (command, "STOP")) zsock_signal (self->pipe, zyre_node_stop (self)); else if (streq (command, "WHISPER")) { // Get peer to send message to char *identity = zmsg_popstr (request); zyre_peer_t *peer = (zyre_peer_t *) zhash_lookup (self->peers, identity); // Send frame on out to peer's mailbox, drop message // if peer doesn't exist (may have been destroyed) if (peer) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_WHISPER); zre_msg_set_content (msg, &request); zyre_peer_send (peer, &msg); } zstr_free (&identity); } else if (streq (command, "SHOUT")) { // Get group to send message to char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->peer_groups, name); if (group) { zre_msg_t *msg = zre_msg_new (ZRE_MSG_SHOUT); zre_msg_set_group (msg, name); zre_msg_set_content (msg, &request); zyre_group_send (group, &msg); } zstr_free (&name); } else if (streq (command, "JOIN")) { char *name = zmsg_popstr (request); if (!zlist_exists (self->own_groups, name)) { void *item; // Only send if we're not already in group zlist_append (self->own_groups, name); zre_msg_t *msg = zre_msg_new (ZRE_MSG_JOIN); zre_msg_set_group (msg, name); // Update status before sending command zre_msg_set_status (msg, ++(self->status)); for (item = zhash_first (self->peers); item != NULL; item = zhash_next (self->peers)) zyre_node_send_peer (zhash_cursor (self->peers), item, msg); zre_msg_destroy (&msg); if (self->verbose) zsys_info ("(%s) JOIN group=%s", self->name, name); } zstr_free (&name); } else if (streq (command, "LEAVE")) { char *name = zmsg_popstr (request); if (zlist_exists (self->own_groups, name)) { void *item; // Only send if we are actually in group zre_msg_t *msg = zre_msg_new (ZRE_MSG_LEAVE); zre_msg_set_group (msg, name); // Update status before sending command zre_msg_set_status (msg, ++(self->status)); for (item = zhash_first (self->peers); item != NULL; item = zhash_next (self->peers)) zyre_node_send_peer (zhash_cursor (self->peers), item, msg); zre_msg_destroy (&msg); zlist_remove (self->own_groups, name); if (self->verbose) zsys_info ("(%s) LEAVE group=%s", self->name, name); } zstr_free (&name); } else if (streq (command, "PEERS")) zsock_send (self->pipe, "p", zhash_keys (self->peers)); else if (streq (command, "GROUP PEERS")) { char *name = zmsg_popstr (request); zyre_group_t *group = (zyre_group_t *) zhash_lookup (self->peer_groups, name); if (group) zsock_send (self->pipe, "p", zyre_group_peers (group)); else zsock_send (self->pipe, "p", NULL); zstr_free (&name); } else if (streq (command, "PEER ENDPOINT")) { char *uuid = zmsg_popstr (request); zyre_peer_t *peer = (zyre_peer_t *) zhash_lookup (self->peers, uuid); assert (peer); zsock_send (self->pipe, "s", zyre_peer_endpoint (peer)); zstr_free (&uuid); } else if (streq (command, "PEER NAME")) { char *uuid = zmsg_popstr (request); zyre_peer_t *peer = (zyre_peer_t *) zhash_lookup (self->peers, uuid); assert (peer); zsock_send (self->pipe, "s", zyre_peer_name (peer)); zstr_free (&uuid); } else if (streq (command, "PEER HEADER")) { char *uuid = zmsg_popstr (request); char *key = zmsg_popstr (request); zyre_peer_t *peer = (zyre_peer_t *) zhash_lookup (self->peers, uuid); if (!peer) zstr_send (self->pipe, ""); else zstr_send (self->pipe, zyre_peer_header (peer, key, NULL)); zstr_free (&uuid); zstr_free (&key); } else if (streq (command, "PEER GROUPS")) zsock_send (self->pipe, "p", zhash_keys (self->peer_groups)); else if (streq (command, "OWN GROUPS")) zsock_send (self->pipe, "p", zlist_dup (self->own_groups)); else if (streq (command, "DUMP")) zyre_node_dump (self); else if (streq (command, "$TERM")) self->terminated = true; else { zsys_error ("invalid command '%s'", command); assert (false); } zstr_free (&command); zmsg_destroy (&request); }