File v3-1-2-log-pollution-1.patch of Package cobbler

From 7a3c263713ced83a1ac6e1dd8197b5ebd35f9c98 Mon Sep 17 00:00:00 2001
From: Enno Gotthold <egotthold@suse.de>
Date: Wed, 19 Jan 2022 15:04:02 +0100
Subject: [PATCH] Security: Validate the data before logging it

This is required so that we don't create an opportunity for log file
pollution.

Scenario is the following: You issue an arbitrary HTTP request that
a system has finished installing. For this you don't need to be
authenticated and any valid str would be passed to the pre & post
install triggers. The validation now introduced will secure the
triggers.

(cherry picked from commit e06e704c2c11303c8c3bedcb3fdf9a9eed4a0b0d)
---
 cobbler/modules/installation/post_log.py | 25 ++++++++++++++++++++----
 cobbler/modules/installation/pre_log.py  | 16 ++++++++++++---
 2 files changed, 34 insertions(+), 7 deletions(-)

diff --git a/cobbler/modules/installation/post_log.py b/cobbler/modules/installation/post_log.py
index 707361bd..af5228d4 100644
--- a/cobbler/modules/installation/post_log.py
+++ b/cobbler/modules/installation/post_log.py
@@ -21,6 +21,8 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
 
 import time
 
+from cobbler import validate
+
 
 def register():
     """
@@ -33,17 +35,32 @@ def register():
 
 def run(api, args, logger):
     """
+    The method runs the trigger, meaning this logs that an installation has ended.
+
+    The list of args should have three elements:
+        - 0: system or profile
+        - 1: the name of the system or profile
+        - 2: the ip or a "?"
 
     :param api: This parameter is unused currently.
     :param args: An array of three elements. Type (system/profile), name and ip. If no ip is present use a ``?``.
     :param logger: This parameter is unused currently.
     :return: Always 0
     """
-    # FIXME: make everything use the logger, no prints, use util.subprocess_call, etc
+    objtype = args[0]
+    name = args[1]
+    ip = args[2]
+
+    if not validate.validate_obj_type(objtype):
+        return 1
+
+    if not api.find_items(objtype, name=name, return_list=False):
+        return 1
+
+    if not (ip == "?" or validate.ipv4_address(ip) or validate.ipv6_address(ip)):
+        return 1
 
-    objtype = args[0]   # "system" or "profile"
-    name = args[1]      # name of system or profile
-    ip = args[2]        # ip or "?"
+    # FIXME: use the logger
 
     fd = open("/var/log/cobbler/install.log", "a+")
     fd.write("%s\t%s\t%s\tstop\t%s\n" % (objtype, name, ip, time.time()))
diff --git a/cobbler/modules/installation/pre_log.py b/cobbler/modules/installation/pre_log.py
index 7da148d4..c52d85f0 100644
--- a/cobbler/modules/installation/pre_log.py
+++ b/cobbler/modules/installation/pre_log.py
@@ -1,5 +1,7 @@
 import time
 
+from cobbler import validate
+
 
 def register():
     """
@@ -31,10 +33,18 @@ def run(api, args, logger):
     name = args[1]
     ip = args[2]
 
+    if not validate.validate_obj_type(objtype):
+        return 1
+
+    if not api.find_items(objtype, name=name, return_list=False):
+        return 1
+
+    if not (ip == "?" or validate.ipv4_address(ip) or validate.ipv6_address(ip)):
+        return 1
+
     # FIXME: use the logger
 
-    fd = open("/var/log/cobbler/install.log", "a+")
-    fd.write("%s\t%s\t%s\tstart\t%s\n" % (objtype, name, ip, time.time()))
-    fd.close()
+    with open("/var/log/cobbler/install.log", "a+") as fd:
+        fd.write("%s\t%s\t%s\tstart\t%s\n" % (objtype, name, ip, time.time()))
 
     return 0
-- 
2.35.1

openSUSE Build Service is sponsored by