simple_dns/dns/rdata/
a.rs1use crate::{bytes_buffer::BytesBuffer, dns::WireFormat};
2use std::net::Ipv4Addr;
3
4use super::RR;
5
6#[derive(Debug, PartialEq, Eq, Hash, Clone)]
8pub struct A {
9 pub address: u32,
11}
12
13impl RR for A {
14 const TYPE_CODE: u16 = 1;
15}
16
17impl<'a> WireFormat<'a> for A {
18 const MINIMUM_LEN: usize = 4;
19
20 fn parse(data: &mut BytesBuffer<'a>) -> crate::Result<Self>
21 where
22 Self: Sized,
23 {
24 data.get_u32().map(|address| Self { address })
25 }
26
27 fn write_to<T: std::io::Write>(&self, out: &mut T) -> crate::Result<()> {
28 out.write_all(&self.address.to_be_bytes())
29 .map_err(crate::SimpleDnsError::from)
30 }
31}
32
33impl A {
34 pub fn into_owned(self) -> Self {
36 self
37 }
38}
39
40impl From<Ipv4Addr> for A {
41 fn from(addr: Ipv4Addr) -> Self {
42 Self {
43 address: addr.into(),
44 }
45 }
46}
47
48#[cfg(test)]
49mod tests {
50 use crate::{rdata::RData, ResourceRecord};
51
52 use super::*;
53
54 #[test]
55 fn parse_and_write_a() {
56 let a = A {
57 address: 2130706433,
58 };
59
60 let mut bytes = Vec::new();
61 assert!(a.write_to(&mut bytes).is_ok());
62
63 let a = A::parse(&mut BytesBuffer::new(&bytes));
64 assert!(a.is_ok());
65 let a = a.unwrap();
66
67 assert_eq!(2130706433, a.address);
68 assert_eq!(bytes.len(), a.len());
69 }
70
71 #[test]
72 fn parse_sample() -> Result<(), Box<dyn std::error::Error>> {
73 let sample_a = std::fs::read("samples/zonefile/A.sample.A")?;
74 let sample_ip: u32 = "26.3.0.103".parse::<Ipv4Addr>()?.into();
75
76 let sample_a_rdata = match ResourceRecord::parse(&mut BytesBuffer::new(&sample_a))?.rdata {
77 RData::A(a) => a,
78 _ => unreachable!(),
79 };
80
81 assert_eq!(sample_a_rdata.address, sample_ip);
82 Ok(())
83 }
84}