#include "core/or/or.h"
#include "core/or/extendinfo.h"
#include "core/or/protover.h"
+#include "core/or/relay_msg.h"
#include "core/crypto/onion_crypto.h"
#include "core/crypto/onion_fast.h"
#include "core/crypto/onion_ntor.h"
params_out->subproto.flow_ctrl = req->proto_version;
params_out->cc_enabled = true;
break;
+ case PRT_RELAY_CELL:
+ if (!relay_msg_is_enabled() ||
+ !protover_is_supported_here(PRT_RELAY_CELL, req->proto_version)) {
+ ret = false;
+ goto end;
+ }
+ params_out->subproto.relay_cell = req->proto_version;
+ break;
default:
/* Reject any unknown values. */
ret = false;
circ_params->cc_enabled =
circ_params->cc_enabled && our_ns_params->cc_enabled;
+ /* If the circuit relay cell protocol version is higher than ours it means we
+ * don't support it so error. */
+ if (circ_params->subproto.relay_cell > our_ns_params->subproto.relay_cell) {
+ return false;
+ }
+
return true;
}
uint8_t **resp_msg_out,
size_t *resp_msg_len_out)
{
- int ret = -1;
-
/* Failed to parse the extension. */
if (!parse_ntor3_server_ext(param_request_msg, param_request_len,
params_out)) {
params_out->sendme_inc_cells = our_ns_params->sendme_inc_cells;
/* Success. */
- ret = 0;
+ return 0;
err:
- return ret;
+ return -1;
}
/* This is the maximum value for keys_out_len passed to
/** Negotiated subprotocol versions set after a ntorv3 handshake. */
typedef struct circuit_subproto_t {
uint8_t flow_ctrl;
+ uint8_t relay_cell;
} circuit_subproto_t;
/**
#include "core/or/connection_or.h"
#include "core/or/congestion_control_common.h"
#include "core/or/congestion_control_flow.h"
+#include "core/or/protover.h"
#include "app/config/config.h"
#include "core/mainloop/cpuworker.h"
#include "lib/crypt_ops/crypto_rand.h"
* circuit negotiation into the CPU worker context */
req.circ_ns_params.cc_enabled = congestion_control_enabled();
req.circ_ns_params.sendme_inc_cells = congestion_control_sendme_inc();
+ req.circ_ns_params.subproto.relay_cell = PROTOVER_RELAY_CELL_PROTO;
job = tor_malloc_zero(sizeof(cpuworker_job_t));
job->circ = circ;
/** True iff this hop supports the ntorv3 subprotocol request which is
* defined by Relay=5 */
bool supports_ntorv3_subproto_req;
+ /** True iff this hop supports the RelayCell=1 protocol. */
+ bool supports_relay_cell_proto;
};
#endif /* !defined(EXTEND_INFO_ST_H) */
if (pv && for_exit_use) {
info->exit_supports_congestion_control =
pv->supports_congestion_control;
+ info->supports_relay_cell_proto =
+ pv->supports_relay_cell_proto;
}
if (pv) {
PROTOVER_FLOWCTRL_CC);
trn_ntorv3_ext_subproto_add_reqs(req, proto_req);
}
+ /* Build the RelayCell version request. */
+ if (ei->supports_relay_cell_proto) {
+ trn_ntorv3_ext_subproto_req_t *proto_req =
+ trn_ntorv3_ext_subproto_req_new();
+ trn_ntorv3_ext_subproto_req_set_proto_id(proto_req, PRT_RELAY_CELL);
+ trn_ntorv3_ext_subproto_req_set_proto_version(proto_req,
+ PROTOVER_RELAY_CELL_PROTO);
+ trn_ntorv3_ext_subproto_add_reqs(req, proto_req);
+ }
/* Encoding into an extension field. */
ret = trn_ntorv3_ext_subproto_encoded_len(req);