adding docstrings
This commit is contained in:
parent
6367671094
commit
a023165a8d
@ -1,3 +1,5 @@
|
|||||||
|
//! DNS server component for processing requests and replying with DNS records
|
||||||
|
|
||||||
use clap::Parser;
|
use clap::Parser;
|
||||||
use std::{thread};
|
use std::{thread};
|
||||||
|
|
||||||
@ -9,6 +11,7 @@ use std::net::SocketAddr;
|
|||||||
use dnstplib::net::socket::DNSSocket;
|
use dnstplib::net::socket::DNSSocket;
|
||||||
use dnstplib::processor::RequestProcesor;
|
use dnstplib::processor::RequestProcesor;
|
||||||
|
|
||||||
|
/// Command-line arguments for configuring the server
|
||||||
#[derive(Parser, Debug)]
|
#[derive(Parser, Debug)]
|
||||||
#[command(author, version, about, long_about = None)]
|
#[command(author, version, about, long_about = None)]
|
||||||
struct Args {
|
struct Args {
|
||||||
|
@ -1,18 +1,24 @@
|
|||||||
|
//! Utility functions for operating on bytes
|
||||||
|
|
||||||
|
/// 8-bit mask for wiping out bits past a byte. Formatted as a 32-bit number
|
||||||
const BYTEMASK_32: u32 = 0b11111111;
|
const BYTEMASK_32: u32 = 0b11111111;
|
||||||
|
/// 8-bit mask for wiping out bits past a byte. Formatted as a 16-bit number
|
||||||
const BYTEMASK_16: u16 = 0b11111111;
|
const BYTEMASK_16: u16 = 0b11111111;
|
||||||
|
|
||||||
|
/// Take two sequential bytes starting from idx in buffer and return a concatenated 2 byte number
|
||||||
pub fn two_byte_extraction(buffer: &[u8], idx: usize) -> u16
|
pub fn two_byte_extraction(buffer: &[u8], idx: usize) -> u16
|
||||||
{
|
{
|
||||||
((buffer[idx] as u16) << 8) | buffer[idx + 1] as u16
|
((buffer[idx] as u16) << 8) | buffer[idx + 1] as u16
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Take a 2 byte number and split it in to it's two 8 bit halves
|
||||||
pub fn two_byte_split(num: u16) -> (u8, u8)
|
pub fn two_byte_split(num: u16) -> (u8, u8)
|
||||||
{
|
{
|
||||||
((num >> 8) as u8,
|
((num >> 8) as u8,
|
||||||
(num & BYTEMASK_16) as u8)
|
(num & BYTEMASK_16) as u8)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Split a 32 bit number into it's 8-bit quartered components
|
||||||
pub fn four_byte_split(num: u32) -> (u8, u8, u8, u8)
|
pub fn four_byte_split(num: u32) -> (u8, u8, u8, u8)
|
||||||
{
|
{
|
||||||
((num >> 24) as u8,
|
((num >> 24) as u8,
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
use crate::byte::{four_byte_split, two_byte_split};
|
use crate::byte::{four_byte_split, two_byte_split};
|
||||||
use crate::message::question::{QClass, QType};
|
use crate::message::question::{DNSQuestion, QClass, QType};
|
||||||
use crate::string::encode_domain_name;
|
use crate::string::encode_domain_name;
|
||||||
|
|
||||||
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug)]
|
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug)]
|
||||||
@ -14,7 +14,7 @@ pub struct DNSAnswer {
|
|||||||
|
|
||||||
impl DNSAnswer {
|
impl DNSAnswer {
|
||||||
|
|
||||||
pub fn to_bytes(& self) -> Vec<u8>
|
pub fn to_bytes(&self) -> Vec<u8>
|
||||||
{
|
{
|
||||||
let mut ret = encode_domain_name(&self.name);
|
let mut ret = encode_domain_name(&self.name);
|
||||||
|
|
||||||
@ -40,4 +40,16 @@ impl DNSAnswer {
|
|||||||
|
|
||||||
return ret
|
return ret
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn answers_to_bytes(answers: &Vec<DNSAnswer>) -> Vec<u8>
|
||||||
|
{
|
||||||
|
let mut ret = Vec::with_capacity(20);
|
||||||
|
|
||||||
|
for a in answers
|
||||||
|
{
|
||||||
|
ret.append(&mut a.to_bytes());
|
||||||
|
}
|
||||||
|
|
||||||
|
ret
|
||||||
}
|
}
|
@ -2,14 +2,17 @@ use std::convert::TryFrom;
|
|||||||
use crate::byte::apply_split_bytes;
|
use crate::byte::apply_split_bytes;
|
||||||
use crate::message::header::Direction::Response;
|
use crate::message::header::Direction::Response;
|
||||||
|
|
||||||
|
/// Size in bytes for a DNS message
|
||||||
pub const HEADER_SIZE: usize = 12;
|
pub const HEADER_SIZE: usize = 12;
|
||||||
|
|
||||||
|
/// Flag for whether the message represents a request or a response
|
||||||
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug, Copy, Clone)]
|
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug, Copy, Clone)]
|
||||||
pub enum Direction {
|
pub enum Direction {
|
||||||
Request = 0,
|
Request = 0,
|
||||||
Response = 1
|
Response = 1
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Operation code for describing the purpose of the message
|
||||||
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug, Copy, Clone)]
|
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug, Copy, Clone)]
|
||||||
pub enum Opcode {
|
pub enum Opcode {
|
||||||
Query = 0,
|
Query = 0,
|
||||||
@ -32,6 +35,7 @@ impl TryFrom<u16> for Opcode {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// What is the status of the request or response, what was the nature of the error, if encountered
|
||||||
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug, Copy, Clone)]
|
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug, Copy, Clone)]
|
||||||
pub enum ResponseCode {
|
pub enum ResponseCode {
|
||||||
NoError = 0,
|
NoError = 0,
|
||||||
@ -68,17 +72,23 @@ impl TryFrom<u16> for ResponseCode {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Represents a header including flag fields and record counts
|
||||||
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug)]
|
#[derive(Ord, PartialOrd, Eq, PartialEq, Debug)]
|
||||||
pub struct DNSHeader {
|
pub struct DNSHeader {
|
||||||
|
/// Random ID for associating responses with requests
|
||||||
pub id: u16,
|
pub id: u16,
|
||||||
|
/// Is the message a request or the associated response
|
||||||
pub direction: Direction,
|
pub direction: Direction,
|
||||||
|
/// What is the message function, e.g query, reverse DNS query
|
||||||
pub opcode: Opcode,
|
pub opcode: Opcode,
|
||||||
pub authoritative: bool,
|
pub authoritative: bool,
|
||||||
pub truncation: bool,
|
pub truncation: bool,
|
||||||
pub recursion_desired: bool,
|
pub recursion_desired: bool,
|
||||||
pub recursion_available: bool,
|
pub recursion_available: bool,
|
||||||
pub valid_zeroes: bool,
|
pub valid_zeroes: bool,
|
||||||
|
/// Status of the request or response
|
||||||
pub response: ResponseCode,
|
pub response: ResponseCode,
|
||||||
|
/// Number of questions being made, should be the same in both the request and response
|
||||||
pub question_count: u16,
|
pub question_count: u16,
|
||||||
pub answer_record_count: u16,
|
pub answer_record_count: u16,
|
||||||
pub authority_record_count: u16,
|
pub authority_record_count: u16,
|
||||||
@ -86,6 +96,7 @@ pub struct DNSHeader {
|
|||||||
}
|
}
|
||||||
|
|
||||||
impl DNSHeader {
|
impl DNSHeader {
|
||||||
|
/// Serialise a header memory structure back into bytes for putting on the wire
|
||||||
pub fn to_bytes(&self) -> [u8; 12]
|
pub fn to_bytes(&self) -> [u8; 12]
|
||||||
{
|
{
|
||||||
let mut header_bytes: [u8; 12] = [0; 12];
|
let mut header_bytes: [u8; 12] = [0; 12];
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
use std::net::SocketAddr;
|
use std::net::SocketAddr;
|
||||||
use crate::message::answer::DNSAnswer;
|
use crate::message::answer::{answers_to_bytes, DNSAnswer};
|
||||||
use crate::message::header::DNSHeader;
|
use crate::message::header::DNSHeader;
|
||||||
use crate::message::question::{DNSQuestion, questions_to_bytes};
|
use crate::message::question::{DNSQuestion, questions_to_bytes};
|
||||||
|
|
||||||
@ -17,8 +17,10 @@ impl DNSResponse {
|
|||||||
{
|
{
|
||||||
let mut header_bytes = self.header.to_bytes().to_vec();
|
let mut header_bytes = self.header.to_bytes().to_vec();
|
||||||
let mut body_bytes = questions_to_bytes(&self.questions);
|
let mut body_bytes = questions_to_bytes(&self.questions);
|
||||||
|
let mut answer_bytes = answers_to_bytes(&self.answers);
|
||||||
|
|
||||||
header_bytes.append(&mut body_bytes);
|
header_bytes.append(&mut body_bytes);
|
||||||
|
header_bytes.append(&mut answer_bytes);
|
||||||
|
|
||||||
return header_bytes
|
return header_bytes
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user