Commit 0a29865a authored by Marek Vavrusa's avatar Marek Vavrusa

Ported libknot to new pkt API.

parent e3b85192
...@@ -89,19 +89,29 @@ typedef enum { ...@@ -89,19 +89,29 @@ typedef enum {
* OPCODE and the QTYPE. * OPCODE and the QTYPE.
*/ */
typedef enum { typedef enum {
KNOT_QUERY_INVALID, /*!< Invalid query. */ KNOT_QUERY_INVALID = 1 << 1, /*!< Invalid query. */
KNOT_QUERY_NORMAL, /*!< Normal query. */ KNOT_QUERY_NORMAL = 1 << 2, /*!< Normal query. */
KNOT_QUERY_AXFR, /*!< Request for AXFR transfer. */ KNOT_QUERY_AXFR = 1 << 3, /*!< Request for AXFR transfer. */
KNOT_QUERY_IXFR, /*!< Request for IXFR transfer. */ KNOT_QUERY_IXFR = 1 << 4, /*!< Request for IXFR transfer. */
KNOT_QUERY_NOTIFY, /*!< NOTIFY query. */ KNOT_QUERY_NOTIFY = 1 << 5, /*!< NOTIFY query. */
KNOT_QUERY_UPDATE, /*!< Dynamic update. */ KNOT_QUERY_UPDATE = 1 << 6, /*!< Dynamic update. */
KNOT_RESPONSE_NORMAL, /*!< Normal response. */ KNOT_RESPONSE = 1 << 0, /*!< Is response. */
KNOT_RESPONSE_AXFR, /*!< AXFR transfer response. */ KNOT_RESPONSE_NORMAL = KNOT_RESPONSE|KNOT_QUERY_NORMAL,/*!< Normal response. */
KNOT_RESPONSE_IXFR, /*!< IXFR transfer response. */ KNOT_RESPONSE_AXFR = KNOT_RESPONSE|KNOT_QUERY_AXFR, /*!< AXFR transfer response. */
KNOT_RESPONSE_NOTIFY, /*!< NOTIFY response. */ KNOT_RESPONSE_IXFR = KNOT_RESPONSE|KNOT_QUERY_IXFR, /*!< IXFR transfer response. */
KNOT_RESPONSE_UPDATE /*!< Dynamic update response. */ KNOT_RESPONSE_NOTIFY = KNOT_RESPONSE|KNOT_QUERY_NOTIFY,/*!< NOTIFY response. */
KNOT_RESPONSE_UPDATE = KNOT_RESPONSE|KNOT_QUERY_UPDATE /*!< Dynamic update response. */
} knot_packet_type_t; } knot_packet_type_t;
/*!
* \brief DNS packet section identifiers.
*/
typedef enum {
KNOT_ANSWER = 0,
KNOT_AUTHORITY = 1,
KNOT_ADDITIONAL = 2
} knot_section_t;
/*! /*!
* \brief TSIG algorithm numbers. * \brief TSIG algorithm numbers.
* *
......
...@@ -29,7 +29,7 @@ ...@@ -29,7 +29,7 @@
#include "libknot/util/tolower.h" #include "libknot/util/tolower.h"
#include "libknot/util/debug.h" #include "libknot/util/debug.h"
#include "libknot/util/utils.h" #include "libknot/util/utils.h"
#include "libknot/util/wire.h" #include "libknot/packet/wire.h"
/*----------------------------------------------------------------------------*/ /*----------------------------------------------------------------------------*/
......
...@@ -21,7 +21,7 @@ ...@@ -21,7 +21,7 @@
#include "libknot/dnssec/rrset-sign.h" #include "libknot/dnssec/rrset-sign.h"
#include "libknot/dnssec/sig0.h" #include "libknot/dnssec/sig0.h"
#include "libknot/dnssec/sign.h" #include "libknot/dnssec/sign.h"
#include "libknot/util/wire.h" #include "libknot/packet/wire.h"
/*! /*!
* \brief Lifetime fudge of the SIG(0) packets in seconds. * \brief Lifetime fudge of the SIG(0) packets in seconds.
......
...@@ -274,7 +274,7 @@ short knot_edns_to_wire(const knot_opt_rr_t *opt_rr, uint8_t *wire, ...@@ -274,7 +274,7 @@ short knot_edns_to_wire(const knot_opt_rr_t *opt_rr, uint8_t *wire,
assert(EDNS_MIN_SIZE <= (int)max_size); assert(EDNS_MIN_SIZE <= (int)max_size);
if ((int)max_size < opt_rr->size) { if ((int)max_size < opt_rr->size) {
dbg_edns("Not enough place for OPT RR wire format.\n"); printf("Not enough place for OPT RR wire format.\n");
return KNOT_ESPACE; return KNOT_ESPACE;
} }
......
...@@ -32,6 +32,8 @@ ...@@ -32,6 +32,8 @@
#include "libknot/util/utils.h" #include "libknot/util/utils.h"
#include "libknot/rrset.h" #include "libknot/rrset.h"
struct knot_packet;
/*----------------------------------------------------------------------------*/ /*----------------------------------------------------------------------------*/
/*! \brief Structure representing one OPT RR Option. */ /*! \brief Structure representing one OPT RR Option. */
struct knot_opt_option { struct knot_opt_option {
...@@ -80,6 +82,13 @@ enum knot_edns_const { ...@@ -80,6 +82,13 @@ enum knot_edns_const {
EDNS_MIN_SIZE = 11 /*!< Minimum size of EDNS OPT RR in wire format. */ EDNS_MIN_SIZE = 11 /*!< Minimum size of EDNS OPT RR in wire format. */
}; };
enum {
KNOT_PKT_EDNS_PAYLOAD = 0,
KNOT_PKT_EDNS_VERSION = 1,
KNOT_PKT_EDNS_RCODE = 2,
KNOT_PKT_EDNS_NSID = 3
};
/*----------------------------------------------------------------------------*/ /*----------------------------------------------------------------------------*/
/*! /*!
* \brief Creates new empty OPT RR structure for holding EDNS parameters. * \brief Creates new empty OPT RR structure for holding EDNS parameters.
...@@ -230,6 +239,7 @@ int knot_edns_add_option(knot_opt_rr_t *opt_rr, uint16_t code, ...@@ -230,6 +239,7 @@ int knot_edns_add_option(knot_opt_rr_t *opt_rr, uint16_t code,
*/ */
int knot_edns_has_option(const knot_opt_rr_t *opt_rr, uint16_t code); int knot_edns_has_option(const knot_opt_rr_t *opt_rr, uint16_t code);
/*! /*!
* \brief Converts the given OPT RR into wire format. * \brief Converts the given OPT RR into wire format.
* *
......
...@@ -30,16 +30,16 @@ ...@@ -30,16 +30,16 @@
#include "libknot/consts.h" #include "libknot/consts.h"
#include "libknot/dname.h" #include "libknot/dname.h"
#include "libknot/edns.h" #include "libknot/edns.h"
#include "libknot/packet/packet.h" #include "libknot/packet/wire.h"
#include "libknot/packet/query.h" #include "libknot/packet/compr.h"
#include "libknot/packet/response.h" #include "libknot/packet/pkt.h"
#include "libknot/rrset.h" #include "libknot/rrset.h"
#include "libknot/rrset-dump.h" #include "libknot/rrset-dump.h"
#include "libknot/tsig.h" #include "libknot/tsig.h"
#include "libknot/tsig-op.h" #include "libknot/tsig-op.h"
#include "libknot/util/tolower.h" #include "libknot/util/tolower.h"
#include "libknot/util/utils.h" #include "libknot/util/utils.h"
#include "libknot/util/wire.h"
#include "libknot/zone/node.h" #include "libknot/zone/node.h"
#include "libknot/zone/zone.h" #include "libknot/zone/zone.h"
#include "libknot/zone/zonedb.h" #include "libknot/zone/zonedb.h"
......
...@@ -19,8 +19,7 @@ ...@@ -19,8 +19,7 @@
#include "libknot/nameserver/chaos.h" #include "libknot/nameserver/chaos.h"
#include "common/descriptor.h" #include "common/descriptor.h"
#include "libknot/packet/packet.h" #include "libknot/packet/pkt.h"
#include "libknot/packet/response.h"
/*! /*!
* \brief Get a string result for a given TXT query. * \brief Get a string result for a given TXT query.
...@@ -89,10 +88,10 @@ static knot_rrset_t *create_txt_rrset(const knot_dname_t *owner, ...@@ -89,10 +88,10 @@ static knot_rrset_t *create_txt_rrset(const knot_dname_t *owner,
* \param return KNOT_RCODE_NOERROR if the response was succesfully created, * \param return KNOT_RCODE_NOERROR if the response was succesfully created,
* otherwise an RCODE representing the failure. * otherwise an RCODE representing the failure.
*/ */
static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response, static int answer_txt(knot_nameserver_t *nameserver, knot_pkt_t *response,
uint8_t *response_wire, size_t *response_size) uint8_t *response_wire, size_t *response_size)
{ {
const knot_dname_t *qname = knot_packet_qname(response); const knot_dname_t *qname = knot_pkt_qname(response);
const char *response_str = get_txt_response_string(nameserver, qname); const char *response_str = get_txt_response_string(nameserver, qname);
if (response_str == NULL || response_str[0] == '\0') if (response_str == NULL || response_str[0] == '\0')
return KNOT_RCODE_REFUSED; return KNOT_RCODE_REFUSED;
...@@ -101,7 +100,8 @@ static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response, ...@@ -101,7 +100,8 @@ static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response,
if (!rrset) if (!rrset)
return KNOT_RCODE_SERVFAIL; return KNOT_RCODE_SERVFAIL;
int result = knot_response_add_rrset_answer(response, rrset, 0); assert(KNOT_PKT_IN_AN(response)) /* #10 */;
int result = knot_pkt_put(response, 0, rrset, KNOT_PF_FREE);
if (result != KNOT_EOK) { if (result != KNOT_EOK) {
knot_rrset_deep_free(&rrset, 1); knot_rrset_deep_free(&rrset, 1);
return KNOT_RCODE_SERVFAIL; return KNOT_RCODE_SERVFAIL;
...@@ -109,12 +109,10 @@ static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response, ...@@ -109,12 +109,10 @@ static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response,
result = ns_response_to_wire(response, response_wire, response_size); result = ns_response_to_wire(response, response_wire, response_size);
if (result != KNOT_EOK) { if (result != KNOT_EOK) {
knot_rrset_deep_free(&rrset, 1);
return KNOT_RCODE_SERVFAIL; return KNOT_RCODE_SERVFAIL;
} }
knot_rrset_deep_free(&rrset, 1); knot_wire_set_rcode(response->wire, KNOT_RCODE_NOERROR);
knot_response_set_rcode(response, KNOT_RCODE_NOERROR);
return KNOT_RCODE_NOERROR; return KNOT_RCODE_NOERROR;
} }
...@@ -122,12 +120,12 @@ static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response, ...@@ -122,12 +120,12 @@ static int answer_txt(knot_nameserver_t *nameserver, knot_packet_t *response,
/*! /*!
* \brief Create a response for a given query in the CHAOS class. * \brief Create a response for a given query in the CHAOS class.
*/ */
int knot_ns_answer_chaos(knot_nameserver_t *nameserver, knot_packet_t *resp, int knot_ns_answer_chaos(knot_nameserver_t *nameserver, knot_pkt_t *resp,
uint8_t *resp_wire, size_t *resp_size) uint8_t *resp_wire, size_t *resp_size)
{ {
int rcode = KNOT_RCODE_REFUSED; int rcode = KNOT_RCODE_REFUSED;
if (knot_packet_qtype(resp) == KNOT_RRTYPE_TXT) { if (knot_pkt_qtype(resp) == KNOT_RRTYPE_TXT) {
rcode = answer_txt(nameserver, resp, resp_wire, resp_size); rcode = answer_txt(nameserver, resp, resp_wire, resp_size);
} }
......
...@@ -30,7 +30,7 @@ ...@@ -30,7 +30,7 @@
#include <stdint.h> #include <stdint.h>
#include "libknot/nameserver/name-server.h" #include "libknot/nameserver/name-server.h"
#include "libknot/packet/packet.h" #include "libknot/packet/pkt.h"
/*! /*!
* \brief Create a response for a given query in the CHAOS class. * \brief Create a response for a given query in the CHAOS class.
...@@ -42,7 +42,7 @@ ...@@ -42,7 +42,7 @@
* *
* \return Always KNOT_EOK. * \return Always KNOT_EOK.
*/ */
int knot_ns_answer_chaos(knot_nameserver_t *nameserver, knot_packet_t *response, int knot_ns_answer_chaos(knot_nameserver_t *nameserver, knot_pkt_t *response,
uint8_t *response_wire, size_t *response_size); uint8_t *response_wire, size_t *response_size);
#endif // _KNOT_CHAOS_H_ #endif // _KNOT_CHAOS_H_
......
This diff is collapsed.
...@@ -43,7 +43,7 @@ ...@@ -43,7 +43,7 @@
#include "libknot/edns.h" #include "libknot/edns.h"
#include "libknot/consts.h" #include "libknot/consts.h"
#include "libknot/tsig.h" #include "libknot/tsig.h"
#include "libknot/packet/packet.h" #include "libknot/packet/pkt.h"
#include "common/sockaddr.h" #include "common/sockaddr.h"
#include "common/lists.h" #include "common/lists.h"
#include "libknot/updates/changesets.h" #include "libknot/updates/changesets.h"
...@@ -64,8 +64,7 @@ typedef struct knot_nameserver { ...@@ -64,8 +64,7 @@ typedef struct knot_nameserver {
* queries. * queries.
*/ */
knot_zonedb_t *zone_db; knot_zonedb_t *zone_db;
uint8_t *err_response; /*!< Prepared generic error response. */ knot_pkt_t *err_response; /*!< Prepared generic error response. */
size_t err_resp_size; /*!< Size of the prepared error response. */
knot_opt_rr_t *opt_rr; /*!< OPT RR with the server's EDNS0 info. */ knot_opt_rr_t *opt_rr; /*!< OPT RR with the server's EDNS0 info. */
const char *identity; //!< RFC 4892, server identity (id.server, hostname.bind). const char *identity; //!< RFC 4892, server identity (id.server, hostname.bind).
...@@ -88,8 +87,8 @@ typedef struct knot_ns_xfr { ...@@ -88,8 +87,8 @@ typedef struct knot_ns_xfr {
int type; int type;
int flags; int flags;
sockaddr_t addr, saddr; sockaddr_t addr, saddr;
knot_packet_t *query; knot_pkt_t *query;
knot_packet_t *response; knot_pkt_t *response;
knot_rcode_t rcode; knot_rcode_t rcode;
xfr_callback_t send; xfr_callback_t send;
xfr_callback_t recv; xfr_callback_t recv;
...@@ -200,8 +199,6 @@ knot_nameserver_t *knot_ns_create(); ...@@ -200,8 +199,6 @@ knot_nameserver_t *knot_ns_create();
* to decide what to do with the query, the knot_query_t type is used for this * to decide what to do with the query, the knot_query_t type is used for this
* purpose. * purpose.
* *
* \param query_wire Wire format of the query.
* \param qsize Size of the query in octets.
* \param packet Packet structure to be filled with the parsed query. * \param packet Packet structure to be filled with the parsed query.
* \param type Type of the query. * \param type Type of the query.
* *
...@@ -219,8 +216,7 @@ knot_nameserver_t *knot_ns_create(); ...@@ -219,8 +216,7 @@ knot_nameserver_t *knot_ns_create();
* ns_error_response() with \a rcode set to this * ns_error_response() with \a rcode set to this
* value to get proper error response. * value to get proper error response.
*/ */
int knot_ns_parse_packet(const uint8_t *query_wire, size_t qsize, int knot_ns_parse_packet(knot_pkt_t *packet, knot_packet_type_t *type);
knot_packet_t *packet, knot_packet_type_t *type);
int knot_ns_error_response_from_query_wire(const knot_nameserver_t *nameserver, int knot_ns_error_response_from_query_wire(const knot_nameserver_t *nameserver,
const uint8_t *query, size_t size, const uint8_t *query, size_t size,
...@@ -228,20 +224,20 @@ int knot_ns_error_response_from_query_wire(const knot_nameserver_t *nameserver, ...@@ -228,20 +224,20 @@ int knot_ns_error_response_from_query_wire(const knot_nameserver_t *nameserver,
size_t *rsize); size_t *rsize);
int knot_ns_error_response_from_query(const knot_nameserver_t *nameserver, int knot_ns_error_response_from_query(const knot_nameserver_t *nameserver,
const knot_packet_t *query, const knot_pkt_t *query,
uint8_t rcode, uint8_t *response_wire, uint8_t rcode, uint8_t *response_wire,
size_t *rsize); size_t *rsize);
void knot_ns_error_response_full(knot_nameserver_t *nameserver, void knot_ns_error_response_full(knot_nameserver_t *nameserver,
knot_packet_t *response, uint8_t rcode, knot_pkt_t *response, uint8_t rcode,
uint8_t *response_wire, size_t *rsize); uint8_t *response_wire, size_t *rsize);
int knot_ns_prep_normal_response(knot_nameserver_t *nameserver, int knot_ns_prep_normal_response(knot_nameserver_t *nameserver,
knot_packet_t *query, knot_packet_t **resp, knot_pkt_t *query, knot_pkt_t *resp,
const knot_zone_t **zone, size_t max_size); const knot_zone_t **zone, size_t max_size);
int knot_ns_prep_update_response(knot_nameserver_t *nameserver, int knot_ns_prep_update_response(knot_nameserver_t *nameserver,
knot_packet_t *query, knot_packet_t **resp, knot_pkt_t *query, knot_pkt_t **resp,
knot_zone_t **zone, size_t max_size); knot_zone_t **zone, size_t max_size);
/*! /*!
...@@ -258,11 +254,11 @@ int knot_ns_prep_update_response(knot_nameserver_t *nameserver, ...@@ -258,11 +254,11 @@ int knot_ns_prep_update_response(knot_nameserver_t *nameserver,
* \retval KNOT_EMALF if an error occured and the response is not valid. * \retval KNOT_EMALF if an error occured and the response is not valid.
*/ */
int knot_ns_answer_normal(knot_nameserver_t *nameserver, int knot_ns_answer_normal(knot_nameserver_t *nameserver,
const knot_zone_t *zone, knot_packet_t *resp, const knot_zone_t *zone, knot_pkt_t *resp,
uint8_t *response_wire, size_t *rsize, int check_any); uint8_t *response_wire, size_t *rsize, int check_any);
int knot_ns_answer_ixfr_udp(knot_nameserver_t *nameserver, int knot_ns_answer_ixfr_udp(knot_nameserver_t *nameserver,
const knot_zone_t *zone, knot_packet_t *resp, const knot_zone_t *zone, knot_pkt_t *resp,
uint8_t *response_wire, size_t *rsize); uint8_t *response_wire, size_t *rsize);
int knot_ns_init_xfr(knot_nameserver_t *nameserver, knot_ns_xfr_t *xfr); int knot_ns_init_xfr(knot_nameserver_t *nameserver, knot_ns_xfr_t *xfr);
...@@ -357,15 +353,15 @@ int knot_ns_switch_zone(knot_nameserver_t *nameserver, ...@@ -357,15 +353,15 @@ int knot_ns_switch_zone(knot_nameserver_t *nameserver,
int knot_ns_process_ixfrin(knot_nameserver_t *nameserver, int knot_ns_process_ixfrin(knot_nameserver_t *nameserver,
knot_ns_xfr_t *xfr); knot_ns_xfr_t *xfr);
int knot_ns_process_update(const knot_packet_t *query, int knot_ns_process_update(const knot_pkt_t *query,
knot_zone_contents_t *old_contents, knot_zone_contents_t *old_contents,
knot_zone_contents_t **new_contents, knot_zone_contents_t **new_contents,
knot_changesets_t *chgs, knot_rcode_t *rcode); knot_changesets_t *chgs, knot_rcode_t *rcode);
int knot_ns_create_forward_query(const knot_packet_t *query, int knot_ns_create_forward_query(const knot_pkt_t *query,
uint8_t *query_wire, size_t *size); uint8_t *query_wire, size_t *size);
int knot_ns_process_forward_response(const knot_packet_t *response, int knot_ns_process_forward_response(const knot_pkt_t *response,
uint16_t original_id, uint16_t original_id,
uint8_t *response_wire, size_t *size); uint8_t *response_wire, size_t *size);
...@@ -388,7 +384,7 @@ int knot_ns_tsig_required(int packet_nr); ...@@ -388,7 +384,7 @@ int knot_ns_tsig_required(int packet_nr);
* \retval KNOT_EOK * \retval KNOT_EOK
* \retval NS_ERR_SERVFAIL * \retval NS_ERR_SERVFAIL
*/ */
int ns_response_to_wire(knot_packet_t *resp, uint8_t *wire, int ns_response_to_wire(knot_pkt_t *resp, uint8_t *wire,
size_t *wire_size); size_t *wire_size);
/*! /*!
...@@ -398,7 +394,6 @@ int ns_response_to_wire(knot_packet_t *resp, uint8_t *wire, ...@@ -398,7 +394,6 @@ int ns_response_to_wire(knot_packet_t *resp, uint8_t *wire,
*/ */
void knot_ns_destroy(knot_nameserver_t **nameserver); void knot_ns_destroy(knot_nameserver_t **nameserver);
#endif /* _KNOTNAME_SERVER_H_ */ #endif /* _KNOTNAME_SERVER_H_ */
/*! @} */ /*! @} */
...@@ -18,7 +18,7 @@ ...@@ -18,7 +18,7 @@
#include <assert.h> #include <assert.h>
#include <stdlib.h> #include <stdlib.h>
#include "libknot/packet/packet.h" #include "libknot/packet/pkt.h"
#include "libknot/util/debug.h" #include "libknot/util/debug.h"
#include "libknot/common.h" #include "libknot/common.h"
#include "common/descriptor.h" #include "common/descriptor.h"
...@@ -692,8 +692,8 @@ static knot_rrset_t *knot_pkt_rr_from_wire(const uint8_t *wire, size_t *pos, ...@@ -692,8 +692,8 @@ static knot_rrset_t *knot_pkt_rr_from_wire(const uint8_t *wire, size_t *pos,
} }
*pos += KNOT_RR_HEADER_SIZE; *pos += KNOT_RR_HEADER_SIZE;
dbg_packet_verbose("%s: read type %u, class %u, ttl %u, rdlength %u\n", dbg_packet_verb("%s: read type %u, class %u, ttl %u, rdlength %u\n",
__func__, rrset->type, rrset->rclass, rrset->ttl, rdlength); __func__, rrset->type, rrset->rclass, rrset->ttl, rdlength);
if (rdlength == 0) { if (rdlength == 0) {
return rrset; return rrset;
......
/*! /*!
* \file packet.h * \file pkt.h
* *
* \author Lubos Slovak <lubos.slovak@nic.cz> * \author Lubos Slovak <lubos.slovak@nic.cz>
* *
......
...@@ -30,8 +30,8 @@ ...@@ -30,8 +30,8 @@
#include "common/descriptor.h" #include "common/descriptor.h"
#include "libknot/util/debug.h" #include "libknot/util/debug.h"
#include "libknot/util/utils.h" #include "libknot/util/utils.h"
#include "libknot/packet/response.h" #include "libknot/packet/wire.h"
#include "libknot/util/wire.h" #include "libknot/packet/pkt.h"
#include "libknot/dname.h" #include "libknot/dname.h"
#include "libknot/rdata.h" #include "libknot/rdata.h"
...@@ -229,21 +229,19 @@ static int knot_rrset_header_to_wire(const knot_rrset_t *rrset, ...@@ -229,21 +229,19 @@ static int knot_rrset_header_to_wire(const knot_rrset_t *rrset,
return KNOT_EMALF; return KNOT_EMALF;
} }
const uint8_t *owner; const uint8_t *owner = NULL;
uint8_t owner_len; uint8_t owner_len = 0;
uint16_t *rr_compress = NULL;
// Use compressed owner. if (compr && compr->rrinfo->compress_ptr[0] > 0) {
if (compr) { rr_compress = compr->rrinfo->compress_ptr;
owner = compr->owner.wire + compr->owner.pos; owner_len = sizeof(uint16_t);
owner_len = compr->owner.size;
// Use rrset owner.
} else { } else {
owner = rrset->owner; owner = rrset->owner;
owner_len = knot_dname_size(owner); owner_len = 0;
} }
dbg_response("Max size: %zu, compressed owner: %s, owner size: %u\n", dbg_packet("%s: max size: %zu, compressed owner: %s, owner size: %u\n",
max_size, compr ? "yes" : "no", owner_len); __func__, max_size, rr_compress ? "yes" : "no", owner_len);
// Check wire space for header. // Check wire space for header.
if (*size + owner_len + type_cls_ttl_len + rrlen_len > max_size) { if (*size + owner_len + type_cls_ttl_len + rrlen_len > max_size) {
...@@ -251,8 +249,22 @@ static int knot_rrset_header_to_wire(const knot_rrset_t *rrset, ...@@ -251,8 +249,22 @@ static int knot_rrset_header_to_wire(const knot_rrset_t *rrset,
return KNOT_ESPACE; return KNOT_ESPACE;
} }
// Write owner, type, class and ttl to wire. if (rr_compress && rr_compress[COMPR_HINT_OWNER] != 0) {
*pos += knot_dname_to_wire(*pos, owner, KNOT_DNAME_MAXLEN); /* Put compression pointer. */
knot_wire_put_pointer(*pos, rr_compress[COMPR_HINT_OWNER]);
*pos += owner_len;
} else {
/* Write owner, type, class and ttl to wire. */
int ret = knot_pkt_put_dname(owner, *pos, KNOT_DNAME_MAXLEN, compr);
if (ret < 0) {
return ret;
} else {
owner_len = ret;
*pos += owner_len;
}
/* Store first dname compression hint. */
knot_pkt_compr_hint_set(compr->rrinfo, COMPR_HINT_OWNER, compr->wire_pos);
}
dbg_rrset_detail(" Type: %u\n", rrset->type); dbg_rrset_detail(" Type: %u\n", rrset->type);
knot_wire_write_u16(*pos, rrset->type); knot_wire_write_u16(*pos, rrset->type);
...@@ -266,6 +278,7 @@ static int knot_rrset_header_to_wire(const knot_rrset_t *rrset, ...@@ -266,6 +278,7 @@ static int knot_rrset_header_to_wire(const knot_rrset_t *rrset,
knot_wire_write_u32(*pos, rrset->ttl); knot_wire_write_u32(*pos, rrset->ttl);
*pos += sizeof(uint32_t); *pos += sizeof(uint32_t);
assert(owner_len != 0);
*size += owner_len + type_cls_ttl_len; *size += owner_len + type_cls_ttl_len;
return KNOT_EOK; return KNOT_EOK;
...@@ -307,18 +320,26 @@ static int knot_rrset_rdata_to_wire_one(const knot_rrset_t *rrset, ...@@ -307,18 +320,26 @@ static int knot_rrset_rdata_to_wire_one(const knot_rrset_t *rrset,
/* Actual RDLENGTH. */ /* Actual RDLENGTH. */
uint16_t rdlength = 0; uint16_t rdlength = 0;
/* Compression pointer hint. */
uint16_t hint_id = COMPR_HINT_RDATA + rdata_pos;
const rdata_descriptor_t *desc = get_rdata_descriptor(rrset->type); const rdata_descriptor_t *desc = get_rdata_descriptor(rrset->type);
for (int i = 0; desc->block_types[i] != KNOT_RDATA_WF_END; i++) { for (int i = 0; desc->block_types[i] != KNOT_RDATA_WF_END; i++) {
int item = desc->block_types[i]; int item = desc->block_types[i];
if (compr && descriptor_item_is_compr_dname(item)) { if (compr && descriptor_item_is_compr_dname(item)) {
dbg_packet("%s: putting compressed name\n", __func__);
const knot_dname_t *dname = rdata + offset; const knot_dname_t *dname = rdata + offset;
int ret = knot_response_compress_dname(dname, int ret = knot_pkt_put_dname(dname, *pos,
compr, *pos, max_size - size - rdlength,
max_size - size - rdlength); compr);
if (ret < 0) { if (ret < 0) {
return KNOT_ESPACE; return KNOT_ESPACE;
} }
/* Store first dname compression hint. */
if (knot_pkt_compr_hint(compr->rrinfo, hint_id) == 0) {
knot_pkt_compr_hint_set(compr->rrinfo, hint_id, compr->wire_pos);
}
assert(ret + size + rdlength <= max_size); assert(ret + size + rdlength <= max_size);
dbg_response_exec_detail( dbg_response_exec_detail(
char *name = knot_dname_to_str(dname); char *name = knot_dname_to_str(dname);
...@@ -331,6 +352,7 @@ dbg_response_exec_detail( ...@@ -331,6 +352,7 @@ dbg_response_exec_detail(
offset += knot_dname_size(dname); offset += knot_dname_size(dname);
compr->wire_pos += ret; compr->wire_pos += ret;
} else if (descriptor_item_is_dname(item)) { } else if (descriptor_item_is_dname(item)) {
dbg_packet("%s: putting uncompressed name\n", __func__);
const knot_dname_t *dname = rdata + offset; const knot_dname_t *dname = rdata + offset;
dbg_rrset_exec_detail( dbg_rrset_exec_detail(
char *name = knot_dname_to_str(dname); char *name = knot_dname_to_str(dname);
...@@ -342,6 +364,10 @@ dbg_rrset_exec_detail( ...@@ -342,6 +364,10 @@ dbg_rrset_exec_detail(
int dname_size = knot_dname_to_wire(*pos, dname, maxb); int dname_size = knot_dname_to_wire(*pos, dname, maxb);
if (dname_size < 0) if (dname_size < 0)
return KNOT_ESPACE; return KNOT_ESPACE;
/* Store first dname compression hint. */
if (knot_pkt_compr_hint(compr->rrinfo, hint_id) == 0) {
knot_pkt_compr_hint_set(compr->rrinfo, hint_id, compr->wire_pos);
}
dbg_rrset_detail("Uncompressed dname size: %d\n", dbg_rrset_detail("Uncompressed dname size: %d\n",
dname_size); dname_size);
*pos += dname_size; *pos += dname_size;
...@@ -409,52 +435,24 @@ dbg_rrset_exec_detail( ...@@ -409,52 +435,24 @@ dbg_rrset_exec_detail(
size += rdlength; size += rdlength;
*rr_size = size; *rr_size = size;
dbg_packet("%s: written rrset %zu bytes\n", __func__, *rr_size);
assert(size <= max_size); assert(size <= max_size);
return KNOT_EOK; return KNOT_EOK;
} }
static int knot_rrset_to_wire_aux(const knot_rrset_t *rrset, uint8_t **pos, static int knot_rrset_to_wire_aux(const knot_rrset_t *rrset, uint8_t **pos,
size_t max_size, compression_param_t *comp) size_t max_size, knot_compr_t *comp)
{ {
uint8_t wf_owner[256];
size_t size = 0; size_t size = 0;
assert(rrset != NULL); assert(rrset != NULL);
assert(rrset->owner != NULL); assert(rrset->owner != NULL);
assert(pos != NULL); assert(pos != NULL);
assert(*pos != NULL); assert(*pos != NULL);
dbg_rrset_detail("Max size: %zu, owner: %p, owner size: %d\n",
max_size, rrset, knot_dname_size(rrset->owner));
knot_compr_t compr_info;
if (comp) {
dbg_response_detail("Compressing RR owner: %s.\n",
rrset->owner);
compr_info.table = comp->compressed_dnames;
compr_info.wire = comp->wire;
compr_info.wire_pos = comp->wire_pos;
int ret = knot_response_compress_dname(rrset->owner, &compr_info,
wf_owner, max_size);
if (ret < 0) {
return KNOT_ESPACE;
}
compr_info.owner.pos = 0;
compr_info.owner.wire = wf_owner;
compr_info.owner.size = ret;
dbg_response_detail("Compressed owner has size=%d\n",
compr_info.owner.size);
}
dbg_rrset_detail("Max size: %zu, size: %zu\n", max_size, size);
// No RDATA, just save header and 0 RDLENGTH. // No RDATA, just save header and 0 RDLENGTH.
if (rrset->rdata_count == 0) { if (rrset->rdata_count == 0) {
size_t header_size = 0; size_t header_size = 0;
int ret = knot_rrset_header_to_wire(rrset, pos, max_size, int ret = knot_rrset_header_to_wire(rrset, pos, max_size, comp,
comp ? &compr_info : NULL,
&header_size); &header_size);
if (ret != KNOT_EOK) { if (ret != KNOT_EOK) {
return ret; return ret;
...@@ -474,8 +472,7 @@ static int knot_rrset_to_wire_aux(const knot_rrset_t *rrset, uint8_t **pos, ...@@ -474,8 +472,7 @@ static int knot_rrset_to_wire_aux(const knot_rrset_t *rrset, uint8_t **pos,
max_size);