Hi,
I am contacting you today to let you know I have found cross-site scripting vectors within the latest version of the RadEditor. I have attached images of the payloads that seem to bypass the XSS filter.
The second payload only works on Firefox browsers, but the first works on Chrome browsers too. While it still requires users to click on the link to trigger XSS, it can be easily social engineered in most situations.
DefaultFilters,StripCssExpressions,StripDomEventAttributes,RemoveScripts
"Hi Sullivanst,
Thank you for pointing this out, the old check indeed had this flaw. I have updated the code so it first makes the attribute lower case and then searches with indexOf:
if (attr && attr.toLowerCase().indexOf("javascript") > -1) {
Regards,
Peter Milchev
Progress Telerik
Virtual Classroom, the free self-paced technical training that gets you up to speed with Telerik and Kendo UI products quickly just got a fresh new look + new and improved content including a brand new Blazor course! Check it out at https://learn.telerik.com/.
Hello Andrew,
Thank you for bringing up this case, it indeed is not sanitized by the DOM or events sanitizers. The same issue is observed also with the <animate> tag in the SVG as well:
For the time being, you can alleviate the issue by using a custom filter client-side and manually sanitizing the content on the server-side:
Here is a sample implementation of the client-side filter:
<script type="text/javascript">
function OnClientLoad(editor, args) {
editor.get_filtersManager().add(new MyCustomSVGFilter());
}
function MyCustomSVGFilter() {
MyCustomSVGFilter.initializeBase(this);
this.set_isDom(true);
this.set_enabled(true);
this.set_name("MyCustomSVGFilter");
this.set_description("Strips set, animate and brute attributes that contain 'javascript:' as value");
}
MyCustomSVGFilter.prototype = {
encodeScripts: function (contentToEncode) {
var list = contentToEncode.getElementsByTagName("set");
for (let item of list) {
var attr = item.getAttribute("to");
if (attr && attr.toLowerCase().indexOf("javascript") > -1) {
item.removeAttribute("to");
}
}
list = contentToEncode.getElementsByTagName("animate");
for (let item of list) {
var attr = item.getAttribute("to");
if (attr && attr.toLowerCase().indexOf("javascript") > -1) {
item.removeAttribute("to");
}
}
list = contentToEncode.getElementsByTagName("brute");
for (let item of list) {
var attr = item.getAttribute("href");
if (attr && attr.toLowerCase().indexOf("javascript") > -1) {
item.removeAttribute("href");
}
}
return contentToEncode;
},
getDesignContent: function (content) {
return this.encodeScripts(content);
},
// The code below is the same because it needs to be applied when switching to HTML mode and also when content is submitted.
getHtmlContent: function (content) {
return this.encodeScripts(content);
}
}
MyCustomSVGFilter.registerClass('MyCustomSVGFilterFilter', Telerik.Web.UI.Editor.Filter);
</script>
As a small token of gratitude for helping us identify this, we have updated your Telerik points.
Regards,
Peter Milchev
Progress Telerik
Virtual Classroom, the free self-paced technical training that gets you up to speed with Telerik and Kendo UI products quickly just got a fresh new look + new and improved content including a brand new Blazor course! Check it out at https://learn.telerik.com/.