CVE-2023-28606: Improper Neutralization of Input During Web Page Generation ('Cross-site Scripting') (CWE-79)
value: js/event-graph.js in MISP before 2.4.169 allows XSS via event-graph node tooltips.
CWE description: The product does not neutralize or incorrectly neutralizes user-controllable input before it is placed in output that is used as a web page that is served to other users.
CVSS v3 base score: 6.1
Published: 2023-03-18T18:15Z
Repository: https://github.com/MISP/MISP
Language: JavaScript
Files changed: app/webroot/js/event-graph.js
Commit date: 2023-03-10 11:10:42 +0100
Commit message: fix: [security] XSS in event-graph node tooltips

- as reported by Cyber Controls from SIX Group

Diff: diff --git a/app/webroot/js/event-graph.js b/app/webroot/js/event-graph.js
index 150e9b6628b..e025803ae74 100644
--- a/app/webroot/js/event-graph.js
+++ b/app/webroot/js/event-graph.js
@@ -713,11 +713,11 @@ class EventGraph {
             }
 
             if ( node.node_type == 'object' ) {
                 var group =  'object';
                 var label = dataHandler.generate_label(node);
-                var labelHtml = label + '</br><i>' + escapeHtml(node.comment) + '</i>'
+                var labelHtml = escapeHtml(label) + '</br><i>' + escapeHtml(node.comment) + '</i>'
                 label += ' ' + escapeHtml(node.comment)
                 var striped_value = that.strip_text_value(label);
                 node_conf = {
                     id: node.id,
                     uuid: node.uuid,
@@ -740,11 +740,11 @@ class EventGraph {
                 label = node.label;
                 node_conf = {
                     id: node.id,
                     uuid: node.uuid,
                     label: label,
-                    title: label,
+                    title: escapeHtml(label),
                     group: group,
                     mass: 20,
                     color: {
                         background: tag_color,
                         border: tag_color
@@ -764,19 +764,19 @@ class EventGraph {
                 label = that.scope_keyType + ": " + node.label;
                 var striped_value = that.strip_text_value(label);
                 node_conf = {
                     id: node.id,
                     label: striped_value,
-                    title: label,
+                    title: escapeHtml(label),
                     group: group
                 };
                 dataHandler.mapping_value_to_nodeID.set(label, node.id);
             } else {
                 group =  'attribute';
-                label = node.type + ': ' + node.label;
+                label = escapeHtml(node.type) + ': ' + node.label;
                 label += ' ' + escapeHtml(node.comment)
-                var labelHtml = label + '</br><i>' + escapeHtml(node.comment) + '</i>'
+                var labelHtml = escapeHtml(label) + '</br><i>' + escapeHtml(node.comment) + '</i>'
                 var striped_value = that.strip_text_value(label);
                 node_conf = {
                     id: node.id,
                     uuid: node.uuid,
                     event_id: node.event_id,
@@ -1051,11 +1051,11 @@ class EventGraph {
                     var node = {
                         id: attr.uuid,
                         x: parent_pos.x,
                         y: parent_pos.y,
                         label: attr.object_relation + ': ' + striped_value,
-                        title: attr.object_relation + ': ' + attr.value,
+                        title: escapeHtml(attr.object_relation) + ': ' + escapeHtml(attr.value),
                         group: 'obj_relation',
                         color: {
                             background: parent_color
                         },
                         font: {

Vulnerable code:                 var labelHtml = label + '</br><i>' + escapeHtml(node.comment) + '</i>'
                    title: label,
                    title: label,
                label = node.type + ': ' + node.label;
                var labelHtml = label + '</br><i>' + escapeHtml(node.comment) + '</i>'
                        title: attr.object_relation + ': ' + attr.value,
Fixed code:                 var labelHtml = escapeHtml(label) + '</br><i>' + escapeHtml(node.comment) + '</i>'
                    title: escapeHtml(label),
                    title: escapeHtml(label),
                label = escapeHtml(node.type) + ': ' + node.label;
                var labelHtml = escapeHtml(label) + '</br><i>' + escapeHtml(node.comment) + '</i>'
                        title: escapeHtml(attr.object_relation) + ': ' + escapeHtml(attr.value),