Improve TimeExceeded and ParamProblem support

- Improve TimeExceeded support
   - Add support for message codes
   - Add the TimeExceeded enum type
 - Improve ParamProblem support
   - Add support for message codes
   - Add the ParamProblem enem type

Closes: #152
Approved by: whitequark
v0.7.x
Dan Robertson 2018-02-05 14:34:18 +00:00 committed by Homu
parent 01f3b53e70
commit c3d5790c8e
1 changed files with 60 additions and 7 deletions

View File

@ -69,7 +69,6 @@ enum_with_unknown! {
}
}
impl fmt::Display for DstUnreachable {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
@ -93,6 +92,56 @@ impl fmt::Display for DstUnreachable {
}
}
enum_with_unknown! {
/// Internet protocol control message subtype for the type "Parameter Problem".
pub doc enum ParamProblem(u8) {
/// Erroneous header field encountered.
ErroneousHdrField = 0,
/// Unrecognized Next Header type encountered.
UnrecognizedNxtHdr = 1,
/// Unrecognized IPv6 option encountered.
UnrecognizedOption = 2
}
}
impl fmt::Display for ParamProblem {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
&ParamProblem::ErroneousHdrField =>
write!(f, "erroneous header field."),
&ParamProblem::UnrecognizedNxtHdr =>
write!(f, "unrecognized next header type."),
&ParamProblem::UnrecognizedOption =>
write!(f, "unrecognized IPv6 option."),
&ParamProblem::Unknown(id) =>
write!(f, "{}", id)
}
}
}
enum_with_unknown! {
/// Internet protocol control message subtype for the type "Time Exceeded".
pub doc enum TimeExceeded(u8) {
/// Hop limit exceeded in transit.
HopLimitExceeded = 0,
/// Fragment reassembly time exceeded.
FragReassemExceeded = 1
}
}
impl fmt::Display for TimeExceeded {
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
match self {
&TimeExceeded::HopLimitExceeded =>
write!(f, "hop limit exceeded in transit"),
&TimeExceeded::FragReassemExceeded =>
write!(f, "fragment reassembly time exceeded"),
&TimeExceeded::Unknown(id) =>
write!(f, "{}", id)
}
}
}
/// A read/write wrapper around an Internet Control Message Protocol version 6 packet buffer.
#[derive(Debug, PartialEq, Clone)]
pub struct Packet<T: AsRef<[u8]>> {
@ -334,10 +383,12 @@ pub enum Repr<'a> {
data: &'a [u8]
},
TimeExceeded {
reason: TimeExceeded,
header: Ipv6Repr,
data: &'a [u8]
},
ParamProblem {
reason: ParamProblem,
pointer: u32,
header: Ipv6Repr,
data: &'a [u8]
@ -398,16 +449,18 @@ impl<'a> Repr<'a> {
data: payload
})
},
(Message::TimeExceeded, 0) => {
(Message::TimeExceeded, code) => {
let (payload, repr) = create_packet_from_payload(packet)?;
Ok(Repr::TimeExceeded {
reason: TimeExceeded::from(code),
header: repr,
data: payload
})
},
(Message::ParamProblem, 0) => {
(Message::ParamProblem, code) => {
let (payload, repr) = create_packet_from_payload(packet)?;
Ok(Repr::ParamProblem {
reason: ParamProblem::from(code),
pointer: packet.param_problem_ptr(),
header: repr,
data: payload
@ -473,16 +526,16 @@ impl<'a> Repr<'a> {
emit_contained_packet(packet.payload_mut(), header, &data);
},
&Repr::TimeExceeded { header, data } => {
&Repr::TimeExceeded { reason, header, data } => {
packet.set_msg_type(Message::TimeExceeded);
packet.set_msg_code(0);
packet.set_msg_code(reason.into());
emit_contained_packet(packet.payload_mut(), header, &data);
},
&Repr::ParamProblem { pointer, header, data } => {
&Repr::ParamProblem { reason, pointer, header, data } => {
packet.set_msg_type(Message::ParamProblem);
packet.set_msg_code(0);
packet.set_msg_code(reason.into());
packet.set_param_problem_ptr(pointer);
emit_contained_packet(packet.payload_mut(), header, &data);