25
1
mirror of https://github.com/processone/ejabberd.git synced 2024-11-20 16:15:59 +01:00

Don't auto-decode forwarded payload

This commit is contained in:
Evgeniy Khramtsov 2016-11-13 13:41:04 +03:00
parent 132033d01a
commit 7e9f1a6dc1
8 changed files with 67 additions and 65 deletions

View File

@ -181,7 +181,7 @@
-type starttls_proceed() :: #starttls_proceed{}. -type starttls_proceed() :: #starttls_proceed{}.
-record(forwarded, {delay :: #delay{}, -record(forwarded, {delay :: #delay{},
sub_els = [] :: [xmpp_element() | fxml:xmlel()]}). xml_els = [] :: [fxml:xmlel()]}).
-type forwarded() :: #forwarded{}. -type forwarded() :: #forwarded{}.
-record(privilege, {perms = [] :: [#privilege_perm{}], -record(privilege, {perms = [] :: [#privilege_perm{}],

View File

@ -2679,7 +2679,7 @@
-xml(forwarded, -xml(forwarded,
#elem{name = <<"forwarded">>, #elem{name = <<"forwarded">>,
xmlns = <<"urn:xmpp:forward:0">>, xmlns = <<"urn:xmpp:forward:0">>,
result = {forwarded, '$delay', '$_els'}, result = {forwarded, '$delay', '$_xmls'},
refs = [#ref{name = delay, min = 0, refs = [#ref{name = delay, min = 0,
max = 1, label = '$delay'}]}). max = 1, label = '$delay'}]}).

View File

@ -198,7 +198,7 @@ send_copies(JID, To, Packet, Direction)->
-spec build_forward_packet(jid(), message(), jid(), jid(), direction()) -> message(). -spec build_forward_packet(jid(), message(), jid(), jid(), direction()) -> message().
build_forward_packet(JID, #message{type = T} = Msg, Sender, Dest, Direction) -> build_forward_packet(JID, #message{type = T} = Msg, Sender, Dest, Direction) ->
Forwarded = #forwarded{sub_els = [complete_packet(JID, Msg, Direction)]}, Forwarded = #forwarded{xml_els = [xmpp:encode(complete_packet(JID, Msg, Direction))]},
Carbon = case Direction of Carbon = case Direction of
sent -> #carbons_sent{forwarded = Forwarded}; sent -> #carbons_sent{forwarded = Forwarded};
received -> #carbons_received{forwarded = Forwarded} received -> #carbons_received{forwarded = Forwarded}

View File

@ -217,7 +217,8 @@ process_iq(#iq{to = To, lang = Lang, sub_els = [SubEl]} = IQ, Type) ->
Delegations = get_delegations(LServer), Delegations = get_delegations(LServer),
case dict:find({NS, Type}, Delegations) of case dict:find({NS, Type}, Delegations) of
{ok, {Host, _}} -> {ok, {Host, _}} ->
Delegation = #delegation{forwarded = #forwarded{sub_els = [IQ]}}, Delegation = #delegation{
forwarded = #forwarded{xml_els = [xmpp:encode(IQ)]}},
NewFrom = jid:make(LServer), NewFrom = jid:make(LServer),
NewTo = jid:make(Host), NewTo = jid:make(Host),
ejabberd_local:route_iq( ejabberd_local:route_iq(
@ -236,14 +237,15 @@ process_iq(#iq{to = To, lang = Lang, sub_els = [SubEl]} = IQ, Type) ->
-spec process_iq_result(iq(), iq()) -> ok. -spec process_iq_result(iq(), iq()) -> ok.
process_iq_result(#iq{from = From, to = To, id = ID, lang = Lang} = IQ, process_iq_result(#iq{from = From, to = To, id = ID, lang = Lang} = IQ,
#iq{type = result} = ResIQ) -> #iq{type = result} = ResIQ) ->
case xmpp:get_subtag(ResIQ, #delegation{}) of try
#delegation{ #delegation{forwarded = #forwarded{xml_els = [SubEl]}} =
forwarded = #forwarded{ xmpp:get_subtag(ResIQ, #delegation{}),
sub_els = [#iq{from = To, to = From, case xmpp:decode(SubEl, ?NS_CLIENT, [ignore_els]) of
type = Type, id = ID} = Reply]}} #iq{from = To, to = From, type = Type, id = ID} = Reply
when Type == error; Type == result -> when Type == error; Type == result ->
ejabberd_router:route(From, To, Reply); ejabberd_router:route(From, To, Reply)
_ -> end
catch _:_ ->
?ERROR_MSG("got iq-result with invalid delegated " ?ERROR_MSG("got iq-result with invalid delegated "
"payload:~n~s", [xmpp:pp(ResIQ)]), "payload:~n~s", [xmpp:pp(ResIQ)]),
Txt = <<"External component failure">>, Txt = <<"External component failure">>,

View File

@ -794,7 +794,7 @@ msg_to_el(#archive_msg{timestamp = TS, packet = Pkt1, nick = Nick, peer = Peer},
MsgType, JidRequestor, #jid{lserver = LServer} = JidArchive) -> MsgType, JidRequestor, #jid{lserver = LServer} = JidArchive) ->
Pkt2 = maybe_update_from_to(Pkt1, JidRequestor, JidArchive, Peer, MsgType, Pkt2 = maybe_update_from_to(Pkt1, JidRequestor, JidArchive, Peer, MsgType,
Nick), Nick),
#forwarded{sub_els = [Pkt2], #forwarded{xml_els = [xmpp:encode(Pkt2)],
delay = #delay{stamp = TS, from = jid:make(LServer)}}. delay = #delay{stamp = TS, from = jid:make(LServer)}}.
maybe_update_from_to(#xmlel{} = El, JidRequestor, JidArchive, Peer, maybe_update_from_to(#xmlel{} = El, JidRequestor, JidArchive, Peer,

View File

@ -257,25 +257,33 @@ get_permissions(ServerHost) ->
end. end.
forward_message(From, To, Msg) -> forward_message(From, To, Msg) ->
Host = From#jid.lserver,
ServerHost = To#jid.lserver, ServerHost = To#jid.lserver,
Lang = xmpp:get_lang(Msg),
case xmpp:get_subtag(Msg, #privilege{}) of case xmpp:get_subtag(Msg, #privilege{}) of
#privilege{forwarded = #forwarded{sub_els = [#message{} = SubEl]}} -> #privilege{forwarded = #forwarded{xml_els = [SubEl]}} ->
case SubEl#message.from of try xmpp:decode(SubEl, ?NS_CLIENT, [ignore_els]) of
#jid{lresource = <<"">>, lserver = ServerHost} -> #message{} = NewMsg ->
ejabberd_router:route( case NewMsg#message.from of
xmpp:get_from(SubEl), xmpp:get_to(SubEl), SubEl); #jid{lresource = <<"">>, lserver = ServerHost} ->
ejabberd_router:route(
xmpp:get_from(NewMsg), xmpp:get_to(NewMsg), NewMsg);
_ ->
Lang = xmpp:get_lang(Msg),
Txt = <<"Invalid 'from' attribute in forwarded message">>,
Err = xmpp:err_forbidden(Txt, Lang),
ejabberd_router:route_error(To, From, Msg, Err)
end;
_ -> _ ->
Lang = xmpp:get_lang(Msg), Txt = <<"Message not found in forwarded payload">>,
Txt = <<"Invalid 'from' attribute">>, Err = xmpp:err_bad_request(Txt, Lang),
Err = xmpp:err_forbidden(Txt, Lang), ejabberd_router:route_error(To, From, Msg, Err)
catch _:{xmpp_codec, Why} ->
Txt = xmpp:format_error(Why),
Err = xmpp:err_bad_request(Txt, Lang),
ejabberd_router:route_error(To, From, Msg, Err) ejabberd_router:route_error(To, From, Msg, Err)
end; end;
_ -> _ ->
?ERROR_MSG("got invalid forwarded payload from external " Txt = <<"Invalid <forwarded/> element">>,
"component '~s':~n~s", [Host, xmpp:pp(Msg)]),
Lang = xmpp:get_lang(Msg),
Txt = <<"Invalid forwarded payload">>,
Err = xmpp:err_bad_request(Txt, Lang), Err = xmpp:err_bad_request(Txt, Lang),
ejabberd_router:route_error(To, From, Msg, Err) ejabberd_router:route_error(To, From, Msg, Err)
end. end.

View File

@ -6639,7 +6639,7 @@ pp(mam_archived, 2) -> [by, id];
pp(mam_result, 4) -> [xmlns, queryid, id, sub_els]; pp(mam_result, 4) -> [xmlns, queryid, id, sub_els];
pp(mam_prefs, 4) -> [xmlns, default, always, never]; pp(mam_prefs, 4) -> [xmlns, default, always, never];
pp(mam_fin, 5) -> [xmlns, id, rsm, stable, complete]; pp(mam_fin, 5) -> [xmlns, id, rsm, stable, complete];
pp(forwarded, 2) -> [delay, sub_els]; pp(forwarded, 2) -> [delay, xml_els];
pp(carbons_disable, 0) -> []; pp(carbons_disable, 0) -> [];
pp(carbons_enable, 0) -> []; pp(carbons_enable, 0) -> [];
pp(carbons_private, 0) -> []; pp(carbons_private, 0) -> [];
@ -11966,53 +11966,41 @@ encode_carbons_disable({carbons_disable}, __TopXMLNS) ->
decode_forwarded(__TopXMLNS, __IgnoreEls, decode_forwarded(__TopXMLNS, __IgnoreEls,
{xmlel, <<"forwarded">>, _attrs, _els}) -> {xmlel, <<"forwarded">>, _attrs, _els}) ->
{Delay, __Els} = decode_forwarded_els(__TopXMLNS, {Delay, __Xmls} = decode_forwarded_els(__TopXMLNS,
__IgnoreEls, _els, undefined, []), __IgnoreEls, _els, undefined, []),
{forwarded, Delay, __Els}. {forwarded, Delay, __Xmls}.
decode_forwarded_els(__TopXMLNS, __IgnoreEls, [], Delay, decode_forwarded_els(__TopXMLNS, __IgnoreEls, [], Delay,
__Els) -> __Xmls) ->
{Delay, lists:reverse(__Els)}; {Delay, lists:reverse(__Xmls)};
decode_forwarded_els(__TopXMLNS, __IgnoreEls, decode_forwarded_els(__TopXMLNS, __IgnoreEls,
[{xmlel, <<"delay">>, _attrs, _} = _el | _els], Delay, [{xmlel, <<"delay">>, _attrs, _} = _el | _els], Delay,
__Els) -> __Xmls) ->
case get_attr(<<"xmlns">>, _attrs) of case get_attr(<<"xmlns">>, _attrs) of
<<"urn:xmpp:delay">> -> <<"urn:xmpp:delay">> ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els, decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
decode_delay(<<"urn:xmpp:delay">>, __IgnoreEls, decode_delay(<<"urn:xmpp:delay">>, __IgnoreEls,
_el), _el),
__Els); __Xmls);
_ -> _ ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els, decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
Delay, __Els) Delay, __Xmls)
end; end;
decode_forwarded_els(__TopXMLNS, __IgnoreEls, decode_forwarded_els(__TopXMLNS, __IgnoreEls,
[{xmlel, _, _, _} = _el | _els], Delay, __Els) -> [{xmlel, _, _, _} = _el | _els], Delay, __Xmls) ->
if __IgnoreEls ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
Delay, [_el | __Els]);
true ->
case is_known_tag(_el, __TopXMLNS) of
true ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
Delay,
[decode(_el, __TopXMLNS, []) | __Els]);
false ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
Delay, __Els)
end
end;
decode_forwarded_els(__TopXMLNS, __IgnoreEls,
[_ | _els], Delay, __Els) ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els, decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
Delay, __Els). Delay, [_el | __Xmls]);
decode_forwarded_els(__TopXMLNS, __IgnoreEls,
[_ | _els], Delay, __Xmls) ->
decode_forwarded_els(__TopXMLNS, __IgnoreEls, _els,
Delay, __Xmls).
encode_forwarded({forwarded, Delay, __Els}, encode_forwarded({forwarded, Delay, __Xmls},
__TopXMLNS) -> __TopXMLNS) ->
__NewTopXMLNS = __NewTopXMLNS =
choose_top_xmlns(<<"urn:xmpp:forward:0">>, [], choose_top_xmlns(<<"urn:xmpp:forward:0">>, [],
__TopXMLNS), __TopXMLNS),
_els = [encode(_el, __NewTopXMLNS) || _el <- __Els] ++ _els = __Xmls ++
lists:reverse('encode_forwarded_$delay'(Delay, lists:reverse('encode_forwarded_$delay'(Delay,
__NewTopXMLNS, [])), __NewTopXMLNS, [])),
_attrs = enc_xmlns_attrs(__NewTopXMLNS, __TopXMLNS), _attrs = enc_xmlns_attrs(__NewTopXMLNS, __TopXMLNS),

View File

@ -42,16 +42,20 @@ add_delay_info(Stz, From, Time, Desc) ->
-spec unwrap_carbon(stanza()) -> xmpp_element(). -spec unwrap_carbon(stanza()) -> xmpp_element().
unwrap_carbon(#message{} = Msg) -> unwrap_carbon(#message{} = Msg) ->
case xmpp:get_subtag(Msg, #carbons_sent{}) of try
#carbons_sent{forwarded = #forwarded{sub_els = [El]}} -> case xmpp:get_subtag(Msg, #carbons_sent{}) of
El; #carbons_sent{forwarded = #forwarded{xml_els = [El]}} ->
_ -> xmpp:decode(El, ?NS_CLIENT, [ignore_els]);
case xmpp:get_subtag(Msg, #carbons_received{}) of _ ->
#carbons_received{forwarded = #forwarded{sub_els = [El]}} -> case xmpp:get_subtag(Msg, #carbons_received{}) of
El; #carbons_received{forwarded = #forwarded{xml_els = [El]}} ->
_ -> xmpp:decode(El, ?NS_CLIENT, [ignore_els]);
Msg _ ->
end Msg
end
end
catch _:{xmpp_codec, _} ->
Msg
end; end;
unwrap_carbon(Stanza) -> Stanza. unwrap_carbon(Stanza) -> Stanza.