static int handle_seq_fetch (seqhash_t *s, JSON in, JSON *outp) { const char *name; bool create = false; bool created = false; int64_t v, pre, post, *valp; if (!Jget_str (in, "name", &name) || !Jget_bool (in, "create", &create) || !Jget_int64 (in, "preincrement", &pre) || !Jget_int64 (in, "postincrement", &post)) { errno = EPROTO; return (-1); } if (seq_fetch_and_add (s, name, pre, post, &v) < 0) { if (!create || (errno != ENOENT)) return (-1); /* Create and initialize */ valp = seq_create (s, name); *valp += pre; v = *valp; *valp += post; created = true; } *outp = Jnew (); Jadd_str (*outp, "name", name); Jadd_int64 (*outp, "value", v); if (create && created) Jadd_bool (*outp, "created", true); return (0); }
static inline void get_states (json_object *jcb, int64_t *os, int64_t *ns) { json_object *o = NULL; Jget_obj (jcb, JSC_STATE_PAIR, &o); Jget_int64 (o, JSC_STATE_PAIR_OSTATE, os); Jget_int64 (o, JSC_STATE_PAIR_NSTATE, ns); }
static inline void get_states (JSON jcb, int64_t *os, int64_t *ns) { JSON o = NULL; Jget_obj (jcb, JSC_STATE_PAIR, &o); Jget_int64 (o, JSC_STATE_PAIR_OSTATE, os); Jget_int64 (o, JSC_STATE_PAIR_NSTATE, ns); }
static int update_rdesc (flux_t h, int64_t j, JSON o) { int rc = -1; int64_t nnodes = 0; int64_t ntasks = 0; char key1[20] = {'\0'}; char key2[20] = {'\0'}; if (!Jget_int64 (o, JSC_RDESC_NNODES, &nnodes)) return -1; if (!Jget_int64 (o, JSC_RDESC_NTASKS, &ntasks)) return -1; if ((nnodes < 0) || (ntasks < 0)) return -1; snprintf (key1, 20, "lwj.%ld.nnodes", j); snprintf (key2, 20, "lwj.%ld.ntasks", j); if (kvs_put_int64 (h, key1, nnodes) < 0) flux_log (h, LOG_ERR, "update %s: %s", key1, strerror (errno)); else if (kvs_put_int64 (h, key2, ntasks) < 0) flux_log (h, LOG_ERR, "update %s: %s", key2, strerror (errno)); else if (kvs_commit (h) < 0) flux_log (h, LOG_ERR, "commit failed"); else { flux_log (h, LOG_DEBUG, "job (%ld) assigned new resources.", j); rc = 0; } return rc; }
static bool fetch_rank_pdesc (JSON src, int64_t *p, int64_t *n, const char **c) { if (!src) return false; if (!Jget_str (src, "command", c)) return false; if (!Jget_int64 (src, "pid", p)) return false; if (!Jget_int64 (src, "nodeid", n)) return false; return true; }
/* Handle responses */ void ping_continuation (flux_rpc_t *rpc, void *arg) { struct ping_ctx *ctx = arg; const char *json_str, *route, *pad; int64_t sec, nsec; struct timespec t0; int seq; json_object *out = NULL; struct ping_data *pdata = flux_rpc_aux_get (rpc); tstat_t *tstat = pdata->tstat; if (flux_rpc_get (rpc, &json_str) < 0) { log_err ("flux_rpc_get"); goto done; } if (!(out = Jfromstr (json_str)) || !Jget_int (out, "seq", &seq) || !Jget_int64 (out, "time.tv_sec", &sec) || !Jget_int64 (out, "time.tv_nsec", &nsec) || !Jget_str (out, "pad", &pad) || !Jget_str (out, "route", &route) || strcmp (ctx->pad, pad) != 0) { log_err ("error decoding ping response"); goto done; } t0.tv_sec = sec; t0.tv_nsec = nsec; tstat_push (tstat, monotime_since (t0)); pdata->seq = seq; if (pdata->route) free (pdata->route); pdata->route = xstrdup (route); pdata->rpc_count++; done: if (flux_rpc_next (rpc) < 0 && pdata->rpc_count) { if (ctx->rank != NULL) { printf ("%s!%s pad=%lu seq=%d time=(%0.3f:%0.3f:%0.3f) ms stddev %0.3f\n", ctx->rank, ctx->topic, strlen (ctx->pad), pdata->seq, tstat_min (tstat), tstat_mean (tstat), tstat_max (tstat), tstat_stddev (tstat)); } else { char s[16]; snprintf (s, sizeof (s), "%u", ctx->nodeid); printf ("%s%s%s pad=%lu seq=%d time=%0.3f ms (%s)\n", ctx->nodeid == FLUX_NODEID_ANY ? "" : s, ctx->nodeid == FLUX_NODEID_ANY ? "" : "!", ctx->topic, strlen (ctx->pad), pdata->seq, tstat_mean (tstat), pdata->route); } flux_rpc_destroy (rpc); } Jput (out); }
static int update_rdesc (flux_t *h, int64_t j, json_object *o) { int rc = -1; int64_t nnodes = 0; int64_t ntasks = 0; int64_t walltime = 0; char *key1 = NULL; char *key2 = NULL; char *key3 = NULL; flux_kvs_txn_t *txn = NULL; flux_future_t *f = NULL; if (!Jget_int64 (o, JSC_RDESC_NNODES, &nnodes)) goto done; if (!Jget_int64 (o, JSC_RDESC_NTASKS, &ntasks)) goto done; if (!Jget_int64 (o, JSC_RDESC_WALLTIME, &walltime)) goto done; if ((nnodes < 0) || (ntasks < 0) || (walltime < 0)) goto done; key1 = lwj_key (h, j, ".nnodes"); key2 = lwj_key (h, j, ".ntasks"); key3 = lwj_key (h, j, ".walltime"); if (!key1 || !key2 || !key3) goto done; if (!(txn = flux_kvs_txn_create ())) { flux_log_error (h, "txn_create"); goto done; } if (flux_kvs_txn_pack (txn, 0, key1, "I", nnodes) < 0) { flux_log_error (h, "update %s", key1); goto done; } if (flux_kvs_txn_pack (txn, 0, key2, "I", ntasks) < 0) { flux_log_error (h, "update %s", key2); goto done; } if (flux_kvs_txn_pack (txn, 0, key3, "I", walltime) < 0) { flux_log_error (h, "update %s", key3); goto done; } if (!(f = flux_kvs_commit (h, 0, txn)) || flux_future_get (f, NULL) < 0) { flux_log_error (h, "commit failed"); goto done; } flux_log (h, LOG_DEBUG, "job (%"PRId64") assigned new resources.", j); rc = 0; done: flux_future_destroy (f); flux_kvs_txn_destroy (txn); free (key1); free (key2); free (key3); return rc; }
static int update_1pdesc (flux_t *h, flux_kvs_txn_t *txn, int r, int64_t j, json_object *o, json_object *ha, json_object *ea) { flux_future_t *f = NULL; int rc = -1; json_object *d = NULL; char *key; const char *json_str; const char *hn = NULL, *en = NULL; int64_t pid = 0, hindx = 0, eindx = 0, hrank = 0; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_PID, &pid)) return -1; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_HINDX, &hindx)) return -1; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_EINDX, &eindx)) return -1; if (!Jget_ar_str (ha, (int)hindx, &hn)) return -1; if (!Jget_ar_str (ea, (int)eindx, &en)) return -1; key = lwj_key (h, j, ".%d.procdesc", r); if (!key || !(f = flux_kvs_lookup (h, 0, key)) || flux_kvs_lookup_get (f, &json_str) < 0 || !(d = Jfromstr (json_str))) { flux_log_error (h, "extract %s", key); goto done; } Jadd_str (d, "command", en); Jadd_int64 (d, "pid", pid); errno = 0; if ( (hrank = strtoul (hn, NULL, 10)) && errno != 0) { flux_log (h, LOG_ERR, "invalid hostname %s", hn); goto done; } Jadd_int64 (d, "nodeid", (int64_t)hrank); if (flux_kvs_txn_put (txn, 0, key, Jtostr (d)) < 0) { flux_log_error (h, "put %s", key); goto done; } rc = 0; done: flux_future_destroy (f); free (key); if (d) Jput (d); return rc; }
static void job_state_cb (flux_t h, flux_msg_handler_t *w, const flux_msg_t *msg, void *arg) { int64_t jobid = -1; json_object *o = NULL; const char *topic = NULL; const char *json_str = NULL; const char *state = NULL; int len = 12; if (flux_msg_get_topic (msg, &topic) < 0) goto done; if (flux_event_decode (msg, NULL, &json_str) < 0 || !(o = Jfromstr (json_str)) || !Jget_int64 (o, "lwj", &jobid)) { flux_log (h, LOG_ERR, "%s: bad message", __FUNCTION__); goto done; } if (strncmp (topic, "jsc", 3) == 0) len = 10; state = topic + len; if (strcmp (state, jsc_job_num2state (J_RESERVED)) == 0) fixup_newjob_event (h, jobid); if (invoke_cbs (h, jobid, get_update_jcb (h, jobid, state), 0) < 0) flux_log (h, LOG_ERR, "job_state_cb: failed to invoke callbacks"); if (job_is_finished (state)) delete_jobinfo (h, jobid); done: return; }
static int update_state (flux_t h, int64_t j, JSON o) { int rc = -1; int64_t st = 0; char *key; if (!Jget_int64 (o, JSC_STATE_PAIR_NSTATE, &st)) return -1; if ((st >= J_FOR_RENT) || (st < J_NULL)) return -1; key = xasprintf ("lwj.%"PRId64".state", j); if (kvs_put_string (h, key, jsc_job_num2state ((job_state_t)st)) < 0) flux_log_error (h, "update %s", key); else if (kvs_commit (h) < 0) flux_log_error (h, "commit %s", key); else { flux_log (h, LOG_DEBUG, "job (%"PRId64") assigned new state: %s", j, jsc_job_num2state ((job_state_t)st)); rc = 0; } free (key); if (send_state_event (h, st, j) < 0) flux_log_error (h, "send state event"); return rc; }
static int update_pdesc (flux_t h, int64_t j, JSON o) { int i = 0; int rc = -1; int64_t size = 0; JSON h_arr = NULL, e_arr = NULL, pd_arr = NULL, pde = NULL; if (!Jget_int64 (o, JSC_PDESC_SIZE, &size)) return -1; if (!Jget_obj (o, JSC_PDESC_PDARRAY, &pd_arr)) return -1; if (!Jget_obj (o, JSC_PDESC_HOSTNAMES, &h_arr)) return -1; if (!Jget_obj (o, JSC_PDESC_EXECS, &e_arr)) return -1; for (i=0; i < (int) size; ++i) { if (!Jget_ar_obj (pd_arr, i, &pde)) goto done; if ( (rc = update_1pdesc (h, i, j, pde, h_arr, e_arr)) < 0) goto done; } if (kvs_commit (h) < 0) { flux_log (h, LOG_ERR, "update_pdesc commit failed"); goto done; } rc = 0; done: return rc; }
static int64_t next_jobid (flux_t h) { int64_t ret = (int64_t) -1; const char *json_str; json_object *req, *resp; flux_rpc_t *rpc; req = Jnew (); Jadd_str (req, "name", "lwj"); Jadd_int64 (req, "preincrement", 1); Jadd_int64 (req, "postincrement", 0); Jadd_bool (req, "create", true); rpc = flux_rpc (h, "cmb.seq.fetch", json_object_to_json_string (req), 0, 0); json_object_put (req); if ((flux_rpc_get (rpc, NULL, &json_str) < 0) || !(resp = json_tokener_parse (json_str))) { flux_log_error (h, "rpc_get"); goto out; } Jget_int64 (resp, "value", &ret); json_object_put (resp); out: flux_rpc_destroy (rpc); return ret; }
static resrc_graph_req_t *resrc_graph_req_from_json (JSON ga) { JSON go = NULL; /* graph json object */ const char *name = NULL; int i, ngraphs = 0; int64_t ssize; resrc_graph_req_t *resrc_graph_req = NULL; if (Jget_ar_len (ga, &ngraphs)) { resrc_graph_req = xzmalloc ((ngraphs + 1) * sizeof (resrc_graph_req_t)); for (i=0; i < ngraphs; i++) { Jget_ar_obj (ga, i, &go); if (Jget_str (go, "name", &name)) resrc_graph_req[i].name = xstrdup (name); else goto fail; if (Jget_int64 (go, "size", &ssize)) resrc_graph_req[i].size = (size_t) ssize; else goto fail; } /* end of the line */ resrc_graph_req[i].name = NULL; } return resrc_graph_req; fail: free (resrc_graph_req); return NULL; }
static int update_1pdesc (flux_t h, int r, int64_t j, JSON o, JSON ha, JSON ea) { int rc = -1; JSON d = NULL; char *key; char *json_str = NULL; const char *hn = NULL, *en = NULL; int64_t pid = 0, hindx = 0, eindx = 0, hrank = 0; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_PID, &pid)) return -1; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_HINDX, &hindx)) return -1; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_EINDX, &eindx)) return -1; if (!Jget_ar_str (ha, (int)hindx, &hn)) return -1; if (!Jget_ar_str (ea, (int)eindx, &en)) return -1; key = xasprintf ("lwj.%"PRId64".%"PRId32".procdesc", j, r); if (kvs_get (h, key, &json_str) < 0 || !(d = Jfromstr (json_str))) { flux_log_error (h, "extract %s", key); goto done; } Jadd_str (d, "command", en); Jadd_int64 (d, "pid", pid); errno = 0; if ( (hrank = strtoul (hn, NULL, 10)) && errno != 0) { flux_log (h, LOG_ERR, "invalid hostname %s", hn); goto done; } Jadd_int64 (d, "nodeid", (int64_t)hrank); if (kvs_put (h, key, Jtostr (d)) < 0) { flux_log_error (h, "put %s", key); goto done; } rc = 0; done: free (key); if (d) Jput (d); if (json_str) free (json_str); return rc; }
static int handle_seq_set (seqhash_t *s, JSON in, JSON *outp) { const char *name; int64_t old, v; if (!Jget_str (in, "name", &name) || !Jget_int64 (in, "value", &v)) { errno = EPROTO; return (-1); } if ((Jget_int64 (in, "oldvalue", &old) && (seq_cmp_and_set (s, name, old, v) < 0)) || (seq_set (s, name, v) < 0)) return (-1); *outp = Jnew (); Jadd_str (*outp, "name", name); Jadd_bool (*outp, "set", true); Jadd_int64 (*outp, "value", v); return (0); }
static int update_1pdesc (flux_t h, int r, int64_t j, JSON o, JSON ha, JSON ea) { int rc = -1; JSON d = NULL; char key[20] = {'\0'};; const char *hn = NULL, *en = NULL; int64_t pid = 0, hindx = 0, eindx = 0, hrank = 0; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_PID, &pid)) return -1; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_HINDX, &hindx)) return -1; if (!Jget_int64 (o, JSC_PDESC_RANK_PDARRAY_EINDX, &eindx)) return -1; if (!Jget_ar_str (ha, (int)hindx, &hn)) return -1; if (!Jget_ar_str (ea, (int)eindx, &en)) return -1; snprintf (key, 20, "lwj.%ld.%d.procdesc", j, r); if (kvs_get_obj (h, key, &d) < 0) { flux_log (h, LOG_ERR, "extract %s: %s", key, strerror (errno)); goto done; } Jadd_str (d, "command", en); Jadd_int64 (d, "pid", pid); errno = 0; if ( (hrank = strtoul (hn, NULL, 10)) && errno != 0) { flux_log (h, LOG_ERR, "invalid hostname %s", hn); goto done; } Jadd_int64 (d, "nodeid", (int64_t)hrank); if (kvs_put_obj (h, key, d) < 0) { flux_log (h, LOG_ERR, "put %s: %s", key, strerror (errno)); goto done; } rc = 0; done: if (d) Jput (d); return rc; }
static int update_rdesc (flux_t h, int64_t j, JSON o) { int rc = -1; int64_t nnodes = 0; int64_t ntasks = 0; int64_t walltime = 0; char *key1; char *key2; char *key3; if (!Jget_int64 (o, JSC_RDESC_NNODES, &nnodes)) return -1; if (!Jget_int64 (o, JSC_RDESC_NTASKS, &ntasks)) return -1; if (!Jget_int64 (o, JSC_RDESC_WALLTIME, &walltime)) return -1; if ((nnodes < 0) || (ntasks < 0) || (walltime < 0)) return -1; key1 = xasprintf ("lwj.%"PRId64".nnodes", j); key2 = xasprintf ("lwj.%"PRId64".ntasks", j); key3 = xasprintf ("lwj.%"PRId64".walltime", j); if (kvs_put_int64 (h, key1, nnodes) < 0) flux_log_error (h, "update %s", key1); else if (kvs_put_int64 (h, key2, ntasks) < 0) flux_log_error (h, "update %s", key2); else if (kvs_put_int64 (h, key3, walltime) < 0) flux_log_error (h, "update %s", key3); else if (kvs_commit (h) < 0) flux_log_error (h, "commit failed"); else { flux_log (h, LOG_DEBUG, "job (%"PRId64") assigned new resources.", j); rc = 0; } free (key1); free (key2); return rc; }
static int update_hash_1ra (flux_t *h, int64_t j, json_object *o, zhash_t *rtab) { int rc = 0; int64_t ncores = 0; int64_t rank = 0; int64_t *curcnt; char *key; json_object *c = NULL; if (!Jget_obj (o, JSC_RDL_ALLOC_CONTAINED, &c)) return -1; if (!Jget_int64 (c, JSC_RDL_ALLOC_CONTAINING_RANK, &rank)) return -1; if (!Jget_int64 (c, JSC_RDL_ALLOC_CONTAINED_NCORES, &ncores)) return -1; key = lwj_key (h, j, ".rank.%ju.cores", rank); if (!(curcnt = zhash_lookup (rtab, key))) { curcnt = xzmalloc (sizeof (*curcnt)); *curcnt = ncores; zhash_insert (rtab, key, curcnt); zhash_freefn (rtab, key, free); } else *curcnt = *curcnt + ncores; free (key); return rc; }
static int update_1ra (flux_t h, int r, int64_t j, JSON o) { int rc = 0; int64_t ncores = 0; char key[20] = {'\0'}; JSON c = NULL; if (!Jget_obj (o, JSC_RDL_ALLOC_CONTAINED, &c)) return -1; if (!Jget_int64 (c, JSC_RDL_ALLOC_CONTAINED_NCORES, &ncores)) return -1; snprintf (key, 20, "lwj.%ld.rank.%d.cores", j, r); if ( (rc = kvs_put_int64 (h, key, ncores)) < 0) { flux_log (h, LOG_ERR, "put %s: %s", key, strerror (errno)); } return rc; }
static int update_pdesc (flux_t *h, int64_t j, json_object *o) { int i = 0; int rc = -1; int64_t size = 0; json_object *h_arr = NULL; json_object *e_arr = NULL; json_object *pd_arr = NULL; json_object *pde = NULL; flux_kvs_txn_t *txn = NULL; flux_future_t *f = NULL; if (!Jget_int64 (o, JSC_PDESC_SIZE, &size)) goto done; if (!Jget_obj (o, JSC_PDESC_PDARRAY, &pd_arr)) goto done; if (!Jget_obj (o, JSC_PDESC_HOSTNAMES, &h_arr)) goto done; if (!Jget_obj (o, JSC_PDESC_EXECS, &e_arr)) goto done; if (!(txn = flux_kvs_txn_create ())) { flux_log_error (h, "txn_create"); goto done; } for (i=0; i < (int) size; ++i) { if (!Jget_ar_obj (pd_arr, i, &pde)) goto done; if ( (rc = update_1pdesc (h, txn, i, j, pde, h_arr, e_arr)) < 0) goto done; } if (!(f = flux_kvs_commit (h, 0, txn)) || flux_future_get (f, NULL) < 0) { flux_log (h, LOG_ERR, "update_pdesc commit failed"); goto done; } rc = 0; done: flux_kvs_txn_destroy (txn); flux_future_destroy (f); return rc; }
static int update_state (flux_t *h, int64_t j, json_object *o) { int rc = -1; int64_t st = 0; char *key = NULL; flux_kvs_txn_t *txn = NULL; flux_future_t *f = NULL; if (!Jget_int64 (o, JSC_STATE_PAIR_NSTATE, &st)) goto done; if ((st >= J_FOR_RENT) || (st < J_NULL)) goto done; if (!(key = lwj_key (h, j, ".state"))) goto done; if (!(txn = flux_kvs_txn_create ())) { flux_log_error (h, "txn_create"); goto done; } if (flux_kvs_txn_pack (txn, 0, key, "s", jsc_job_num2state ((job_state_t)st)) < 0) { flux_log_error (h, "update %s", key); goto done; } if (!(f = flux_kvs_commit (h, 0, txn)) || flux_future_get (f, NULL) < 0) { flux_log_error (h, "commit %s", key); goto done; } flux_log (h, LOG_DEBUG, "job (%"PRId64") assigned new state: %s", j, jsc_job_num2state ((job_state_t)st)); rc = 0; if (send_state_event (h, st, j) < 0) flux_log_error (h, "send state event"); done: flux_future_destroy (f); flux_kvs_txn_destroy (txn); free (key); return rc; }
static int update_state (flux_t h, int64_t j, JSON o) { int rc = -1; int64_t st = 0; char key[20] = {'\0'}; if (!Jget_int64 (o, JSC_STATE_PAIR_NSTATE, &st)) return -1; if ((st >= J_FOR_RENT) || (st < J_NULL)) return -1; snprintf (key, 20, "lwj.%ld.state", j); if (kvs_put_string (h, key, jsc_job_num2state ((job_state_t)st)) < 0) flux_log (h, LOG_ERR, "update %s: %s", key, strerror (errno)); else if (kvs_commit (h) < 0) flux_log (h, LOG_ERR, "commit %s: %s", key, strerror (errno)); else { flux_log (h, LOG_DEBUG, "job (%ld) assigned new state: %s", j, jsc_job_num2state ((job_state_t)st)); rc = 0; } return rc; }
static bool complete_job (wjctx_t *ctx) { JSON jcb = NULL; JSON o = NULL; bool rc = false; char *json_str = NULL; int64_t state = J_NULL; if (jsc_query_jcb (ctx->h, ctx->jobid, JSC_STATE_PAIR, &json_str) == 0) { jcb = Jfromstr (json_str); Jget_obj (jcb, JSC_STATE_PAIR, &o); Jget_int64 (o, JSC_STATE_PAIR_NSTATE, &state); Jput (jcb); free (json_str); flux_log (ctx->h, LOG_INFO, "%"PRId64" already started (%s)", ctx->jobid, jsc_job_num2state (state)); if (state == J_COMPLETE) { flux_log (ctx->h, LOG_INFO, "%"PRId64" already completed", ctx->jobid); rc = true; } } return rc; }
static inline void get_jobid (JSON jcb, int64_t *j) { Jget_int64 (jcb, JSC_JOBID, j); }
resrc_reqst_t *resrc_reqst_from_json (JSON o, resrc_reqst_t *parent) { bool exclusive = false; JSON ca = NULL; /* array of child json objects */ JSON co = NULL; /* child json object */ JSON ga = NULL; /* array of graph json objects */ int64_t endtime; int64_t qty = 0; int64_t size = 0; int64_t starttime; resrc_reqst_t *child_reqst = NULL; resrc_reqst_t *resrc_reqst = NULL; resrc_t *resrc = NULL; if (!Jget_int64 (o, "req_qty", &qty) && (qty < 1)) goto ret; /* * If the size has not been specified, leave it at zero. A size * of zero means that this job request will not consume any part * of the resource. This allows multiple jobs to share the same * resource. */ if (Jget_int64 (o, "req_size", &size) && (size < 0)) goto ret; /* * If exclusivity has not been specified, leave it at false. */ Jget_bool (o, "exclusive", &exclusive); /* * We use the request's start time to determine whether to request * resources that are available now or in the future. A zero * starttime conveys a request for resources that are available * now. */ if (parent) starttime = parent->starttime; else if (!(Jget_int64 (o, "starttime", &starttime))) starttime = 0; if (parent) endtime = parent->endtime; else if (!(Jget_int64 (o, "endtime", &endtime))) endtime = TIME_MAX; resrc = resrc_new_from_json (o, NULL, false); if (resrc) { resrc_reqst = resrc_reqst_new (resrc, qty, size, starttime, endtime, exclusive); if ((ga = Jobj_get (o, "graphs"))) resrc_reqst->g_reqs = resrc_graph_req_from_json (ga); if ((co = Jobj_get (o, "req_child"))) { child_reqst = resrc_reqst_from_json (co, resrc_reqst); if (child_reqst) resrc_reqst_add_child (resrc_reqst, child_reqst); } else if ((ca = Jobj_get (o, "req_children"))) { int i, nchildren = 0; if (Jget_ar_len (ca, &nchildren)) { for (i=0; i < nchildren; i++) { Jget_ar_obj (ca, i, &co); child_reqst = resrc_reqst_from_json (co, resrc_reqst); if (child_reqst) resrc_reqst_add_child (resrc_reqst, child_reqst); } } } } ret: return resrc_reqst; }
resrc_flow_t *resrc_flow_new_from_json (json_t *o, resrc_flow_t *parent) { json_t *jhierarchyo = NULL; /* json hierarchy object */ const char *basename = NULL; const char *name = NULL; const char *hierarchy = NULL; const char *path = NULL; const char *hierarchy_path = NULL; const char *tmp = NULL; const char *type = NULL; int64_t id; int64_t ssize; resrc_flow_t *resrc_flow = NULL; resrc_t *flow_resrc; resrc_t *resrc = NULL; size_t size = 1; uuid_t uuid; if (!Jget_str (o, "type", &type)) goto ret; Jget_str (o, "basename", &basename); Jget_str (o, "name", &name); if (!(Jget_int64 (o, "id", &id))) id = -1; if (Jget_str (o, "uuid", &tmp)) uuid_parse (tmp, uuid); else uuid_clear(uuid); if (Jget_int64 (o, "size", &ssize)) size = (size_t) ssize; if ((jhierarchyo = Jobj_get (o, "hierarchy"))) { /* Get first key and value from hierarchy object */ const char *key = json_object_iter_key (json_object_iter (jhierarchyo)); if (key) { hierarchy = key; Jget_str (jhierarchyo, key, &hierarchy_path); } } if (!Jget_str (o, "path", &path)) { if (hierarchy_path) path = xstrdup (hierarchy_path); } if (!path) { if (parent) path = xasprintf ("%s/%s", resrc_path (parent->flow_resrc), name); else path = xasprintf ("/%s", name); } if (!(flow_resrc = resrc_new_resource (type, path, basename, name, NULL, id, uuid, size))) goto ret; if (!strncmp (type, "node", 5)) { resrc = resrc_lookup (name); } if ((resrc_flow = resrc_flow_new (parent, flow_resrc, resrc))) { /* add time window if we are given a start time */ int64_t starttime; if (Jget_int64 (o, "starttime", &starttime)) { json_t * w = Jnew (); char *json_str; int64_t endtime; int64_t wall_time; Jadd_int64 (w, "starttime", starttime); if (!Jget_int64 (o, "endtime", &endtime)) { if (Jget_int64 (o, "walltime", &wall_time)) endtime = starttime + wall_time; else endtime = TIME_MAX; } Jadd_int64 (w, "endtime", endtime); json_str = xstrdup (Jtostr (w)); resrc_twindow_insert (resrc_flow->flow_resrc, "0", (void *) json_str); Jput (w); } } if (resrc) resrc_graph_insert (resrc, hierarchy, resrc_flow); ret: return resrc_flow; }
static inline void get_jobid (json_object *jcb, int64_t *j) { Jget_int64 (jcb, JSC_JOBID, j); }