/** * Checks a JSON object contains only allowed keys * * @param obj JSON object * @param allowed_keys A NULL-terminated string array with the allowed keys * @param obsolete_keys A NULL-terminated string array with the obsolete_keys */ static int check_allowed_keys(json_t* obj, const char* allowed_keys[], const char* obsolete_keys[]) { /* obj is a JSON object */ const char *key = NULL; void *iter = json_object_iter(obj); const char **allowed = NULL; int found = FALSE; while(iter) { key = json_object_iter_key(iter); found = FALSE; for (allowed = allowed_keys; allowed && *allowed; allowed++) { if (strcmp(*allowed, key) == 0) { found = TRUE; break; } } for (allowed = obsolete_keys; allowed && *allowed; allowed++) { if (strcmp(*allowed, key) == 0) { tr_warning("Configuration option [%s] is obsolete!", key); found = TRUE; break; } } if (!found) { tr_err("Invalid configuration item found: %s", key); return FALSE; } iter = json_object_iter_next(obj, iter); } return TRUE; }
void trp_peer_set_linkcost(TRP_PEER *peer, unsigned int linkcost) { if ((linkcost>TRP_METRIC_INFINITY) && (linkcost!=TRP_METRIC_INVALID)) { /* This indicates a programming error, but probably means an already infinite metric * was (incorrectly) incremented. Issue a warning and proceed with an infinite metric. */ tr_warning("trp_peer_set_linkcost: link cost > infinity encountered, setting to infinity"); linkcost=TRP_METRIC_INFINITY; } peer->linkcost=linkcost; }
int NanostackInterface::socket_send(void *handle, const void *p, unsigned size) { // Validate parameters NanostackSocket * socket = static_cast<NanostackSocket *>(handle); if (NULL == handle) { MBED_ASSERT(false); return NSAPI_ERROR_NO_SOCKET; } nanostack_lock(); int ret; if (socket->closed()) { ret = NSAPI_ERROR_NO_CONNECTION; } else if (socket->is_connecting()) { ret = NSAPI_ERROR_WOULD_BLOCK; } else { ret = ::socket_sendto(socket->socket_id, &socket->ns_address, (uint8_t*)p, size); /* * \return 0 on success. * \return -1 invalid socket id. * \return -2 Socket memory allocation fail. * \return -3 TCP state not established. * \return -4 Socket tx process busy. * \return -5 TLS authentication not ready. * \return -6 Packet too short. * */ if (-4 == ret) { ret = NSAPI_ERROR_WOULD_BLOCK; } else if (ret != 0) { tr_warning("socket_sendto ret %i, socket_id %i", ret, socket->socket_id); ret = NSAPI_ERROR_DEVICE_ERROR; } else { ret = size; } } nanostack_unlock(); tr_debug("socket_send(socket=%p) sock_id=%d, ret=%i", socket, socket->socket_id, ret); return ret; }
DH *tr_create_matching_dh (unsigned char *priv_key, size_t keylen, DH *in_dh) { DH *dh = NULL; int dh_err = 0; if (!in_dh) return NULL; if (NULL == (dh = DH_new())) { tr_crit("tr_create_matching_dh: unable to allocate new DH structure."); return NULL; } if ((NULL == (dh->g = BN_dup(in_dh->g))) || (NULL == (dh->p = BN_dup(in_dh->p)))) { DH_free(dh); tr_debug("tr_create_matching_dh: Invalid dh parameter values, can't be duped."); return NULL; } /* TBD -- share code with previous function */ if ((priv_key) && (keylen > 0)) dh->priv_key = BN_bin2bn(priv_key, keylen, NULL); DH_generate_key(dh); /* generates the public key */ DH_check(dh, &dh_err); if (0 != dh_err) { tr_warning("Warning: dh_check failed with %d", dh_err); if (dh_err & DH_CHECK_P_NOT_PRIME) tr_warning(": p value is not prime"); else if (dh_err & DH_CHECK_P_NOT_SAFE_PRIME) tr_warning(": p value is not a safe prime"); else if (dh_err & DH_UNABLE_TO_CHECK_GENERATOR) tr_warning(": unable to check the generator value"); else if (dh_err & DH_NOT_SUITABLE_GENERATOR) tr_warning(": the g value is not a generator"); else tr_warning("unhandled error %i", dh_err); } return(dh); }
DH *tr_create_dh_params(unsigned char *priv_key, size_t keylen) { DH *dh = NULL; int dh_err = 0; if (NULL == (dh = DH_new())) return NULL; if ((NULL == (dh->g = BN_new())) || (NULL == (dh->p = BN_new())) || (NULL == (dh->q = BN_new()))) { DH_free(dh); return NULL; } BN_set_word(dh->g, 2); dh->p = BN_bin2bn(tr_2048_dhprime, sizeof(tr_2048_dhprime), NULL); BN_rshift1(dh->q, dh->p); if ((priv_key) && (keylen > 0)) dh->priv_key = BN_bin2bn(priv_key, keylen, NULL); DH_generate_key(dh); /* generates the public key */ DH_check(dh, &dh_err); if (0 != dh_err) { tr_warning("Warning: dh_check failed with %d", dh_err); if (dh_err & DH_CHECK_P_NOT_PRIME) tr_warning(": p value is not prime"); else if (dh_err & DH_CHECK_P_NOT_SAFE_PRIME) tr_warning(": p value is not a safe prime"); else if (dh_err & DH_UNABLE_TO_CHECK_GENERATOR) tr_warning(": unable to check the generator value"); else if (dh_err & DH_NOT_SUITABLE_GENERATOR) tr_warning(": the g value is not a generator"); else tr_warning("unhandled error %i", dh_err); } return(dh); }
/** * Clean up any finished TID request processes * * This is called by the main process after forking each TID request. If you want to be * sure finished processes are cleaned up promptly even during a lull in TID requests, * this can be called from the main thread of the main process. It is not thread-safe, * so should not be used from sub-threads. It should not be called by child processes - * this would probably be harmless but ineffective. * * @param tids */ void tids_sweep_procs(TIDS_INSTANCE *tids) { guint ii; struct tid_process tp = {0}; char result[TIDS_MAX_MESSAGE_LEN] = {0}; ssize_t result_len; int status; int wait_rc; /* loop backwards over the array so we can remove elements as we go */ for (ii=tids->pids->len; ii > 0; ii--) { /* ii-1 is the current index - get our own copy, we may destroy the list's copy */ tp = g_array_index(tids->pids, struct tid_process, ii-1); wait_rc = waitpid(tp.pid, &status, WNOHANG); if (wait_rc == 0) continue; /* process still running */ if (wait_rc < 0) { /* invalid options will probably keep being invalid, report that condition */ if(errno == EINVAL) tr_crit("tids_sweep_procs: waitpid called with invalid options"); /* If we got ECHILD, that means the PID was invalid; we'll assume the process was * terminated and we missed it. For all other errors, move on * to the next PID to check. */ if (errno != ECHILD) continue; tr_warning("tid_sweep_procs: TID process %d disappeared", tp.pid); } /* remove the item (we still have a copy of the data) */ g_array_remove_index_fast(tids->pids, ii-1); /* disturbs only indices >= ii-1 which we've already handled */ /* Report exit status unless we got ECHILD above or somehow waitpid returned the wrong pid */ if (wait_rc == tp.pid) { if (WIFEXITED(status)) { tr_debug("tids_sweep_procs: TID process %d exited with status %d.", tp.pid, WTERMSIG(status)); } else if (WIFSIGNALED(status)) { tr_debug("tids_sweep_procs: TID process %d terminated by signal %d.", tp.pid, WTERMSIG(status)); } } else if (wait_rc > 0) { tr_err("tids_sweep_procs: waitpid returned pid %d, expected %d", wait_rc, tp.pid); } /* read the pipe - if the TID request worked, it will have written status before terminating */ result_len = read(tp.read_fd, result, TIDS_MAX_MESSAGE_LEN); close(tp.read_fd); if ((result_len > 0) && (strcmp(result, TIDS_SUCCESS_MESSAGE) == 0)) { tids->req_count++; tr_info("tids_sweep_procs: TID process %d exited after successful request.", tp.pid); } else if ((result_len > 0) && (strcmp(result, TIDS_ERROR_MESSAGE) == 0)) { tids->req_error_count++; tr_info("tids_sweep_procs: TID process %d exited after unsuccessful request.", tp.pid); } else { tids->error_count++; tr_info("tids_sweep_procs: TID process %d exited with an error.", tp.pid); } } }