289 lines
6.0 KiB
C
289 lines
6.0 KiB
C
|
|
/*
|
||
|
|
**********************************************************************************************
|
||
|
|
* File: dns_decoder.h
|
||
|
|
* Description: dns decoder api
|
||
|
|
* Authors: Liu XueLi <liuxueli@geedgenetworks.com>
|
||
|
|
* Date: 2024-02-07
|
||
|
|
* Copyright: (c) Since 2022 Geedge Networks, Ltd. All rights reserved.
|
||
|
|
***********************************************************************************************
|
||
|
|
*/
|
||
|
|
|
||
|
|
#ifndef _DNS_DECODER_H_
|
||
|
|
#define _DNS_DECODER_H_
|
||
|
|
|
||
|
|
#ifdef __cplusplus
|
||
|
|
extern "C"
|
||
|
|
{
|
||
|
|
#endif
|
||
|
|
|
||
|
|
#include <stdint.h>
|
||
|
|
#include <linux/limits.h>
|
||
|
|
#include <stddef.h>
|
||
|
|
|
||
|
|
#define DNS_MESSAGE_TOPIC "TOPIC_DNS"
|
||
|
|
|
||
|
|
#define DNS_NAME_MAX (NAME_MAX + 1)
|
||
|
|
#define HINFO_NAME_MAX (40 + 1) /* https://www.ietf.org/rfc/rfc1010.txt */
|
||
|
|
|
||
|
|
#define DNS_CLASS_UNKNOWN 0
|
||
|
|
#define DNS_CLASS_IN 1
|
||
|
|
#define DNS_CLASS_CS 2
|
||
|
|
#define DNS_CLASS_CH 3
|
||
|
|
#define DNS_CLASS_HS 4
|
||
|
|
#define DNS_CLASS_ANY 255
|
||
|
|
|
||
|
|
/* RR(resource record) type, defined in https://www.ietf.org/rfc/rfc1035.txt */
|
||
|
|
enum dns_rr_type
|
||
|
|
{
|
||
|
|
DNS_RR_TYPE_A = 1,
|
||
|
|
DNS_RR_TYPE_NS,
|
||
|
|
DNS_RR_TYPE_MD, /* Obsolete - use MX, rfc973 */
|
||
|
|
DNS_RR_TYPE_MF, /* Obsolete - use MX, rfc973 */
|
||
|
|
DNS_RR_TYPE_CNAME,
|
||
|
|
DNS_RR_TYPE_SOA,
|
||
|
|
DNS_RR_TYPE_MB, /* EXPERIMENTAL, rfc883,rfc2505 */
|
||
|
|
DNS_RR_TYPE_MG, /* EXPERIMENTAL, rfc883,rfc2505 */
|
||
|
|
DNS_RR_TYPE_MR, /* EXPERIMENTAL, rfc883 */
|
||
|
|
DNS_RR_TYPE_NULL, /* EXPERIMENTAL, rfc1035 */
|
||
|
|
DNS_RR_TYPE_WKS, /* Not to be relied upon, rfc1123 */
|
||
|
|
DNS_RR_TYPE_PTR,
|
||
|
|
DNS_RR_TYPE_HINFO,
|
||
|
|
DNS_RR_TYPE_MINFO,
|
||
|
|
DNS_RR_TYPE_MX,
|
||
|
|
DNS_RR_TYPE_TXT,
|
||
|
|
DNS_RR_TYPE_RP,
|
||
|
|
DNS_RR_TYPE_ISDN = 20,
|
||
|
|
DNS_RR_TYPE_AAAA = 28, /* dns_ipv6 */
|
||
|
|
DNS_RR_TYPE_SRV = 33,
|
||
|
|
DNS_RR_TYPE_DNAME = 39,
|
||
|
|
DNS_RR_TYPE_OPT = 41,
|
||
|
|
DNS_RR_TYPE_DS = 43,
|
||
|
|
DNS_RR_TYPE_RRSIG = 46,
|
||
|
|
DNS_RR_TYPE_NSEC,
|
||
|
|
DNS_RR_TYPE_DNSKEY,
|
||
|
|
DNS_RR_TYPE_NSEC3 = 50,
|
||
|
|
DNS_RR_TYPE_NSEC3PARAM,
|
||
|
|
DNS_RR_TYPE_HTTPS = 65,
|
||
|
|
DNS_RR_TYPE_AXFR = 252,
|
||
|
|
DNS_RR_TYPE_MAILB,
|
||
|
|
DNS_RR_TYPE_MAILA, /* Obsolete - see MX */
|
||
|
|
DNS_RR_TYPE_ANY,
|
||
|
|
DNS_RR_TYPE_DLV = 32769, /* DSNSEC Lokkaside Validation */
|
||
|
|
DNS_RR_TYPE_UNKNOWN = 65534
|
||
|
|
};
|
||
|
|
|
||
|
|
struct dstring
|
||
|
|
{
|
||
|
|
size_t value_sz;
|
||
|
|
uint8_t value[DNS_NAME_MAX];
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_hinfo
|
||
|
|
{
|
||
|
|
struct dstring os;
|
||
|
|
struct dstring cpu;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_minfo
|
||
|
|
{
|
||
|
|
struct dstring rmailbx;
|
||
|
|
struct dstring emailbx;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_mx
|
||
|
|
{
|
||
|
|
uint16_t preference;
|
||
|
|
struct dstring exchange;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_soa
|
||
|
|
{
|
||
|
|
struct dstring mname;
|
||
|
|
struct dstring rname;
|
||
|
|
uint32_t serial;
|
||
|
|
uint32_t refresh;
|
||
|
|
uint32_t retry;
|
||
|
|
uint32_t expire;
|
||
|
|
uint32_t minimum;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_rp
|
||
|
|
{
|
||
|
|
struct dstring txt_rr;
|
||
|
|
struct dstring mailbox;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_wks
|
||
|
|
{
|
||
|
|
uint8_t protocol;
|
||
|
|
uint32_t addr;
|
||
|
|
uint32_t size;
|
||
|
|
uint8_t *bitmap;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_srv
|
||
|
|
{
|
||
|
|
uint16_t priority;
|
||
|
|
uint16_t weight;
|
||
|
|
uint16_t port;
|
||
|
|
struct dstring target;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_ds
|
||
|
|
{
|
||
|
|
uint16_t key_tag;
|
||
|
|
uint8_t algo;
|
||
|
|
uint8_t digest_type;
|
||
|
|
uint32_t digest_len;
|
||
|
|
uint8_t *digest;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_rrsig
|
||
|
|
{
|
||
|
|
uint16_t type_covered;
|
||
|
|
uint8_t algo;
|
||
|
|
uint8_t labels;
|
||
|
|
uint32_t original_ttl;
|
||
|
|
uint32_t sig_expiration;
|
||
|
|
uint32_t sig_inception;
|
||
|
|
uint16_t key_tag;
|
||
|
|
uint32_t signature_len;
|
||
|
|
uint8_t *signature;
|
||
|
|
struct dstring signer_name;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_nsec
|
||
|
|
{
|
||
|
|
uint16_t maps_len;
|
||
|
|
struct dstring next_domain;
|
||
|
|
struct dstring type_bit_maps;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_dnskey
|
||
|
|
{
|
||
|
|
uint16_t flags;
|
||
|
|
uint8_t protocol;
|
||
|
|
uint8_t algo;
|
||
|
|
uint32_t public_key_len;
|
||
|
|
uint8_t *public_key;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_nsec3
|
||
|
|
{
|
||
|
|
uint8_t hash_algo;
|
||
|
|
uint8_t flags;
|
||
|
|
uint8_t salt_len;
|
||
|
|
uint8_t hash_len;
|
||
|
|
uint16_t iteration;
|
||
|
|
uint16_t maps_len;
|
||
|
|
uint8_t *salt_value;
|
||
|
|
uint8_t *next_hash_owner;
|
||
|
|
struct dstring type_bit_maps;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct rdata_nsec3param
|
||
|
|
{
|
||
|
|
uint8_t hash_algo;
|
||
|
|
uint8_t flags;
|
||
|
|
uint8_t salt_len;
|
||
|
|
uint16_t iteration;
|
||
|
|
uint8_t *salt_value;
|
||
|
|
};
|
||
|
|
|
||
|
|
/* rr is short for resource record */
|
||
|
|
struct dns_resource_record
|
||
|
|
{
|
||
|
|
struct dstring qname;
|
||
|
|
enum dns_rr_type type;
|
||
|
|
uint16_t rr_class;
|
||
|
|
uint32_t ttl; /* 1byte: extended RCODE; 1byte: version; 2bytes: Z(upper bit) if type is OPT */
|
||
|
|
uint16_t rdlength;
|
||
|
|
union
|
||
|
|
{
|
||
|
|
|
||
|
|
struct dstring cname;
|
||
|
|
struct dstring mb;
|
||
|
|
struct dstring md;
|
||
|
|
struct dstring mf;
|
||
|
|
struct dstring mg;
|
||
|
|
struct dstring mr;
|
||
|
|
struct dstring ns;
|
||
|
|
struct dstring ptr;
|
||
|
|
struct dstring a;
|
||
|
|
struct dstring aaaa;
|
||
|
|
struct dstring dname;
|
||
|
|
struct dstring isdn;
|
||
|
|
struct dstring unknown;
|
||
|
|
|
||
|
|
struct dstring txt;
|
||
|
|
struct dstring null;
|
||
|
|
|
||
|
|
struct rdata_hinfo hinfo;
|
||
|
|
struct rdata_minfo minfo;
|
||
|
|
struct rdata_mx mx;
|
||
|
|
struct rdata_soa soa;
|
||
|
|
struct rdata_rp rp;
|
||
|
|
struct rdata_wks wks;
|
||
|
|
struct rdata_srv srv;
|
||
|
|
struct rdata_ds ds;
|
||
|
|
struct rdata_rrsig rrsig;
|
||
|
|
struct rdata_nsec nsec;
|
||
|
|
struct rdata_dnskey dnskey;
|
||
|
|
struct rdata_nsec3 nsec3;
|
||
|
|
struct rdata_nsec3param nsec3param;
|
||
|
|
struct dstring string;
|
||
|
|
} rdata;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct dns_message;
|
||
|
|
|
||
|
|
|
||
|
|
/*.
|
||
|
|
First call DNS_MESSAGE_TRANSACTION_BEGIN to create the transaction,
|
||
|
|
then publish the transaction's DNS_MESSAGE_QUERY/DNS_MESSAGE_RESPONSE,
|
||
|
|
and finally call DNS_MESSAGE_TRANSACTION_END to release the transaction.
|
||
|
|
*/
|
||
|
|
enum dns_message_type
|
||
|
|
{
|
||
|
|
DNS_MESSAGE_QUERY=1,
|
||
|
|
DNS_MESSAGE_RESPONSE,
|
||
|
|
DNS_MESSAGE_TRANSACTION_BEGIN,
|
||
|
|
DNS_MESSAGE_TRANSACTION_END,
|
||
|
|
DNS_MESSAGE_MAX
|
||
|
|
};
|
||
|
|
|
||
|
|
enum dns_message_type dns_message_type_get(struct dns_message *msg);
|
||
|
|
|
||
|
|
struct dns_flag
|
||
|
|
{
|
||
|
|
uint8_t qr:1;
|
||
|
|
uint8_t opcode:4;
|
||
|
|
uint8_t aa:1;
|
||
|
|
uint8_t tc:1;
|
||
|
|
uint8_t rd:1;
|
||
|
|
uint8_t ra:1;
|
||
|
|
uint8_t z:3;
|
||
|
|
uint8_t rcode:4;
|
||
|
|
};
|
||
|
|
|
||
|
|
struct dns_query_question
|
||
|
|
{
|
||
|
|
enum dns_rr_type qtype;
|
||
|
|
uint16_t qclass;
|
||
|
|
size_t qname_sz;
|
||
|
|
uint8_t qname[DNS_NAME_MAX];
|
||
|
|
};
|
||
|
|
|
||
|
|
int32_t dns_message_header_id_get(struct dns_message *msg);
|
||
|
|
struct dns_flag *dns_message_header_flag_get0(struct dns_message *msg);
|
||
|
|
void dns_message_question_get0(struct dns_message *msg, struct dns_query_question **question, uint16_t *n_question);
|
||
|
|
void dns_message_answer_resource_record_get0(struct dns_message *msg, struct dns_resource_record **answer_rr, uint16_t *n_answer_rr);
|
||
|
|
void dns_message_authority_resource_record_get0(struct dns_message *msg, struct dns_resource_record **authority_rr, uint16_t *n_authority_rr);
|
||
|
|
void dns_message_additional_resource_record_get0(struct dns_message *msg, struct dns_resource_record **additional_rr, uint16_t *n_additional_rr);
|
||
|
|
|
||
|
|
#ifdef __cplusplus
|
||
|
|
}
|
||
|
|
#endif
|
||
|
|
|
||
|
|
#endif
|