tor

The Tor anonymity network
git clone https://git.dasho.dev/tor.git
Log | Files | Refs | README | LICENSE

sendme.c (25430B)


      1 /* Copyright (c) 2019-2021, The Tor Project, Inc. */
      2 /* See LICENSE for licensing information */
      3 
      4 /**
      5 * \file sendme.c
      6 * \brief Code that is related to SENDME cells both in terms of
      7 *        creating/parsing cells and handling the content.
      8 */
      9 
     10 // For access to cpath pvt_crypto field.
     11 #define SENDME_PRIVATE
     12 #define CRYPT_PATH_PRIVATE
     13 
     14 #include "core/or/or.h"
     15 
     16 #include "app/config/config.h"
     17 #include "core/crypto/relay_crypto.h"
     18 #include "core/mainloop/connection.h"
     19 #include "core/or/cell_st.h"
     20 #include "core/or/crypt_path.h"
     21 #include "core/or/circuitlist.h"
     22 #include "core/or/circuituse.h"
     23 #include "core/or/or_circuit_st.h"
     24 #include "core/or/relay.h"
     25 #include "core/or/sendme.h"
     26 #include "core/or/congestion_control_common.h"
     27 #include "core/or/congestion_control_flow.h"
     28 #include "feature/nodelist/networkstatus.h"
     29 #include "lib/ctime/di_ops.h"
     30 #include "trunnel/sendme_cell.h"
     31 
     32 /**
     33 * Return true iff tag_len is some length we recognize.
     34 */
     35 static inline bool
     36 tag_len_ok(size_t tag_len)
     37 {
     38  return tag_len == SENDME_TAG_LEN_CGO || tag_len == SENDME_TAG_LEN_TOR1;
     39 }
     40 
     41 /* Return the minimum version given by the consensus (if any) that should be
     42 * used when emitting a SENDME cell. */
     43 STATIC int
     44 get_emit_min_version(void)
     45 {
     46  return networkstatus_get_param(NULL, "sendme_emit_min_version",
     47                                 SENDME_EMIT_MIN_VERSION_DEFAULT,
     48                                 SENDME_EMIT_MIN_VERSION_MIN,
     49                                 SENDME_EMIT_MIN_VERSION_MAX);
     50 }
     51 
     52 /* Return the minimum version given by the consensus (if any) that should be
     53 * accepted when receiving a SENDME cell. */
     54 STATIC int
     55 get_accept_min_version(void)
     56 {
     57  return networkstatus_get_param(NULL, "sendme_accept_min_version",
     58                                 SENDME_ACCEPT_MIN_VERSION_DEFAULT,
     59                                 SENDME_ACCEPT_MIN_VERSION_MIN,
     60                                 SENDME_ACCEPT_MIN_VERSION_MAX);
     61 }
     62 
     63 /* Pop the first cell digset on the given circuit from the SENDME last digests
     64 * list. NULL is returned if the list is uninitialized or empty.
     65 *
     66 * The caller gets ownership of the returned digest thus is responsible for
     67 * freeing the memory. */
     68 static uint8_t *
     69 pop_first_cell_digest(const circuit_t *circ)
     70 {
     71  uint8_t *circ_digest;
     72 
     73  tor_assert(circ);
     74 
     75  if (circ->sendme_last_digests == NULL ||
     76      smartlist_len(circ->sendme_last_digests) == 0) {
     77    return NULL;
     78  }
     79 
     80  circ_digest = smartlist_get(circ->sendme_last_digests, 0);
     81  smartlist_del_keeporder(circ->sendme_last_digests, 0);
     82  return circ_digest;
     83 }
     84 
     85 /* Return true iff the given cell tag matches the first digest in the
     86 * circuit sendme list. */
     87 static bool
     88 v1_tag_matches(const uint8_t *circ_digest,
     89               const uint8_t *cell_tag, size_t tag_len)
     90 {
     91  tor_assert(circ_digest);
     92  tor_assert(cell_tag);
     93 
     94  /* Compare the digest with the one in the SENDME. This cell is invalid
     95   * without a perfect match. */
     96  if (tor_memneq(circ_digest, cell_tag, tag_len)) {
     97    log_fn(LOG_PROTOCOL_WARN, LD_PROTOCOL,
     98           "SENDME v1 cell digest do not match.");
     99    return false;
    100  }
    101 
    102  /* Digests matches! */
    103  return true;
    104 }
    105 
    106 /* Return true iff the given decoded SENDME version 1 cell is valid and
    107 * matches the expected digest on the circuit.
    108 *
    109 * Validation is done by comparing the digest in the cell from the previous
    110 * cell we saw which tells us that the other side has in fact seen that cell.
    111 * See proposal 289 for more details. */
    112 static bool
    113 cell_v1_is_valid(const sendme_cell_t *cell, const uint8_t *circ_digest,
    114                 size_t circ_digest_len)
    115 {
    116  tor_assert(cell);
    117  tor_assert(circ_digest);
    118 
    119  size_t tag_len = sendme_cell_get_data_len(cell);
    120  if (! tag_len_ok(tag_len))
    121    return false;
    122  if (sendme_cell_getlen_data_v1_digest(cell) < tag_len)
    123    return false;
    124  if (tag_len != circ_digest_len)
    125    return false;
    126 
    127  const uint8_t *cell_digest = sendme_cell_getconstarray_data_v1_digest(cell);
    128  return v1_tag_matches(circ_digest, cell_digest, tag_len);
    129 }
    130 
    131 /* Return true iff the given cell version can be handled or if the minimum
    132 * accepted version from the consensus is known to us. */
    133 STATIC bool
    134 cell_version_can_be_handled(uint8_t cell_version)
    135 {
    136  int accept_version = get_accept_min_version();
    137 
    138  /* We will first check if the consensus minimum accepted version can be
    139   * handled by us and if not, regardless of the cell version we got, we can't
    140   * continue. */
    141  if (accept_version > SENDME_MAX_SUPPORTED_VERSION) {
    142    log_fn(LOG_PROTOCOL_WARN, LD_PROTOCOL,
    143           "Unable to accept SENDME version %u (from consensus). "
    144           "We only support <= %u. Probably your tor is too old?",
    145           accept_version, SENDME_MAX_SUPPORTED_VERSION);
    146    goto invalid;
    147  }
    148 
    149  /* Then, is this version below the accepted version from the consensus? If
    150   * yes, we must not handle it. */
    151  if (cell_version < accept_version) {
    152    log_info(LD_PROTOCOL, "Unacceptable SENDME version %u. Only "
    153                          "accepting %u (from consensus). Closing circuit.",
    154             cell_version, accept_version);
    155    goto invalid;
    156  }
    157 
    158  /* Is this cell version supported by us? */
    159  if (cell_version > SENDME_MAX_SUPPORTED_VERSION) {
    160    log_info(LD_PROTOCOL, "SENDME cell version %u is not supported by us. "
    161                          "We only support <= %u",
    162             cell_version, SENDME_MAX_SUPPORTED_VERSION);
    163    goto invalid;
    164  }
    165 
    166  return true;
    167 invalid:
    168  return false;
    169 }
    170 
    171 /* Return true iff the encoded SENDME cell in cell_payload of length
    172 * cell_payload_len is valid. For each version:
    173 *
    174 *  0: No validation
    175 *  1: Authenticated with last cell digest.
    176 *
    177 * This is the main critical function to make sure we can continue to
    178 * send/recv cells on a circuit. If the SENDME is invalid, the circuit should
    179 * be marked for close by the caller. */
    180 /*
    181 * NOTE: This function uses `layer_hint` to determine
    182 * what the sendme tag length will be, and nothing else.
    183 * Notably, we _don't_ keep a separate queue
    184 * of expected tags for each layer!
    185 */
    186 STATIC bool
    187 sendme_is_valid(circuit_t *circ,
    188                const crypt_path_t *layer_hint,
    189                const uint8_t *cell_payload,
    190                size_t cell_payload_len)
    191 {
    192  uint8_t cell_version;
    193  uint8_t *circ_digest = NULL;
    194  sendme_cell_t *cell = NULL;
    195 
    196  tor_assert(circ);
    197  tor_assert(cell_payload);
    198 
    199  /* An empty payload means version 0 so skip trunnel parsing. We won't be
    200   * able to parse a 0 length buffer into a valid SENDME cell. */
    201  if (cell_payload_len == 0) {
    202    cell_version = 0;
    203  } else {
    204    /* First we'll decode the cell so we can get the version. */
    205    if (sendme_cell_parse(&cell, cell_payload, cell_payload_len) < 0) {
    206      log_fn(LOG_PROTOCOL_WARN, LD_PROTOCOL,
    207             "Unparseable SENDME cell received. Closing circuit.");
    208      goto invalid;
    209    }
    210    cell_version = sendme_cell_get_version(cell);
    211  }
    212 
    213  /* Validate that we can handle this cell version. */
    214  if (CIRCUIT_IS_ORCIRC(circ) &&
    215      TO_OR_CIRCUIT(circ)->used_legacy_circuit_handshake &&
    216      cell_version == 0) {
    217    /* exception, allow v0 sendmes on circuits made with CREATE_FAST */
    218    log_info(LD_CIRC, "Permitting sendme version 0 on legacy circuit.");
    219    /* Record this choice on the circuit, so we can avoid counting
    220     * directory fetches on this circuit toward our geoip stats. */
    221    TO_OR_CIRCUIT(circ)->used_obsolete_sendme = 1;
    222  } else if (!cell_version_can_be_handled(cell_version)) {
    223    goto invalid;
    224  }
    225 
    226  /* Determine the expected tag length for this sendme. */
    227  size_t circ_expects_tag_len;
    228  if (layer_hint) {
    229    circ_expects_tag_len =
    230      relay_crypto_sendme_tag_len(&layer_hint->pvt_crypto);
    231  } else if (CIRCUIT_IS_ORCIRC(circ)) {
    232    const or_circuit_t *or_circ = CONST_TO_OR_CIRCUIT(circ);
    233    circ_expects_tag_len = relay_crypto_sendme_tag_len(&or_circ->crypto);
    234  } else {
    235    tor_assert_nonfatal_unreached();
    236    goto invalid;
    237  }
    238 
    239  /* Pop the first element that was added (FIFO). We do that regardless of the
    240   * version so we don't accumulate on the circuit if v0 is used by the other
    241   * end point. */
    242  circ_digest = pop_first_cell_digest(circ);
    243  if (circ_digest == NULL) {
    244    /* We shouldn't have received a SENDME if we have no digests. Log at
    245     * protocol warning because it can be tricked by sending many SENDMEs
    246     * without prior data cell. */
    247    log_fn(LOG_PROTOCOL_WARN, LD_PROTOCOL,
    248           "We received a SENDME but we have no cell digests to match. "
    249           "Closing circuit.");
    250    goto invalid;
    251  }  /* Validate depending on the version now. */
    252  switch (cell_version) {
    253  case 0x01:
    254    if (!cell_v1_is_valid(cell, circ_digest, circ_expects_tag_len)) {
    255      goto invalid;
    256    }
    257    break;
    258  case 0x00:
    259    /* Version 0, there is no work to be done on the payload so it is
    260     * necessarily valid if we pass the version validation. */
    261    break;
    262  default:
    263    log_warn(LD_PROTOCOL, "Unknown SENDME cell version %d received.",
    264             cell_version);
    265    tor_assert_nonfatal_unreached();
    266    break;
    267  }
    268 
    269  /* Valid cell. */
    270  sendme_cell_free(cell);
    271  tor_free(circ_digest);
    272  return true;
    273 invalid:
    274  sendme_cell_free(cell);
    275  tor_free(circ_digest);
    276  return false;
    277 }
    278 
    279 /* Build and encode a version 1 SENDME cell into payload, which must be at
    280 * least of RELAY_PAYLOAD_SIZE_MAX bytes, using the digest for the cell data.
    281 *
    282 * Return the size in bytes of the encoded cell in payload. A negative value
    283 * is returned on encoding failure. */
    284 STATIC ssize_t
    285 build_cell_payload_v1(const uint8_t *cell_tag, const size_t tag_len,
    286                      uint8_t *payload)
    287 {
    288  ssize_t len = -1;
    289  sendme_cell_t *cell = NULL;
    290 
    291  tor_assert(cell_tag);
    292  tor_assert(tag_len_ok(tag_len));
    293  tor_assert(payload);
    294 
    295  cell = sendme_cell_new();
    296 
    297  /* Building a payload for version 1. */
    298  sendme_cell_set_version(cell, 0x01);
    299  /* Set the data length field for v1. */
    300  sendme_cell_set_data_len(cell, tag_len);
    301  sendme_cell_setlen_data_v1_digest(cell, tag_len);
    302 
    303  /* Copy the digest into the data payload. */
    304  memcpy(sendme_cell_getarray_data_v1_digest(cell), cell_tag, tag_len);
    305 
    306  /* Finally, encode the cell into the payload. */
    307  len = sendme_cell_encode(payload, RELAY_PAYLOAD_SIZE_MAX, cell);
    308 
    309  sendme_cell_free(cell);
    310  return len;
    311 }
    312 
    313 /* Send a circuit-level SENDME on the given circuit using the layer_hint if
    314 * not NULL. The digest is only used for version 1.
    315 *
    316 * Return 0 on success else a negative value and the circuit will be closed
    317 * because we failed to send the cell on it. */
    318 static int
    319 send_circuit_level_sendme(circuit_t *circ, crypt_path_t *layer_hint,
    320                          const uint8_t *cell_tag, size_t tag_len)
    321 {
    322  uint8_t emit_version;
    323  uint8_t payload[RELAY_PAYLOAD_SIZE_MAX];
    324  ssize_t payload_len;
    325 
    326  tor_assert(circ);
    327  tor_assert(cell_tag);
    328 
    329  emit_version = get_emit_min_version();
    330  switch (emit_version) {
    331  case 0x01:
    332    payload_len = build_cell_payload_v1(cell_tag, tag_len, payload);
    333    if (BUG(payload_len < 0)) {
    334      /* Unable to encode the cell, abort. We can recover from this by closing
    335       * the circuit but in theory it should never happen. */
    336      return -1;
    337    }
    338    log_debug(LD_PROTOCOL, "Emitting SENDME version 1 cell.");
    339    break;
    340  case 0x00:
    341    FALLTHROUGH;
    342  default:
    343    /* Unknown version, fallback to version 0 meaning no payload. */
    344    payload_len = 0;
    345    log_debug(LD_PROTOCOL, "Emitting SENDME version 0 cell. "
    346                           "Consensus emit version is %d", emit_version);
    347    break;
    348  }
    349 
    350  if (relay_send_command_from_edge(0, circ, RELAY_COMMAND_SENDME,
    351                                   (char *) payload, payload_len,
    352                                   layer_hint) < 0) {
    353    log_warn(LD_CIRC,
    354             "SENDME relay_send_command_from_edge failed. Circuit's closed.");
    355    return -1; /* the circuit's closed, don't continue */
    356  }
    357  return 0;
    358 }
    359 
    360 /* Record the sendme tag as expected in a future SENDME, */
    361 static void
    362 record_cell_digest_on_circ(circuit_t *circ,
    363                           const uint8_t *sendme_tag,
    364                           size_t tag_len)
    365 {
    366  tor_assert(circ);
    367  tor_assert(sendme_tag);
    368 
    369  /* Add the digest to the last seen list in the circuit. */
    370  if (circ->sendme_last_digests == NULL) {
    371    circ->sendme_last_digests = smartlist_new();
    372  }
    373  // We always allocate the largest possible tag here to
    374  // make sure we don't have heap overflow bugs.
    375  uint8_t *tag;
    376  if (tag_len == SENDME_TAG_LEN_CGO) {
    377    tag = tor_malloc_zero(SENDME_TAG_LEN_TOR1);
    378    memcpy(tag, sendme_tag, tag_len);
    379    // (The final bytes were initialized to zero.)
    380  } else if (tag_len == SENDME_TAG_LEN_TOR1) {
    381    tag = tor_memdup(sendme_tag, SENDME_TAG_LEN_TOR1);
    382  } else {
    383    tor_assert_unreached();
    384  }
    385 
    386  smartlist_add(circ->sendme_last_digests, tag);
    387 }
    388 
    389 /*
    390 * Public API
    391 */
    392 
    393 /** Called when we've just received a relay data cell, when we've just
    394 * finished flushing all bytes to stream <b>conn</b>, or when we've flushed
    395 * *some* bytes to the stream <b>conn</b>.
    396 *
    397 * If conn->outbuf is not too full, and our deliver window is low, send back a
    398 * suitable number of stream-level sendme cells.
    399 */
    400 void
    401 sendme_connection_edge_consider_sending(edge_connection_t *conn)
    402 {
    403  tor_assert(conn);
    404 
    405  int log_domain = TO_CONN(conn)->type == CONN_TYPE_AP ? LD_APP : LD_EXIT;
    406 
    407  /* If we use flow control, we do not send stream sendmes */
    408  if (edge_uses_flow_control(conn))
    409    goto end;
    410 
    411  /* Don't send it if we still have data to deliver. */
    412  if (connection_outbuf_too_full(TO_CONN(conn))) {
    413    goto end;
    414  }
    415 
    416  if (circuit_get_by_edge_conn(conn) == NULL) {
    417    /* This can legitimately happen if the destroy has already arrived and
    418     * torn down the circuit. */
    419    log_info(log_domain, "No circuit associated with edge connection. "
    420                         "Skipping sending SENDME.");
    421    goto end;
    422  }
    423 
    424  while (conn->deliver_window <=
    425         (STREAMWINDOW_START - STREAMWINDOW_INCREMENT)) {
    426    log_debug(log_domain, "Outbuf %" TOR_PRIuSZ ", queuing stream SENDME.",
    427              buf_datalen(TO_CONN(conn)->outbuf));
    428    conn->deliver_window += STREAMWINDOW_INCREMENT;
    429    if (connection_edge_send_command(conn, RELAY_COMMAND_SENDME,
    430                                     NULL, 0) < 0) {
    431      log_debug(LD_CIRC, "connection_edge_send_command failed while sending "
    432                         "a SENDME. Circuit probably closed, skipping.");
    433      goto end; /* The circuit's closed, don't continue */
    434    }
    435  }
    436 
    437 end:
    438  return;
    439 }
    440 
    441 /** Check if the deliver_window for circuit <b>circ</b> (at hop
    442 * <b>layer_hint</b> if it's defined) is low enough that we should
    443 * send a circuit-level sendme back down the circuit. If so, send
    444 * enough sendmes that the window would be overfull if we sent any
    445 * more.
    446 */
    447 void
    448 sendme_circuit_consider_sending(circuit_t *circ, crypt_path_t *layer_hint)
    449 {
    450  bool sent_one_sendme = false;
    451  const uint8_t *tag;
    452  size_t tag_len = 0;
    453  int sendme_inc = sendme_get_inc_count(circ, layer_hint);
    454 
    455  while ((layer_hint ? layer_hint->deliver_window : circ->deliver_window) <=
    456          CIRCWINDOW_START - sendme_inc) {
    457    log_debug(LD_CIRC,"Queuing circuit sendme.");
    458    if (layer_hint) {
    459      layer_hint->deliver_window += sendme_inc;
    460      tag = cpath_get_sendme_tag(layer_hint, &tag_len);
    461    } else {
    462      circ->deliver_window += sendme_inc;
    463      tag = relay_crypto_get_sendme_tag(&TO_OR_CIRCUIT(circ)->crypto,
    464                                        &tag_len);
    465    }
    466    if (send_circuit_level_sendme(circ, layer_hint, tag, tag_len) < 0) {
    467      return; /* The circuit's closed, don't continue */
    468    }
    469    /* Current implementation is not suppose to send multiple SENDME at once
    470     * because this means we would use the same relay crypto digest for each
    471     * SENDME leading to a mismatch on the other side and the circuit to
    472     * collapse. Scream loudly if it ever happens so we can address it. */
    473    tor_assert_nonfatal(!sent_one_sendme);
    474    sent_one_sendme = true;
    475  }
    476 }
    477 
    478 /* Process a circuit-level SENDME cell that we just received. The layer_hint,
    479 * if not NULL, is the Exit hop of the connection which means that we are a
    480 * client. In that case, circ must be an origin circuit. The cell_body_len is
    481 * the length of the SENDME cell payload (excluding the header). The
    482 * cell_payload is the payload.
    483 *
    484 * This function validates the SENDME's digest, and then dispatches to
    485 * the appropriate congestion control algorithm in use on the circuit.
    486 *
    487 * Return 0 on success (the SENDME is valid and the package window has
    488 * been updated properly).
    489 *
    490 * On error, a negative value is returned, which indicates that the
    491 * circuit must be closed using the value as the reason for it. */
    492 int
    493 sendme_process_circuit_level(crypt_path_t *layer_hint,
    494                             circuit_t *circ, const uint8_t *cell_payload,
    495                             uint16_t cell_payload_len)
    496 {
    497  tor_assert(circ);
    498  tor_assert(cell_payload);
    499  congestion_control_t *cc;
    500 
    501  /* Validate the SENDME cell. Depending on the version, different validation
    502   * can be done. An invalid SENDME requires us to close the circuit. */
    503  if (!sendme_is_valid(circ, layer_hint, cell_payload, cell_payload_len)) {
    504    return -END_CIRC_REASON_TORPROTOCOL;
    505  }
    506 
    507  /* origin circuits need to count valid sendmes as valid protocol data */
    508  if (CIRCUIT_IS_ORIGIN(circ)) {
    509    circuit_read_valid_data(TO_ORIGIN_CIRCUIT(circ), cell_payload_len);
    510  }
    511 
    512  // Get CC
    513  if (layer_hint) {
    514    cc = layer_hint->ccontrol;
    515  } else {
    516    cc = circ->ccontrol;
    517  }
    518 
    519  /* If there is no CC object, assume fixed alg */
    520  if (!cc) {
    521    return sendme_process_circuit_level_impl(layer_hint, circ);
    522  }
    523 
    524  return congestion_control_dispatch_cc_alg(cc, circ);
    525 }
    526 
    527 /**
    528 * Process a SENDME for Tor's original fixed window circuit-level flow control.
    529 * Updates the package_window and ensures that it does not exceed the max.
    530 *
    531 * Returns -END_CIRC_REASON_TORPROTOCOL if the max is exceeded, otherwise
    532 * returns 0.
    533 */
    534 int
    535 sendme_process_circuit_level_impl(crypt_path_t *layer_hint, circuit_t *circ)
    536 {
    537  /* If we are the origin of the circuit, we are the Client so we use the
    538   * layer hint (the Exit hop) for the package window tracking. */
    539  if (CIRCUIT_IS_ORIGIN(circ)) {
    540    /* If we are the origin of the circuit, it is impossible to not have a
    541     * cpath. Just in case, bug on it and close the circuit. */
    542    if (BUG(layer_hint == NULL)) {
    543      return -END_CIRC_REASON_TORPROTOCOL;
    544    }
    545    if ((layer_hint->package_window + CIRCWINDOW_INCREMENT) >
    546        CIRCWINDOW_START_MAX) {
    547      static struct ratelim_t exit_warn_ratelim = RATELIM_INIT(600);
    548      log_fn_ratelim(&exit_warn_ratelim, LOG_WARN, LD_PROTOCOL,
    549                     "Unexpected sendme cell from exit relay. "
    550                     "Closing circ.");
    551      return -END_CIRC_REASON_TORPROTOCOL;
    552    }
    553    layer_hint->package_window += CIRCWINDOW_INCREMENT;
    554    log_debug(LD_APP, "circ-level sendme at origin, packagewindow %d.",
    555              layer_hint->package_window);
    556  } else {
    557    /* We aren't the origin of this circuit so we are the Exit and thus we
    558     * track the package window with the circuit object. */
    559    if ((circ->package_window + CIRCWINDOW_INCREMENT) >
    560        CIRCWINDOW_START_MAX) {
    561      static struct ratelim_t client_warn_ratelim = RATELIM_INIT(600);
    562      log_fn_ratelim(&client_warn_ratelim, LOG_PROTOCOL_WARN, LD_PROTOCOL,
    563                     "Unexpected sendme cell from client. "
    564                     "Closing circ (window %d).", circ->package_window);
    565      return -END_CIRC_REASON_TORPROTOCOL;
    566    }
    567    circ->package_window += CIRCWINDOW_INCREMENT;
    568    log_debug(LD_EXIT, "circ-level sendme at non-origin, packagewindow %d.",
    569              circ->package_window);
    570  }
    571 
    572  return 0;
    573 }
    574 
    575 /* Process a stream-level SENDME cell that we just received. The conn is the
    576 * edge connection (stream) that the circuit circ is associated with. The
    577 * cell_body_len is the length of the payload (excluding the header).
    578 *
    579 * Return 0 on success (the SENDME is valid and the package window has
    580 * been updated properly).
    581 *
    582 * On error, a negative value is returned, which indicates that the
    583 * circuit must be closed using the value as the reason for it. */
    584 int
    585 sendme_process_stream_level(edge_connection_t *conn, circuit_t *circ,
    586                            uint16_t cell_body_len)
    587 {
    588  tor_assert(conn);
    589  tor_assert(circ);
    590 
    591  if (edge_uses_flow_control(conn)) {
    592    log_fn(LOG_PROTOCOL_WARN, LD_EDGE,
    593           "Congestion control got stream sendme");
    594    return -END_CIRC_REASON_TORPROTOCOL;
    595  }
    596 
    597  /* Don't allow the other endpoint to request more than our maximum (i.e.
    598   * initial) stream SENDME window worth of data. Well-behaved stock clients
    599   * will not request more than this max (as per the check in the while loop
    600   * of sendme_connection_edge_consider_sending()). */
    601  if ((conn->package_window + STREAMWINDOW_INCREMENT) >
    602      STREAMWINDOW_START_MAX) {
    603    static struct ratelim_t stream_warn_ratelim = RATELIM_INIT(600);
    604    log_fn_ratelim(&stream_warn_ratelim, LOG_PROTOCOL_WARN, LD_PROTOCOL,
    605                   "Unexpected stream sendme cell. Closing circ (window %d).",
    606                   conn->package_window);
    607    return -END_CIRC_REASON_TORPROTOCOL;
    608  }
    609  /* At this point, the stream sendme is valid */
    610  conn->package_window += STREAMWINDOW_INCREMENT;
    611 
    612  /* We count circuit-level sendme's as valid delivered data because they are
    613   * rate limited. */
    614  if (CIRCUIT_IS_ORIGIN(circ)) {
    615    circuit_read_valid_data(TO_ORIGIN_CIRCUIT(circ), cell_body_len);
    616  }
    617 
    618  log_debug(CIRCUIT_IS_ORIGIN(circ) ? LD_APP : LD_EXIT,
    619            "stream-level sendme, package_window now %d.",
    620            conn->package_window);
    621  return 0;
    622 }
    623 
    624 /* Called when a relay DATA cell is received on the given circuit. If
    625 * layer_hint is NULL, this means we are the Exit end point else we are the
    626 * Client. Update the deliver window and return its new value. */
    627 int
    628 sendme_circuit_data_received(circuit_t *circ, crypt_path_t *layer_hint)
    629 {
    630  int deliver_window, domain;
    631 
    632  if (CIRCUIT_IS_ORIGIN(circ)) {
    633    tor_assert(layer_hint);
    634    --layer_hint->deliver_window;
    635    deliver_window = layer_hint->deliver_window;
    636    domain = LD_APP;
    637  } else {
    638    tor_assert(!layer_hint);
    639    --circ->deliver_window;
    640    deliver_window = circ->deliver_window;
    641    domain = LD_EXIT;
    642  }
    643 
    644  log_debug(domain, "Circuit deliver_window now %d.", deliver_window);
    645  return deliver_window;
    646 }
    647 
    648 /* Called when a relay DATA cell is received for the given edge connection
    649 * conn. Update the deliver window and return its new value. */
    650 int
    651 sendme_stream_data_received(edge_connection_t *conn)
    652 {
    653  tor_assert(conn);
    654 
    655  if (edge_uses_flow_control(conn)) {
    656    return flow_control_decide_xoff(conn);
    657  } else {
    658    return --conn->deliver_window;
    659  }
    660 }
    661 
    662 /* Called when a relay DATA cell is packaged on the given circuit. If
    663 * layer_hint is NULL, this means we are the Exit end point else we are the
    664 * Client. Update the package window and return its new value. */
    665 int
    666 sendme_note_circuit_data_packaged(circuit_t *circ, crypt_path_t *layer_hint)
    667 {
    668  int package_window, domain;
    669  congestion_control_t *cc;
    670 
    671  tor_assert(circ);
    672 
    673  if (layer_hint) {
    674    cc = layer_hint->ccontrol;
    675    domain = LD_APP;
    676  } else {
    677    cc = circ->ccontrol;
    678    domain = LD_EXIT;
    679  }
    680 
    681  if (cc) {
    682    congestion_control_note_cell_sent(cc, circ, layer_hint);
    683  } else {
    684    /* Fixed alg uses package_window and must update it */
    685 
    686    if (CIRCUIT_IS_ORIGIN(circ)) {
    687      /* Client side. */
    688      tor_assert(layer_hint);
    689      --layer_hint->package_window;
    690      package_window = layer_hint->package_window;
    691    } else {
    692      /* Exit side. */
    693      tor_assert(!layer_hint);
    694      --circ->package_window;
    695      package_window = circ->package_window;
    696    }
    697    log_debug(domain, "Circuit package_window now %d.", package_window);
    698  }
    699 
    700  /* Return appropriate number designating how many cells can still be sent */
    701  return congestion_control_get_package_window(circ, layer_hint);
    702 }
    703 
    704 /* Called when a relay DATA cell is packaged for the given edge connection
    705 * conn. Update the package window and return its new value. */
    706 int
    707 sendme_note_stream_data_packaged(edge_connection_t *conn, size_t len)
    708 {
    709  tor_assert(conn);
    710 
    711  if (edge_uses_flow_control(conn)) {
    712    flow_control_note_sent_data(conn, len);
    713    if (conn->xoff_received)
    714      return -1;
    715    else
    716      return 1;
    717  }
    718 
    719  --conn->package_window;
    720  log_debug(LD_APP, "Stream package_window now %d.", conn->package_window);
    721  return conn->package_window;
    722 }
    723 
    724 /* Record the cell digest into the circuit sendme digest list depending on
    725 * which edge we are. The digest is recorded only if we expect the next cell
    726 * that we will receive is a SENDME so we can match the digest. */
    727 void
    728 sendme_record_cell_digest_on_circ(circuit_t *circ, crypt_path_t *cpath)
    729 {
    730  const uint8_t *sendme_tag;
    731  size_t tag_len = 0;
    732 
    733  tor_assert(circ);
    734 
    735  /* Is this the last cell before a SENDME? The idea is that if the
    736   * package_window reaches a multiple of the increment, after this cell, we
    737   * should expect a SENDME. */
    738  if (!circuit_sent_cell_for_sendme(circ, cpath)) {
    739    return;
    740  }
    741 
    742  /* Getting the digest is expensive so we only do it once we are certain to
    743   * record it on the circuit. */
    744  if (cpath) {
    745    sendme_tag = cpath_get_sendme_tag(cpath, &tag_len);
    746  } else {
    747    sendme_tag =
    748      relay_crypto_get_sendme_tag(&TO_OR_CIRCUIT(circ)->crypto, &tag_len);
    749  }
    750 
    751  record_cell_digest_on_circ(circ, sendme_tag, tag_len);
    752 }