lsquic_conn.c revision 9626cfc2
110c492f0SDmitri Tikhonov/* Copyright (c) 2017 - 2018 LiteSpeed Technologies Inc.  See LICENSE. */
250aadb33SDmitri Tikhonov#include <assert.h>
350aadb33SDmitri Tikhonov#include <inttypes.h>
450aadb33SDmitri Tikhonov#include <string.h>
550aadb33SDmitri Tikhonov
650aadb33SDmitri Tikhonov#include "lsquic.h"
750aadb33SDmitri Tikhonov#include "lsquic_int_types.h"
850aadb33SDmitri Tikhonov#include "lsquic_conn.h"
950aadb33SDmitri Tikhonov#include "lsquic_packet_common.h"
1050aadb33SDmitri Tikhonov#include "lsquic_packet_in.h"
1183287402SDmitri Tikhonov#include "lsquic_str.h"
1250aadb33SDmitri Tikhonov#include "lsquic_handshake.h"
1350aadb33SDmitri Tikhonov#include "lsquic_mm.h"
1450aadb33SDmitri Tikhonov#include "lsquic_engine_public.h"
1550aadb33SDmitri Tikhonov#include "lsquic_ev_log.h"
1650aadb33SDmitri Tikhonov
1750aadb33SDmitri Tikhonov#include "lsquic_logger.h"
1850aadb33SDmitri Tikhonov
1950aadb33SDmitri Tikhonovlsquic_cid_t
2050aadb33SDmitri Tikhonovlsquic_conn_id (const lsquic_conn_t *lconn)
2150aadb33SDmitri Tikhonov{
2250aadb33SDmitri Tikhonov    return lconn->cn_cid;
2350aadb33SDmitri Tikhonov}
2450aadb33SDmitri Tikhonov
2550aadb33SDmitri Tikhonov
2650aadb33SDmitri Tikhonovvoid *
2750aadb33SDmitri Tikhonovlsquic_conn_get_peer_ctx( const lsquic_conn_t *lconn)
2850aadb33SDmitri Tikhonov{
2950aadb33SDmitri Tikhonov    return lconn->cn_peer_ctx;
3050aadb33SDmitri Tikhonov}
3150aadb33SDmitri Tikhonov
3250aadb33SDmitri Tikhonov
3350aadb33SDmitri Tikhonovvoid
3450aadb33SDmitri Tikhonovlsquic_conn_record_sockaddr (lsquic_conn_t *lconn,
3550aadb33SDmitri Tikhonov            const struct sockaddr *local, const struct sockaddr *peer)
3650aadb33SDmitri Tikhonov{
3750aadb33SDmitri Tikhonov    assert(local->sa_family == peer->sa_family);
3850aadb33SDmitri Tikhonov    switch (local->sa_family)
3950aadb33SDmitri Tikhonov    {
4050aadb33SDmitri Tikhonov    case AF_INET:
4150aadb33SDmitri Tikhonov        lconn->cn_flags |= LSCONN_HAS_PEER_SA|LSCONN_HAS_LOCAL_SA;
4250aadb33SDmitri Tikhonov        memcpy(lconn->cn_local_addr, local, sizeof(struct sockaddr_in));
4350aadb33SDmitri Tikhonov        memcpy(lconn->cn_peer_addr, peer, sizeof(struct sockaddr_in));
4450aadb33SDmitri Tikhonov        break;
4550aadb33SDmitri Tikhonov    case AF_INET6:
4650aadb33SDmitri Tikhonov        lconn->cn_flags |= LSCONN_HAS_PEER_SA|LSCONN_HAS_LOCAL_SA;
4750aadb33SDmitri Tikhonov        memcpy(lconn->cn_local_addr, local, sizeof(struct sockaddr_in6));
4850aadb33SDmitri Tikhonov        memcpy(lconn->cn_peer_addr, peer, sizeof(struct sockaddr_in6));
4950aadb33SDmitri Tikhonov        break;
5050aadb33SDmitri Tikhonov    }
5150aadb33SDmitri Tikhonov}
5250aadb33SDmitri Tikhonov
5350aadb33SDmitri Tikhonov
5450aadb33SDmitri Tikhonovint
5550aadb33SDmitri Tikhonovlsquic_conn_get_sockaddr (const lsquic_conn_t *lconn,
5650aadb33SDmitri Tikhonov                const struct sockaddr **local, const struct sockaddr **peer)
5750aadb33SDmitri Tikhonov{
5850aadb33SDmitri Tikhonov    if ((lconn->cn_flags & (LSCONN_HAS_PEER_SA|LSCONN_HAS_LOCAL_SA)) ==
5950aadb33SDmitri Tikhonov                                    (LSCONN_HAS_PEER_SA|LSCONN_HAS_LOCAL_SA))
6050aadb33SDmitri Tikhonov    {
6150aadb33SDmitri Tikhonov        *local = (struct sockaddr *) lconn->cn_local_addr;
6250aadb33SDmitri Tikhonov        *peer = (struct sockaddr *) lconn->cn_peer_addr;
6350aadb33SDmitri Tikhonov        return 0;
6450aadb33SDmitri Tikhonov    }
6550aadb33SDmitri Tikhonov    else
6650aadb33SDmitri Tikhonov        return -1;
6750aadb33SDmitri Tikhonov}
6850aadb33SDmitri Tikhonov
6950aadb33SDmitri Tikhonov
7050aadb33SDmitri Tikhonovint
7150aadb33SDmitri Tikhonovlsquic_conn_copy_and_release_pi_data (const lsquic_conn_t *conn,
7250aadb33SDmitri Tikhonov          struct lsquic_engine_public *enpub, lsquic_packet_in_t *packet_in)
7350aadb33SDmitri Tikhonov{
7450aadb33SDmitri Tikhonov    assert(!(packet_in->pi_flags & PI_OWN_DATA));
7550aadb33SDmitri Tikhonov    /* The size should be guarded in lsquic_engine_packet_in(): */
7650aadb33SDmitri Tikhonov    assert(packet_in->pi_data_sz <= QUIC_MAX_PACKET_SZ);
7750aadb33SDmitri Tikhonov    unsigned char *const copy = lsquic_mm_get_1370(&enpub->enp_mm);
7850aadb33SDmitri Tikhonov    if (!copy)
7950aadb33SDmitri Tikhonov    {
8050aadb33SDmitri Tikhonov        LSQ_WARN("cannot allocate memory to copy incoming packet data");
8150aadb33SDmitri Tikhonov        return -1;
8250aadb33SDmitri Tikhonov    }
8350aadb33SDmitri Tikhonov    memcpy(copy, packet_in->pi_data, packet_in->pi_data_sz);
8450aadb33SDmitri Tikhonov    packet_in->pi_data = copy;
8550aadb33SDmitri Tikhonov    packet_in->pi_flags |= PI_OWN_DATA;
8650aadb33SDmitri Tikhonov    return 0;
8750aadb33SDmitri Tikhonov}
8850aadb33SDmitri Tikhonov
8950aadb33SDmitri Tikhonov
9050aadb33SDmitri Tikhonovint
9150aadb33SDmitri Tikhonovlsquic_conn_decrypt_packet (lsquic_conn_t *lconn,
9250aadb33SDmitri Tikhonov                            struct lsquic_engine_public *enpub,
9350aadb33SDmitri Tikhonov                            lsquic_packet_in_t *packet_in)
9450aadb33SDmitri Tikhonov{
9550aadb33SDmitri Tikhonov    size_t header_len, data_len;
96c51ce338SDmitri Tikhonov    enum enc_level enc_level;
9750aadb33SDmitri Tikhonov    size_t out_len = 0;
9850aadb33SDmitri Tikhonov    unsigned char *copy = lsquic_mm_get_1370(&enpub->enp_mm);
9950aadb33SDmitri Tikhonov    if (!copy)
10050aadb33SDmitri Tikhonov    {
10150aadb33SDmitri Tikhonov        LSQ_WARN("cannot allocate memory to copy incoming packet data");
10250aadb33SDmitri Tikhonov        return -1;
10350aadb33SDmitri Tikhonov    }
10450aadb33SDmitri Tikhonov
10550aadb33SDmitri Tikhonov    header_len = packet_in->pi_header_sz;
10650aadb33SDmitri Tikhonov    data_len   = packet_in->pi_data_sz - packet_in->pi_header_sz;
107c51ce338SDmitri Tikhonov    enc_level = lconn->cn_esf->esf_decrypt(lconn->cn_enc_session,
10883287402SDmitri Tikhonov                        lconn->cn_version, 0,
10950aadb33SDmitri Tikhonov                        packet_in->pi_packno, packet_in->pi_data,
11050aadb33SDmitri Tikhonov                        &header_len, data_len,
11150aadb33SDmitri Tikhonov                        lsquic_packet_in_nonce(packet_in),
112c51ce338SDmitri Tikhonov                        copy, 1370, &out_len);
113c51ce338SDmitri Tikhonov    if ((enum enc_level) -1 == enc_level)
11450aadb33SDmitri Tikhonov    {
11550aadb33SDmitri Tikhonov        lsquic_mm_put_1370(&enpub->enp_mm, copy);
11650aadb33SDmitri Tikhonov        EV_LOG_CONN_EVENT(lconn->cn_cid, "could not decrypt packet %"PRIu64,
11750aadb33SDmitri Tikhonov                                                        packet_in->pi_packno);
11850aadb33SDmitri Tikhonov        return -1;
11950aadb33SDmitri Tikhonov    }
120c51ce338SDmitri Tikhonov
121c51ce338SDmitri Tikhonov    assert(header_len + out_len <= 1370);
122c51ce338SDmitri Tikhonov    if (packet_in->pi_flags & PI_OWN_DATA)
123c51ce338SDmitri Tikhonov        lsquic_mm_put_1370(&enpub->enp_mm, packet_in->pi_data);
124c51ce338SDmitri Tikhonov    packet_in->pi_data = copy;
125c51ce338SDmitri Tikhonov    packet_in->pi_flags |= PI_OWN_DATA | PI_DECRYPTED
126c51ce338SDmitri Tikhonov                        | (enc_level << PIBIT_ENC_LEV_SHIFT);
127c51ce338SDmitri Tikhonov    packet_in->pi_header_sz = header_len;
128c51ce338SDmitri Tikhonov    packet_in->pi_data_sz   = out_len + header_len;
1299626cfc2SDmitri Tikhonov    EV_LOG_CONN_EVENT(lconn->cn_cid, "decrypted packet %"PRIu64" crypto: %s",
1309626cfc2SDmitri Tikhonov                        packet_in->pi_packno, lsquic_enclev2str[ enc_level ]);
131c51ce338SDmitri Tikhonov    return 0;
13250aadb33SDmitri Tikhonov}
13350aadb33SDmitri Tikhonov
13450aadb33SDmitri Tikhonov
135881272bbSDmitri Tikhonovenum lsquic_version
136881272bbSDmitri Tikhonovlsquic_conn_quic_version (const lsquic_conn_t *lconn)
137881272bbSDmitri Tikhonov{
138881272bbSDmitri Tikhonov    if (lconn->cn_flags & LSCONN_VER_SET)
139881272bbSDmitri Tikhonov        return lconn->cn_version;
140881272bbSDmitri Tikhonov    else
141881272bbSDmitri Tikhonov        return -1;
142881272bbSDmitri Tikhonov}
143881272bbSDmitri Tikhonov
144881272bbSDmitri Tikhonov
145