|
|
|
@ -143,11 +143,31 @@ class FederationBase(object): |
|
|
|
|
def callback(_, pdu): |
|
|
|
|
with logcontext.PreserveLoggingContext(ctx): |
|
|
|
|
if not check_event_content_hash(pdu): |
|
|
|
|
logger.warn( |
|
|
|
|
"Event content has been tampered, redacting %s: %s", |
|
|
|
|
pdu.event_id, pdu.get_pdu_json() |
|
|
|
|
) |
|
|
|
|
return prune_event(pdu) |
|
|
|
|
# let's try to distinguish between failures because the event was |
|
|
|
|
# redacted (which are somewhat expected) vs actual ball-tampering |
|
|
|
|
# incidents. |
|
|
|
|
# |
|
|
|
|
# This is just a heuristic, so we just assume that if the keys are |
|
|
|
|
# about the same between the redacted and received events, then the |
|
|
|
|
# received event was probably a redacted copy (but we then use our |
|
|
|
|
# *actual* redacted copy to be on the safe side.) |
|
|
|
|
redacted_event = prune_event(pdu) |
|
|
|
|
if ( |
|
|
|
|
set(six.iterkeys(redacted_event)) == set(six.iterkeys(pdu)) and |
|
|
|
|
set(six.iterkeys(redacted_event.content)) |
|
|
|
|
== set(six.iterkeys(pdu.content)) |
|
|
|
|
): |
|
|
|
|
logger.info( |
|
|
|
|
"Event %s seems to have been redacted; using our redacted " |
|
|
|
|
"copy", |
|
|
|
|
pdu.event_id, |
|
|
|
|
) |
|
|
|
|
else: |
|
|
|
|
logger.warning( |
|
|
|
|
"Event %s content has been tampered, redacting", |
|
|
|
|
pdu.event_id, pdu.get_pdu_json(), |
|
|
|
|
) |
|
|
|
|
return redacted_event |
|
|
|
|
|
|
|
|
|
if self.spam_checker.check_event_for_spam(pdu): |
|
|
|
|
logger.warn( |
|
|
|
@ -162,8 +182,8 @@ class FederationBase(object): |
|
|
|
|
failure.trap(SynapseError) |
|
|
|
|
with logcontext.PreserveLoggingContext(ctx): |
|
|
|
|
logger.warn( |
|
|
|
|
"Signature check failed for %s", |
|
|
|
|
pdu.event_id, |
|
|
|
|
"Signature check failed for %s: %s", |
|
|
|
|
pdu.event_id, failure.getErrorMessage(), |
|
|
|
|
) |
|
|
|
|
return failure |
|
|
|
|
|
|
|
|
|