forked from lavina/lavina
1
0
Fork 0

feat(xmpp): respond to unknown IQs with errors

This commit is contained in:
Nikita Vilunov 2023-03-21 01:16:02 +01:00
parent a65ea89ce1
commit 3e1bb53c1b
5 changed files with 32 additions and 8 deletions

View File

@ -333,6 +333,21 @@ async fn socket_final(
} }
xml_writer.get_mut().flush().await?; xml_writer.get_mut().flush().await?;
} }
proto::IqClientBody::Unknown(_) => {
let mut events = vec![];
let req = Iq {
from: None,
id: iq.id,
to: None,
r#type: xmpp::client::IqType::Error,
body: (),
};
req.serialize(&mut events);
for i in events {
xml_writer.write_event_async(i).await?;
}
xml_writer.get_mut().flush().await?;
},
}, },
proto::ClientPacket::Message(_) => todo!(), proto::ClientPacket::Message(_) => todo!(),
proto::ClientPacket::Presence(p) => { proto::ClientPacket::Presence(p) => {

View File

@ -15,6 +15,7 @@ pub enum IqClientBody {
Bind(BindRequest), Bind(BindRequest),
Session(Session), Session(Session),
Roster(RosterQuery), Roster(RosterQuery),
Unknown(Ignore),
} }
#[derive(From)] #[derive(From)]
@ -26,6 +27,7 @@ enum IqClientBodyParserInner {
Bind(<BindRequest as FromXml>::P), Bind(<BindRequest as FromXml>::P),
SessionV(<Session as FromXml>::P), SessionV(<Session as FromXml>::P),
RosterV(<RosterQuery as FromXml>::P), RosterV(<RosterQuery as FromXml>::P),
UnknownV(<Ignore as FromXml>::P),
} }
impl FromXml for IqClientBody { impl FromXml for IqClientBody {
@ -58,12 +60,16 @@ impl Parser for IqClientBodyParser {
match_parser!(IqClientBodyParser, name, namespace, event; match_parser!(IqClientBodyParser, name, namespace, event;
BindRequest, BindRequest,
Session, Session,
RosterQuery RosterQuery,
{
IqClientBodyParser(Ignore::parse().into()).consume(namespace, event)
}
) )
} }
Bind(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event), Bind(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event),
SessionV(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event), SessionV(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event),
RosterV(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event), RosterV(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event),
UnknownV(p) => delegate_parsing!(p, IqClientBodyParserInner, namespace, event),
} }
} }
} }
@ -112,7 +118,10 @@ impl Parser for ClientPacketParser {
match_parser!(ClientPacketParser, name, namespace, event; match_parser!(ClientPacketParser, name, namespace, event;
Iq::<IqClientBody>, Iq::<IqClientBody>,
Presence::<Ignore>, Presence::<Ignore>,
Message Message,
{
Continuation::Final(Err(ffail!("Unexpected XML event of name {:?} in namespace {:?}", name, namespace)))
}
) )
} }
IqV(p) => delegate_parsing!(p, ClientPacketParserInner, namespace, event), IqV(p) => delegate_parsing!(p, ClientPacketParserInner, namespace, event),

View File

@ -97,7 +97,7 @@ impl Parser for MessageParser {
} else if bytes.name().0 == b"body" { } else if bytes.name().0 == b"body" {
Continuation::Continue(InBody(state).into()) Continuation::Continue(InBody(state).into())
} else { } else {
Continuation::Final(Err(ffail!("Unexpected XML tag"))) Continuation::Final(Err(ffail!("Unexpected XML event: {event:?}")))
} }
} }
Event::End(_) => { Event::End(_) => {

View File

@ -59,18 +59,18 @@ macro_rules! delegate_parsing {
} }
macro_rules! match_parser { macro_rules! match_parser {
($outer: ident, $name: expr, $ns: expr, $event: expr; $subtype: ty) => { ($outer: ident, $name: expr, $ns: expr, $event: expr; $subtype: ty, $fin: block) => {
if $name.0 == <$subtype as FromXmlTag>::NAME.as_bytes() && $ns == ResolveResult::Bound(Namespace(<$subtype as FromXmlTag>::NS.as_bytes())) { if $name.0 == <$subtype as FromXmlTag>::NAME.as_bytes() && $ns == ResolveResult::Bound(Namespace(<$subtype as FromXmlTag>::NS.as_bytes())) {
$outer(<$subtype as FromXml>::parse().into()).consume($ns, $event) $outer(<$subtype as FromXml>::parse().into()).consume($ns, $event)
} else { } else {
Continuation::Final(Err(ffail!("Unexpected XML event of name {:?} in namespace {:?}", $name, $ns))) $fin
} }
}; };
($outer: ident, $name: expr, $ns: expr, $event: expr; $subtype: ty, $($rest: ty),+) => { ($outer: ident, $name: expr, $ns: expr, $event: expr; $subtype: ty, $($rest: ty),+, $fin: block) => {
if $name.0 == <$subtype as FromXmlTag>::NAME.as_bytes() && $ns == ResolveResult::Bound(Namespace(<$subtype as FromXmlTag>::NS.as_bytes())) { if $name.0 == <$subtype as FromXmlTag>::NAME.as_bytes() && $ns == ResolveResult::Bound(Namespace(<$subtype as FromXmlTag>::NS.as_bytes())) {
$outer(<$subtype as FromXml>::parse().into()).consume($ns, $event) $outer(<$subtype as FromXml>::parse().into()).consume($ns, $event)
} else { } else {
match_parser!($outer, $name, $ns, $event; $($rest),*) match_parser!($outer, $name, $ns, $event; $($rest),*, $fin)
} }
}; };
} }

View File

@ -43,7 +43,7 @@ impl Parser for IgnoreParser {
) )
} }
} }
_ => Continuation::Final(Ok(Ignore)), _ => Continuation::Continue(IgnoreParserInner::InTag { name, depth }.into()),
}, },
} }
} }