Compare commits
10 Commits
0a9f96c329
...
ced9701483
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ced9701483 | ||
|
|
9339189fac | ||
|
|
67410e9fb7 | ||
|
|
db6c27149b | ||
|
|
93d95ac335 | ||
|
|
3e1f76e29a | ||
|
|
7261a82362 | ||
|
|
966a0b626e | ||
|
|
83e93cc9aa | ||
|
|
f6c93fa6da |
456
CVE-2023-6378-and-CVE-2023-6481.patch
Normal file
456
CVE-2023-6378-and-CVE-2023-6481.patch
Normal file
@ -0,0 +1,456 @@
|
||||
From bb095154be011267b64e37a1d401546e7cc2b7c3 Mon Sep 17 00:00:00 2001
|
||||
From: Ceki Gulcu <ceki@qos.ch>
|
||||
Date: Fri, 1 Dec 2023 15:12:22 +0100
|
||||
Subject: [PATCH] fix CVE-2023-6378
|
||||
|
||||
Signed-off-by: Ceki Gulcu <ceki@qos.ch>
|
||||
---
|
||||
.../logback/classic/spi/LoggingEventVO.java | 7 ++
|
||||
.../src/test/input/issue/logback-1754.xml | 30 +++++++
|
||||
.../issue/logback_1754/LogbackTest.java | 78 +++++++++++++++++++
|
||||
.../core/net/HardenedObjectInputStream.java | 55 ++++++++++++-
|
||||
.../ch/qos/logback/core/util/EnvUtil.java | 39 ++++++----
|
||||
.../net/HardenedObjectInputStreamTest.java | 49 +++++++++++-
|
||||
.../rolling/ScaffoldingForRollingTests.java | 2 +-
|
||||
.../ch/qos/logback/core/util/EnvUtilTest.java | 34 ++++++++
|
||||
8 files changed, 275 insertions(+), 19 deletions(-)
|
||||
create mode 100644 logback-classic/src/test/input/issue/logback-1754.xml
|
||||
create mode 100644 logback-classic/src/test/java/ch/qos/logback/classic/issue/logback_1754/LogbackTest.java
|
||||
create mode 100644 logback-core/src/test/java/ch/qos/logback/core/util/EnvUtilTest.java
|
||||
|
||||
diff --git a/logback-classic/src/main/java/ch/qos/logback/classic/spi/LoggingEventVO.java b/logback-classic/src/main/java/ch/qos/logback/classic/spi/LoggingEventVO.java
|
||||
index e21350b2cc..ea2c6ac128 100644
|
||||
--- a/logback-classic/src/main/java/ch/qos/logback/classic/spi/LoggingEventVO.java
|
||||
+++ b/logback-classic/src/main/java/ch/qos/logback/classic/spi/LoggingEventVO.java
|
||||
@@ -14,6 +14,7 @@
|
||||
package ch.qos.logback.classic.spi;
|
||||
|
||||
import java.io.IOException;
|
||||
+import java.io.InvalidObjectException;
|
||||
import java.io.ObjectInputStream;
|
||||
import java.io.ObjectOutputStream;
|
||||
import java.io.Serializable;
|
||||
@@ -38,6 +39,7 @@ public class LoggingEventVO implements ILoggingEvent, Serializable {
|
||||
|
||||
private static final int NULL_ARGUMENT_ARRAY = -1;
|
||||
private static final String NULL_ARGUMENT_ARRAY_ELEMENT = "NULL_ARGUMENT_ARRAY_ELEMENT";
|
||||
+ private static final int ARGUMENT_ARRAY_DESERIALIZATION_LIMIT = 128;
|
||||
|
||||
private String threadName;
|
||||
private String loggerName;
|
||||
@@ -181,6 +183,11 @@ private void readObject(ObjectInputStream in) throws IOException, ClassNotFoundE
|
||||
level = Level.toLevel(levelInt);
|
||||
|
||||
int argArrayLen = in.readInt();
|
||||
+ // Prevent DOS attacks via large or negative arrays
|
||||
+ if (argArrayLen < NULL_ARGUMENT_ARRAY || argArrayLen > ARGUMENT_ARRAY_DESERIALIZATION_LIMIT) {
|
||||
+ throw new InvalidObjectException("Argument array length is invalid: " + argArrayLen);
|
||||
+ }
|
||||
+
|
||||
if (argArrayLen != NULL_ARGUMENT_ARRAY) {
|
||||
argumentArray = new String[argArrayLen];
|
||||
for (int i = 0; i < argArrayLen; i++) {
|
||||
diff --git a/logback-classic/src/test/input/issue/logback-1754.xml b/logback-classic/src/test/input/issue/logback-1754.xml
|
||||
new file mode 100644
|
||||
index 0000000000..ab41185a34
|
||||
--- /dev/null
|
||||
+++ b/logback-classic/src/test/input/issue/logback-1754.xml
|
||||
@@ -0,0 +1,30 @@
|
||||
+<?xml version="1.0" encoding="UTF-8"?>
|
||||
+<!--
|
||||
+ ~ Logback: the reliable, generic, fast and flexible logging framework.
|
||||
+ ~ Copyright (C) 1999-2023, QOS.ch. All rights reserved.
|
||||
+ ~
|
||||
+ ~ This program and the accompanying materials are dual-licensed under
|
||||
+ ~ either the terms of the Eclipse Public License v1.0 as published by
|
||||
+ ~ the Eclipse Foundation
|
||||
+ ~
|
||||
+ ~ or (per the licensee's choosing)
|
||||
+ ~
|
||||
+ ~ under the terms of the GNU Lesser General Public License version 2.1
|
||||
+ ~ as published by the Free Software Foundation.
|
||||
+ -->
|
||||
+
|
||||
+<configuration debug="true">
|
||||
+ <appender name="GENERAL" class="ch.qos.logback.core.rolling.RollingFileAppender">
|
||||
+ <rollingPolicy class="ch.qos.logback.core.rolling.TimeBasedRollingPolicy">
|
||||
+ <fileNamePattern>${logback_1754_targetDirectory}/test-%d{yyyy-MM-dd}.log</fileNamePattern>
|
||||
+ <maxHistory>120</maxHistory>
|
||||
+ </rollingPolicy>
|
||||
+ <encoder>
|
||||
+ <pattern>%date{HH:mm:ss.SSS} [%level] %logger{0} [%thread] [%class{3}:%line] : %msg%n</pattern>
|
||||
+ </encoder>
|
||||
+ <prudent>true</prudent>
|
||||
+ </appender>
|
||||
+ <root level="debug">
|
||||
+ <appender-ref ref="GENERAL" />
|
||||
+ </root>
|
||||
+</configuration>
|
||||
\ No newline at end of file
|
||||
diff --git a/logback-classic/src/test/java/ch/qos/logback/classic/issue/logback_1754/LogbackTest.java b/logback-classic/src/test/java/ch/qos/logback/classic/issue/logback_1754/LogbackTest.java
|
||||
new file mode 100644
|
||||
index 0000000000..3001c00a66
|
||||
--- /dev/null
|
||||
+++ b/logback-classic/src/test/java/ch/qos/logback/classic/issue/logback_1754/LogbackTest.java
|
||||
@@ -0,0 +1,78 @@
|
||||
+/*
|
||||
+ * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
+ * Copyright (C) 1999-2023, QOS.ch. All rights reserved.
|
||||
+ *
|
||||
+ * This program and the accompanying materials are dual-licensed under
|
||||
+ * either the terms of the Eclipse Public License v1.0 as published by
|
||||
+ * the Eclipse Foundation
|
||||
+ *
|
||||
+ * or (per the licensee's choosing)
|
||||
+ *
|
||||
+ * under the terms of the GNU Lesser General Public License version 2.1
|
||||
+ * as published by the Free Software Foundation.
|
||||
+ */
|
||||
+
|
||||
+package ch.qos.logback.classic.issue.logback_1754;
|
||||
+
|
||||
+import ch.qos.logback.classic.ClassicConstants;
|
||||
+import ch.qos.logback.classic.ClassicTestConstants;
|
||||
+import ch.qos.logback.core.testUtil.RandomUtil;
|
||||
+import org.slf4j.Logger;
|
||||
+import org.slf4j.LoggerFactory;
|
||||
+
|
||||
+import java.util.ArrayList;
|
||||
+import java.util.List;
|
||||
+import java.util.concurrent.CountDownLatch;
|
||||
+
|
||||
+import static ch.qos.logback.classic.util.ContextInitializer.CONFIG_FILE_PROPERTY;
|
||||
+
|
||||
+public class LogbackTest {
|
||||
+
|
||||
+ private static final int THREADS = 16;
|
||||
+
|
||||
+ private void runTest() {
|
||||
+
|
||||
+ int diff = RandomUtil.getPositiveInt();
|
||||
+ //System.setProperty("logback.statusListenerClass", "sysout");
|
||||
+ System.setProperty(CONFIG_FILE_PROPERTY, ClassicTestConstants.INPUT_PREFIX+"issue/logback-1754.xml");
|
||||
+ System.setProperty("logback_1754_targetDirectory", ClassicTestConstants.OUTPUT_DIR_PREFIX+"safeWrite_"+diff);
|
||||
+
|
||||
+ CountDownLatch latch = new CountDownLatch(THREADS);
|
||||
+ List<Thread> threads = new ArrayList<Thread>(THREADS);
|
||||
+ for (int i = 0; i < THREADS; i++) {
|
||||
+ LoggerThread thread = new LoggerThread(latch, "message from thread " + i);
|
||||
+ thread.start();
|
||||
+ threads.add(thread);
|
||||
+ }
|
||||
+ for (Thread thread : threads) {
|
||||
+ try {
|
||||
+ thread.join();
|
||||
+ } catch (InterruptedException e) {
|
||||
+ Thread.currentThread().interrupt();
|
||||
+ throw new RuntimeException(e);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ public static void main(String... args) {
|
||||
+ new LogbackTest().runTest();
|
||||
+ }
|
||||
+
|
||||
+ private static final class LoggerThread extends Thread {
|
||||
+ private static final Logger LOG = LoggerFactory.getLogger(LoggerThread.class);
|
||||
+ private final CountDownLatch latch;
|
||||
+ private final String message;
|
||||
+
|
||||
+ LoggerThread(CountDownLatch latch, String message) {
|
||||
+ setDaemon(false);
|
||||
+ this.latch = latch;
|
||||
+ this.message = message;
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public void run() {
|
||||
+ latch.countDown();
|
||||
+ LOG.info(message);
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
diff --git a/logback-core/src/main/java/ch/qos/logback/core/net/HardenedObjectInputStream.java b/logback-core/src/main/java/ch/qos/logback/core/net/HardenedObjectInputStream.java
|
||||
index d1b7301ea4..0674aaf3ea 100755
|
||||
--- a/logback-core/src/main/java/ch/qos/logback/core/net/HardenedObjectInputStream.java
|
||||
+++ b/logback-core/src/main/java/ch/qos/logback/core/net/HardenedObjectInputStream.java
|
||||
@@ -1,10 +1,27 @@
|
||||
+/**
|
||||
+ * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
+ * Copyright (C) 1999-2023, QOS.ch. All rights reserved.
|
||||
+ *
|
||||
+ * This program and the accompanying materials are dual-licensed under
|
||||
+ * either the terms of the Eclipse Public License v1.0 as published by
|
||||
+ * the Eclipse Foundation
|
||||
+ *
|
||||
+ * or (per the licensee's choosing)
|
||||
+ *
|
||||
+ * under the terms of the GNU Lesser General Public License version 2.1
|
||||
+ * as published by the Free Software Foundation.
|
||||
+ */
|
||||
package ch.qos.logback.core.net;
|
||||
|
||||
+import ch.qos.logback.core.util.EnvUtil;
|
||||
+
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.InvalidClassException;
|
||||
import java.io.ObjectInputStream;
|
||||
import java.io.ObjectStreamClass;
|
||||
+import java.lang.reflect.InvocationTargetException;
|
||||
+import java.lang.reflect.Method;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
@@ -22,10 +39,12 @@ public class HardenedObjectInputStream extends ObjectInputStream {
|
||||
|
||||
final List<String> whitelistedClassNames;
|
||||
final static String[] JAVA_PACKAGES = new String[] { "java.lang", "java.util" };
|
||||
+ final private static int DEPTH_LIMIT = 16;
|
||||
+ final private static int ARRAY_LIMIT = 10000;
|
||||
|
||||
public HardenedObjectInputStream(InputStream in, String[] whilelist) throws IOException {
|
||||
super(in);
|
||||
-
|
||||
+ initObjectFilter();
|
||||
this.whitelistedClassNames = new ArrayList<String>();
|
||||
if (whilelist != null) {
|
||||
for (int i = 0; i < whilelist.length; i++) {
|
||||
@@ -36,11 +55,43 @@ public HardenedObjectInputStream(InputStream in, String[] whilelist) throws IOEx
|
||||
|
||||
public HardenedObjectInputStream(InputStream in, List<String> whitelist) throws IOException {
|
||||
super(in);
|
||||
-
|
||||
+ initObjectFilter();
|
||||
this.whitelistedClassNames = new ArrayList<String>();
|
||||
this.whitelistedClassNames.addAll(whitelist);
|
||||
}
|
||||
|
||||
+ private void initObjectFilter() {
|
||||
+
|
||||
+ // invoke the following code by reflection
|
||||
+ // this.setObjectInputFilter(ObjectInputFilter.Config.createFilter(
|
||||
+ // "maxarray=" + ARRAY_LIMIT + ";maxdepth=" + DEPTH_LIMIT + ";"
|
||||
+ // ));
|
||||
+ if(EnvUtil.isJDK9OrHigher()) {
|
||||
+ try {
|
||||
+ ClassLoader classLoader = this.getClass().getClassLoader();
|
||||
+
|
||||
+ Class oifClass = classLoader.loadClass("java.io.ObjectInputFilter");
|
||||
+ Class oifConfigClass = classLoader.loadClass("java.io.ObjectInputFilter$Config");
|
||||
+ Method setObjectInputFilterMethod = this.getClass().getMethod("setObjectInputFilter", oifClass);
|
||||
+
|
||||
+ Method createFilterMethod = oifConfigClass.getMethod("createFilter", String.class);
|
||||
+ Object filter = createFilterMethod.invoke(null, "maxarray=" + ARRAY_LIMIT + ";maxdepth=" + DEPTH_LIMIT + ";");
|
||||
+ setObjectInputFilterMethod.invoke(this, filter);
|
||||
+ } catch (ClassNotFoundException e) {
|
||||
+ // this code should be unreachable
|
||||
+ throw new RuntimeException("Failed to initialize object filter", e);
|
||||
+ } catch (InvocationTargetException e) {
|
||||
+ // this code should be unreachable
|
||||
+ throw new RuntimeException("Failed to initialize object filter", e);
|
||||
+ } catch (NoSuchMethodException e) {
|
||||
+ // this code should be unreachable
|
||||
+ throw new RuntimeException("Failed to initialize object filter", e);
|
||||
+ } catch (IllegalAccessException e) {
|
||||
+ // this code should be unreachable
|
||||
+ throw new RuntimeException("Failed to initialize object filter", e);
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
@Override
|
||||
protected Class<?> resolveClass(ObjectStreamClass anObjectStreamClass) throws IOException, ClassNotFoundException {
|
||||
|
||||
diff --git a/logback-core/src/main/java/ch/qos/logback/core/util/EnvUtil.java b/logback-core/src/main/java/ch/qos/logback/core/util/EnvUtil.java
|
||||
index c200a1c984..f3dcd0cfe3 100644
|
||||
--- a/logback-core/src/main/java/ch/qos/logback/core/util/EnvUtil.java
|
||||
+++ b/logback-core/src/main/java/ch/qos/logback/core/util/EnvUtil.java
|
||||
@@ -1,6 +1,6 @@
|
||||
/**
|
||||
* Logback: the reliable, generic, fast and flexible logging framework.
|
||||
- * Copyright (C) 1999-2015, QOS.ch. All rights reserved.
|
||||
+ * Copyright (C) 1999-2023, QOS.ch. All rights reserved.
|
||||
*
|
||||
* This program and the accompanying materials are dual-licensed under
|
||||
* either the terms of the Eclipse Public License v1.0 as published by
|
||||
@@ -22,22 +22,27 @@
|
||||
public class EnvUtil {
|
||||
|
||||
static private boolean isJDK_N_OrHigher(int n) {
|
||||
- List<String> versionList = new ArrayList<String>();
|
||||
- // this code should work at least until JDK 10 (assuming n parameter is
|
||||
- // always 6 or more)
|
||||
- for (int i = 0; i < 5; i++) {
|
||||
- versionList.add("1." + (n + i));
|
||||
- }
|
||||
-
|
||||
- String javaVersion = System.getProperty("java.version");
|
||||
- if (javaVersion == null) {
|
||||
+ String javaVersionStr = System.getProperty("java.version", "");
|
||||
+ if (javaVersionStr.isEmpty())
|
||||
return false;
|
||||
+
|
||||
+ int version = getJDKVersion(javaVersionStr);
|
||||
+ return version > 0 && n <= version;
|
||||
+ }
|
||||
+
|
||||
+ static public int getJDKVersion(String javaVersionStr) {
|
||||
+ int version = 0;
|
||||
+
|
||||
+ for (char ch : javaVersionStr.toCharArray()) {
|
||||
+ if (Character.isDigit(ch)) {
|
||||
+ version = (version * 10) + (ch - 48);
|
||||
+ } else if (version == 1) {
|
||||
+ version = 0;
|
||||
+ } else {
|
||||
+ break;
|
||||
+ }
|
||||
}
|
||||
- for (String v : versionList) {
|
||||
- if (javaVersion.startsWith(v))
|
||||
- return true;
|
||||
- }
|
||||
- return false;
|
||||
+ return version;
|
||||
}
|
||||
|
||||
static public boolean isJDK5() {
|
||||
@@ -52,6 +57,10 @@ static public boolean isJDK7OrHigher() {
|
||||
return isJDK_N_OrHigher(7);
|
||||
}
|
||||
|
||||
+ static public boolean isJDK9OrHigher() {
|
||||
+ return isJDK_N_OrHigher(9);
|
||||
+ }
|
||||
+
|
||||
static public boolean isJaninoAvailable() {
|
||||
ClassLoader classLoader = EnvUtil.class.getClassLoader();
|
||||
try {
|
||||
diff --git a/logback-core/src/test/java/ch/qos/logback/core/net/HardenedObjectInputStreamTest.java b/logback-core/src/test/java/ch/qos/logback/core/net/HardenedObjectInputStreamTest.java
|
||||
index ff4ddc599f..36f7f11b59 100755
|
||||
--- a/logback-core/src/test/java/ch/qos/logback/core/net/HardenedObjectInputStreamTest.java
|
||||
+++ b/logback-core/src/test/java/ch/qos/logback/core/net/HardenedObjectInputStreamTest.java
|
||||
@@ -1,12 +1,17 @@
|
||||
package ch.qos.logback.core.net;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
+import static org.junit.Assert.fail;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.IOException;
|
||||
+import java.io.InvalidClassException;
|
||||
import java.io.ObjectOutputStream;
|
||||
+import java.util.HashSet;
|
||||
+import java.util.Set;
|
||||
|
||||
+import ch.qos.logback.core.util.EnvUtil;
|
||||
import org.junit.After;
|
||||
import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
@@ -54,5 +59,47 @@ private void writeObject(ObjectOutputStream oos, Object o) throws IOException {
|
||||
oos.flush();
|
||||
oos.close();
|
||||
}
|
||||
-
|
||||
+
|
||||
+ @Test
|
||||
+ public void denialOfService() throws ClassNotFoundException, IOException {
|
||||
+
|
||||
+ if(!EnvUtil.isJDK9OrHigher()) {
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ ByteArrayInputStream bis = new ByteArrayInputStream(payload());
|
||||
+ inputStream = new HardenedObjectInputStream(bis, whitelist);
|
||||
+ try {
|
||||
+ inputStream.readObject();
|
||||
+ fail("InvalidClassException expected");
|
||||
+ } catch(InvalidClassException e) {
|
||||
+ }
|
||||
+ finally {
|
||||
+ inputStream.close();
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ private byte[] payload() throws IOException {
|
||||
+ Set root = buildEvilHashset();
|
||||
+ writeObject(oos, root);
|
||||
+ return bos.toByteArray();
|
||||
+ }
|
||||
+
|
||||
+ private Set buildEvilHashset() {
|
||||
+ Set root = new HashSet();
|
||||
+ Set s1 = root;
|
||||
+ Set s2 = new HashSet();
|
||||
+ for (int i = 0; i < 100; i++) {
|
||||
+ Set t1 = new HashSet();
|
||||
+ Set t2 = new HashSet();
|
||||
+ t1.add("foo"); // make it not equal to t2
|
||||
+ s1.add(t1);
|
||||
+ s1.add(t2);
|
||||
+ s2.add(t1);
|
||||
+ s2.add(t2);
|
||||
+ s1 = t1;
|
||||
+ s2 = t2;
|
||||
+ }
|
||||
+ return root;
|
||||
+ }
|
||||
}
|
||||
diff --git a/logback-core/src/test/java/ch/qos/logback/core/rolling/ScaffoldingForRollingTests.java b/logback-core/src/test/java/ch/qos/logback/core/rolling/ScaffoldingForRollingTests.java
|
||||
index 57389be3f7..504b52adc2 100755
|
||||
--- a/logback-core/src/test/java/ch/qos/logback/core/rolling/ScaffoldingForRollingTests.java
|
||||
+++ b/logback-core/src/test/java/ch/qos/logback/core/rolling/ScaffoldingForRollingTests.java
|
||||
@@ -24,10 +24,10 @@
|
||||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
-import java.sql.Date;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Calendar;
|
||||
+import java.util.Date;
|
||||
import java.util.Enumeration;
|
||||
import java.util.List;
|
||||
import java.util.concurrent.Future;
|
||||
diff --git a/logback-core/src/test/java/ch/qos/logback/core/util/EnvUtilTest.java b/logback-core/src/test/java/ch/qos/logback/core/util/EnvUtilTest.java
|
||||
new file mode 100644
|
||||
index 0000000000..2ee4abd42e
|
||||
--- /dev/null
|
||||
+++ b/logback-core/src/test/java/ch/qos/logback/core/util/EnvUtilTest.java
|
||||
@@ -0,0 +1,34 @@
|
||||
+/**
|
||||
+ * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
+ * Copyright (C) 1999-2023, QOS.ch. All rights reserved.
|
||||
+ *
|
||||
+ * This program and the accompanying materials are dual-licensed under
|
||||
+ * either the terms of the Eclipse Public License v1.0 as published by
|
||||
+ * the Eclipse Foundation
|
||||
+ *
|
||||
+ * or (per the licensee's choosing)
|
||||
+ *
|
||||
+ * under the terms of the GNU Lesser General Public License version 2.1
|
||||
+ * as published by the Free Software Foundation.
|
||||
+ */
|
||||
+package ch.qos.logback.core.util;
|
||||
+
|
||||
+import org.junit.Test;
|
||||
+
|
||||
+import static org.junit.Assert.assertEquals;
|
||||
+
|
||||
+public class EnvUtilTest {
|
||||
+
|
||||
+
|
||||
+ @Test
|
||||
+ public void jdkVersion() {
|
||||
+ assertEquals(4, EnvUtil.getJDKVersion("1.4.xx"));
|
||||
+ assertEquals(5, EnvUtil.getJDKVersion("1.5"));
|
||||
+ assertEquals(5, EnvUtil.getJDKVersion("1.5.xx"));
|
||||
+ assertEquals(5, EnvUtil.getJDKVersion("1.5AA"));
|
||||
+ assertEquals(9, EnvUtil.getJDKVersion("9EA"));
|
||||
+ assertEquals(9, EnvUtil.getJDKVersion("9.0.1"));
|
||||
+ assertEquals(18, EnvUtil.getJDKVersion("18.3+xx"));
|
||||
+ assertEquals(21, EnvUtil.getJDKVersion("21.0.1"));
|
||||
+ }
|
||||
+}
|
||||
681
CVE-2024-12798-and-CVE-2024-12801.patch
Normal file
681
CVE-2024-12798-and-CVE-2024-12801.patch
Normal file
@ -0,0 +1,681 @@
|
||||
This security patch addresses the following vulnerabilities:
|
||||
CVE-2024-12801 (bsc#1234743)
|
||||
Server-Side Request Forgery (SSRF) in SaxEventRecorder
|
||||
CVE-2024-12798 (bsc#1234742)
|
||||
ACE vulnerability in JaninoEventEvaluator
|
||||
|
||||
It is based on the following upstream patches:
|
||||
https://github.com/qos-ch/logback/commit/2cb6d520df7592ef1c3a198f1b5df3c10c93e183.patch
|
||||
https://github.com/qos-ch/logback/commit/5f05041cba4c4ac0a62748c5c527a2da48999f2d.patch
|
||||
https://github.com/qos-ch/logback/commit/6ddf91890a4c23e855132c89086ad7e069d81755.patch
|
||||
|
||||
The change addresses the above issues by:
|
||||
- removing SaxEventRecorder and JaninoEventEvaluator
|
||||
- ignoring external DTD files in DOCTYPE to further reduce vulnerability to SSRF attacks
|
||||
--- a/logback-access/src/main/java/ch/qos/logback/access/boolex/JaninoEventEvaluator.java
|
||||
+++ /dev/null
|
||||
@@ -1,84 +0,0 @@
|
||||
-/**
|
||||
- * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
- * Copyright (C) 1999-2015, QOS.ch. All rights reserved.
|
||||
- *
|
||||
- * This program and the accompanying materials are dual-licensed under
|
||||
- * either the terms of the Eclipse Public License v1.0 as published by
|
||||
- * the Eclipse Foundation
|
||||
- *
|
||||
- * or (per the licensee's choosing)
|
||||
- *
|
||||
- * under the terms of the GNU Lesser General Public License version 2.1
|
||||
- * as published by the Free Software Foundation.
|
||||
- */
|
||||
-package ch.qos.logback.access.boolex;
|
||||
-
|
||||
-import java.util.ArrayList;
|
||||
-import java.util.List;
|
||||
-
|
||||
-import ch.qos.logback.access.spi.IAccessEvent;
|
||||
-import ch.qos.logback.core.CoreConstants;
|
||||
-import ch.qos.logback.core.boolex.JaninoEventEvaluatorBase;
|
||||
-import ch.qos.logback.core.boolex.Matcher;
|
||||
-
|
||||
-public class JaninoEventEvaluator extends JaninoEventEvaluatorBase<IAccessEvent> {
|
||||
-
|
||||
- public final static List<String> DEFAULT_PARAM_NAME_LIST = new ArrayList<String>();
|
||||
- public final static List<Class> DEFAULT_PARAM_TYPE_LIST = new ArrayList<Class>();
|
||||
-
|
||||
- static {
|
||||
- DEFAULT_PARAM_NAME_LIST.add("event");
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(IAccessEvent.class);
|
||||
- }
|
||||
-
|
||||
- @Override
|
||||
- protected String getDecoratedExpression() {
|
||||
- String expression = getExpression();
|
||||
- if (!expression.contains("return")) {
|
||||
- expression = "return " + expression + ";";
|
||||
- addInfo("Adding [return] prefix and a semicolon suffix. Expression becomes [" + expression + "]");
|
||||
- addInfo("See also " + CoreConstants.CODES_URL + "#block");
|
||||
- }
|
||||
- return expression;
|
||||
- }
|
||||
-
|
||||
- @Override
|
||||
- protected String[] getParameterNames() {
|
||||
- List<String> fullNameList = new ArrayList<String>();
|
||||
- fullNameList.addAll(DEFAULT_PARAM_NAME_LIST);
|
||||
-
|
||||
- for (int i = 0; i < matcherList.size(); i++) {
|
||||
- Matcher m = (Matcher) matcherList.get(i);
|
||||
- fullNameList.add(m.getName());
|
||||
- }
|
||||
-
|
||||
- return (String[]) fullNameList.toArray(CoreConstants.EMPTY_STRING_ARRAY);
|
||||
- }
|
||||
-
|
||||
- @Override
|
||||
- protected Class[] getParameterTypes() {
|
||||
- List<Class> fullTypeList = new ArrayList<Class>();
|
||||
- fullTypeList.addAll(DEFAULT_PARAM_TYPE_LIST);
|
||||
- for (int i = 0; i < matcherList.size(); i++) {
|
||||
- fullTypeList.add(Matcher.class);
|
||||
- }
|
||||
- return (Class[]) fullTypeList.toArray(CoreConstants.EMPTY_CLASS_ARRAY);
|
||||
- }
|
||||
-
|
||||
- @Override
|
||||
- protected Object[] getParameterValues(IAccessEvent accessEvent) {
|
||||
- final int matcherListSize = matcherList.size();
|
||||
-
|
||||
- int i = 0;
|
||||
- Object[] values = new Object[DEFAULT_PARAM_NAME_LIST.size() + matcherListSize];
|
||||
-
|
||||
- values[i++] = accessEvent;
|
||||
-
|
||||
- for (int j = 0; j < matcherListSize; j++) {
|
||||
- values[i++] = matcherList.get(j);
|
||||
- }
|
||||
-
|
||||
- return values;
|
||||
- }
|
||||
-
|
||||
-}
|
||||
--- a/logback-classic/src/main/java/ch/qos/logback/classic/boolex/JaninoEventEvaluator.java
|
||||
+++ /dev/null
|
||||
@@ -1,152 +0,0 @@
|
||||
-/**
|
||||
- * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
- * Copyright (C) 1999-2015, QOS.ch. All rights reserved.
|
||||
- *
|
||||
- * This program and the accompanying materials are dual-licensed under
|
||||
- * either the terms of the Eclipse Public License v1.0 as published by
|
||||
- * the Eclipse Foundation
|
||||
- *
|
||||
- * or (per the licensee's choosing)
|
||||
- *
|
||||
- * under the terms of the GNU Lesser General Public License version 2.1
|
||||
- * as published by the Free Software Foundation.
|
||||
- */
|
||||
-package ch.qos.logback.classic.boolex;
|
||||
-
|
||||
-import java.util.ArrayList;
|
||||
-import java.util.List;
|
||||
-import java.util.Map;
|
||||
-
|
||||
-import org.slf4j.Marker;
|
||||
-
|
||||
-import ch.qos.logback.classic.Level;
|
||||
-import ch.qos.logback.classic.spi.ILoggingEvent;
|
||||
-import ch.qos.logback.classic.spi.IThrowableProxy;
|
||||
-import ch.qos.logback.classic.spi.LoggerContextVO;
|
||||
-import ch.qos.logback.classic.spi.ThrowableProxy;
|
||||
-import ch.qos.logback.core.CoreConstants;
|
||||
-import ch.qos.logback.core.boolex.JaninoEventEvaluatorBase;
|
||||
-import ch.qos.logback.core.boolex.Matcher;
|
||||
-
|
||||
-public class JaninoEventEvaluator extends JaninoEventEvaluatorBase<ILoggingEvent> {
|
||||
-
|
||||
- public final static String IMPORT_LEVEL = "import ch.qos.logback.classic.Level;\r\n";
|
||||
-
|
||||
- public final static List<String> DEFAULT_PARAM_NAME_LIST = new ArrayList<String>();
|
||||
- public final static List<Class> DEFAULT_PARAM_TYPE_LIST = new ArrayList<Class>();
|
||||
-
|
||||
- static {
|
||||
- DEFAULT_PARAM_NAME_LIST.add("DEBUG");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("INFO");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("WARN");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("ERROR");
|
||||
-
|
||||
- DEFAULT_PARAM_NAME_LIST.add("event");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("message");
|
||||
-
|
||||
- DEFAULT_PARAM_NAME_LIST.add("formattedMessage");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("logger");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("loggerContext");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("level");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("timeStamp");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("marker");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("mdc");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("throwableProxy");
|
||||
- DEFAULT_PARAM_NAME_LIST.add("throwable");
|
||||
-
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(int.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(int.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(int.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(int.class);
|
||||
-
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(ILoggingEvent.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(String.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(String.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(String.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(LoggerContextVO.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(int.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(long.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(Marker.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(Map.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(IThrowableProxy.class);
|
||||
- DEFAULT_PARAM_TYPE_LIST.add(Throwable.class);
|
||||
- }
|
||||
-
|
||||
- protected String getDecoratedExpression() {
|
||||
- String expression = getExpression();
|
||||
- if (!expression.contains("return")) {
|
||||
- expression = "return " + expression + ";";
|
||||
- addInfo("Adding [return] prefix and a semicolon suffix. Expression becomes [" + expression + "]");
|
||||
- addInfo("See also " + CoreConstants.CODES_URL + "#block");
|
||||
-
|
||||
- }
|
||||
- return IMPORT_LEVEL + expression;
|
||||
- }
|
||||
-
|
||||
- protected String[] getParameterNames() {
|
||||
- List<String> fullNameList = new ArrayList<String>();
|
||||
- fullNameList.addAll(DEFAULT_PARAM_NAME_LIST);
|
||||
-
|
||||
- for (int i = 0; i < matcherList.size(); i++) {
|
||||
- Matcher m = (Matcher) matcherList.get(i);
|
||||
- fullNameList.add(m.getName());
|
||||
- }
|
||||
-
|
||||
- return (String[]) fullNameList.toArray(CoreConstants.EMPTY_STRING_ARRAY);
|
||||
- }
|
||||
-
|
||||
- protected Class[] getParameterTypes() {
|
||||
- List<Class> fullTypeList = new ArrayList<Class>();
|
||||
- fullTypeList.addAll(DEFAULT_PARAM_TYPE_LIST);
|
||||
- for (int i = 0; i < matcherList.size(); i++) {
|
||||
- fullTypeList.add(Matcher.class);
|
||||
- }
|
||||
- return (Class[]) fullTypeList.toArray(CoreConstants.EMPTY_CLASS_ARRAY);
|
||||
- }
|
||||
-
|
||||
- protected Object[] getParameterValues(ILoggingEvent loggingEvent) {
|
||||
- final int matcherListSize = matcherList.size();
|
||||
-
|
||||
- int i = 0;
|
||||
- Object[] values = new Object[DEFAULT_PARAM_NAME_LIST.size() + matcherListSize];
|
||||
-
|
||||
- values[i++] = Level.DEBUG_INTEGER;
|
||||
- values[i++] = Level.INFO_INTEGER;
|
||||
- values[i++] = Level.WARN_INTEGER;
|
||||
- values[i++] = Level.ERROR_INTEGER;
|
||||
-
|
||||
- values[i++] = loggingEvent;
|
||||
- values[i++] = loggingEvent.getMessage();
|
||||
- values[i++] = loggingEvent.getFormattedMessage();
|
||||
- values[i++] = loggingEvent.getLoggerName();
|
||||
- values[i++] = loggingEvent.getLoggerContextVO();
|
||||
- values[i++] = loggingEvent.getLevel().toInteger();
|
||||
- values[i++] = loggingEvent.getTimeStamp();
|
||||
- // In order to avoid NullPointerException, we could push a dummy marker if
|
||||
- // the event's marker is null. However, this would surprise user who
|
||||
- // expect to see a null marker instead of a dummy one.
|
||||
- values[i++] = loggingEvent.getMarker();
|
||||
- values[i++] = loggingEvent.getMDCPropertyMap();
|
||||
-
|
||||
- IThrowableProxy iThrowableProxy = loggingEvent.getThrowableProxy();
|
||||
-
|
||||
- if (iThrowableProxy != null) {
|
||||
- values[i++] = iThrowableProxy;
|
||||
- if (iThrowableProxy instanceof ThrowableProxy) {
|
||||
- values[i++] = ((ThrowableProxy) iThrowableProxy).getThrowable();
|
||||
- } else {
|
||||
- values[i++] = null;
|
||||
- }
|
||||
- } else {
|
||||
- values[i++] = null;
|
||||
- values[i++] = null;
|
||||
- }
|
||||
-
|
||||
- for (int j = 0; j < matcherListSize; j++) {
|
||||
- values[i++] = (Matcher) matcherList.get(j);
|
||||
- }
|
||||
-
|
||||
- return values;
|
||||
- }
|
||||
-
|
||||
-}
|
||||
--- a/logback-classic/src/main/java/ch/qos/logback/classic/util/DefaultNestedComponentRules.java
|
||||
+++ b/logback-classic/src/main/java/ch/qos/logback/classic/util/DefaultNestedComponentRules.java
|
||||
@@ -14,7 +14,6 @@
|
||||
package ch.qos.logback.classic.util;
|
||||
|
||||
import ch.qos.logback.classic.PatternLayout;
|
||||
-import ch.qos.logback.classic.boolex.JaninoEventEvaluator;
|
||||
import ch.qos.logback.classic.encoder.PatternLayoutEncoder;
|
||||
import ch.qos.logback.core.AppenderBase;
|
||||
import ch.qos.logback.core.UnsynchronizedAppenderBase;
|
||||
@@ -38,8 +37,6 @@ public class DefaultNestedComponentRules
|
||||
registry.add(AppenderBase.class, "encoder", PatternLayoutEncoder.class);
|
||||
registry.add(UnsynchronizedAppenderBase.class, "encoder", PatternLayoutEncoder.class);
|
||||
|
||||
- registry.add(EvaluatorFilter.class, "evaluator", JaninoEventEvaluator.class);
|
||||
-
|
||||
SSLNestedComponentRegistryRules.addDefaultNestedComponentRegistryRules(registry);
|
||||
}
|
||||
|
||||
--- /dev/null
|
||||
+++ b/logback-core-blackbox/src/test/blackboxInput/joran/conditional/ifWithExec.xml
|
||||
@@ -0,0 +1,28 @@
|
||||
+<?xml version="1.0" encoding="UTF-8" ?>
|
||||
+
|
||||
+<!--
|
||||
+ ~ Logback: the reliable, generic, fast and flexible logging framework.
|
||||
+ ~ Copyright (C) 1999-2024, QOS.ch. All rights reserved.
|
||||
+ ~
|
||||
+ ~ This program and the accompanying materials are dual-licensed under
|
||||
+ ~ either the terms of the Eclipse Public License v1.0 as published by
|
||||
+ ~ the Eclipse Foundation
|
||||
+ ~
|
||||
+ ~ or (per the licensee's choosing)
|
||||
+ ~
|
||||
+ ~ under the terms of the GNU Lesser General Public License version 2.1
|
||||
+ ~ as published by the Free Software Foundation.
|
||||
+ -->
|
||||
+
|
||||
+<x>
|
||||
+ <stack name="BEGIN"/>
|
||||
+ <if condition='java.lang.Runtime.getRuntime().exec("c:/Windows/System32/calc.exe") == null'>
|
||||
+ <then>
|
||||
+ <stack name="a"/>
|
||||
+ </then>
|
||||
+ <else>
|
||||
+ <stack name="b"/>
|
||||
+ </else>
|
||||
+ </if>
|
||||
+ <stack name="END"/>
|
||||
+</x>
|
||||
--- a/logback-core/src/main/java/ch/qos/logback/core/boolex/JaninoEventEvaluatorBase.java
|
||||
+++ /dev/null
|
||||
@@ -1,95 +0,0 @@
|
||||
-/**
|
||||
- * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
- * Copyright (C) 1999-2015, QOS.ch. All rights reserved.
|
||||
- *
|
||||
- * This program and the accompanying materials are dual-licensed under
|
||||
- * either the terms of the Eclipse Public License v1.0 as published by
|
||||
- * the Eclipse Foundation
|
||||
- *
|
||||
- * or (per the licensee's choosing)
|
||||
- *
|
||||
- * under the terms of the GNU Lesser General Public License version 2.1
|
||||
- * as published by the Free Software Foundation.
|
||||
- */
|
||||
-package ch.qos.logback.core.boolex;
|
||||
-
|
||||
-import java.util.ArrayList;
|
||||
-import java.util.List;
|
||||
-
|
||||
-import org.codehaus.janino.ScriptEvaluator;
|
||||
-
|
||||
-/**
|
||||
- * Abstract class which sets the groundwork for janino based evaluations.
|
||||
- *
|
||||
- * @author Ceki Gülcü
|
||||
- *
|
||||
- * @param <E>
|
||||
- */
|
||||
-abstract public class JaninoEventEvaluatorBase<E> extends EventEvaluatorBase<E> {
|
||||
-
|
||||
- static Class<?> EXPRESSION_TYPE = boolean.class;
|
||||
- static Class<?>[] THROWN_EXCEPTIONS = new Class[1];
|
||||
-
|
||||
- static public final int ERROR_THRESHOLD = 4;
|
||||
- static {
|
||||
- THROWN_EXCEPTIONS[0] = EvaluationException.class;
|
||||
- }
|
||||
-
|
||||
- private String expression;
|
||||
-
|
||||
- ScriptEvaluator scriptEvaluator;
|
||||
- private int errorCount = 0;
|
||||
-
|
||||
- abstract protected String getDecoratedExpression();
|
||||
-
|
||||
- abstract protected String[] getParameterNames();
|
||||
-
|
||||
- abstract protected Class<?>[] getParameterTypes();
|
||||
-
|
||||
- abstract protected Object[] getParameterValues(E event);
|
||||
-
|
||||
- protected List<Matcher> matcherList = new ArrayList<Matcher>();
|
||||
-
|
||||
- @Override
|
||||
- public void start() {
|
||||
- try {
|
||||
- assert context != null;
|
||||
- scriptEvaluator = new ScriptEvaluator(getDecoratedExpression(), EXPRESSION_TYPE, getParameterNames(), getParameterTypes(), THROWN_EXCEPTIONS);
|
||||
- super.start();
|
||||
- } catch (Exception e) {
|
||||
- addError("Could not start evaluator with expression [" + expression + "]", e);
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- public boolean evaluate(E event) throws EvaluationException {
|
||||
- if (!isStarted()) {
|
||||
- throw new IllegalStateException("Evaluator [" + name + "] was called in stopped state");
|
||||
- }
|
||||
- try {
|
||||
- Boolean result = (Boolean) scriptEvaluator.evaluate(getParameterValues(event));
|
||||
- return result.booleanValue();
|
||||
- } catch (Exception ex) {
|
||||
- errorCount++;
|
||||
- if (errorCount >= ERROR_THRESHOLD) {
|
||||
- stop();
|
||||
- }
|
||||
- throw new EvaluationException("Evaluator [" + name + "] caused an exception", ex);
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- public String getExpression() {
|
||||
- return expression;
|
||||
- }
|
||||
-
|
||||
- public void setExpression(String expression) {
|
||||
- this.expression = expression;
|
||||
- }
|
||||
-
|
||||
- public void addMatcher(Matcher matcher) {
|
||||
- matcherList.add(matcher);
|
||||
- }
|
||||
-
|
||||
- public List<Matcher> getMatcherList() {
|
||||
- return matcherList;
|
||||
- }
|
||||
-}
|
||||
--- a/logback-core/src/main/java/ch/qos/logback/core/joran/event/SaxEventRecorder.java
|
||||
+++ b/logback-core/src/main/java/ch/qos/logback/core/joran/event/SaxEventRecorder.java
|
||||
@@ -15,6 +15,7 @@ package ch.qos.logback.core.joran.event;
|
||||
|
||||
import static ch.qos.logback.core.CoreConstants.XML_PARSING;
|
||||
|
||||
+import java.io.ByteArrayInputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.util.ArrayList;
|
||||
@@ -45,6 +46,26 @@ public class SaxEventRecorder extends De
|
||||
cai = new ContextAwareImpl(context, this);
|
||||
}
|
||||
|
||||
+ /**
|
||||
+ * An implementation which disallows external DTDs
|
||||
+ *
|
||||
+ * @param publicId The public identifier, or null if none is
|
||||
+ * available.
|
||||
+ * @param systemId The system identifier provided in the XML
|
||||
+ * document.
|
||||
+ * @return
|
||||
+ * @throws SAXException
|
||||
+ * @throws IOException
|
||||
+ * @since 1.5.13
|
||||
+ */
|
||||
+ @Override
|
||||
+ public InputSource resolveEntity(String publicId, String systemId) throws SAXException, IOException {
|
||||
+ addWarn("Document Type Declaration (DOCTYPE) with external file reference is");
|
||||
+ addWarn("disallowed to prevent Server-Side Request Forgery (SSRF) attacks.");
|
||||
+ addWarn("returning contents of SYSTEM " +systemId+ " as a white space");
|
||||
+ return new InputSource(new ByteArrayInputStream(" ".getBytes()));
|
||||
+ }
|
||||
+
|
||||
public List<SaxEvent> saxEventList = new ArrayList<SaxEvent>();
|
||||
Locator locator;
|
||||
ElementPath globalElementPath = new ElementPath();
|
||||
@@ -102,7 +123,6 @@ public class SaxEventRecorder extends De
|
||||
}
|
||||
|
||||
public void startElement(String namespaceURI, String localName, String qName, Attributes atts) {
|
||||
-
|
||||
String tagName = getTagName(localName, qName);
|
||||
globalElementPath.push(tagName);
|
||||
ElementPath current = globalElementPath.duplicate();
|
||||
--- a/logback-core/src/main/java/ch/qos/logback/core/joran/event/stax/StaxEventRecorder.java
|
||||
+++ /dev/null
|
||||
@@ -1,116 +0,0 @@
|
||||
-/**
|
||||
- * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
- * Copyright (C) 1999-2015, QOS.ch. All rights reserved.
|
||||
- *
|
||||
- * This program and the accompanying materials are dual-licensed under
|
||||
- * either the terms of the Eclipse Public License v1.0 as published by
|
||||
- * the Eclipse Foundation
|
||||
- *
|
||||
- * or (per the licensee's choosing)
|
||||
- *
|
||||
- * under the terms of the GNU Lesser General Public License version 2.1
|
||||
- * as published by the Free Software Foundation.
|
||||
- */
|
||||
-package ch.qos.logback.core.joran.event.stax;
|
||||
-
|
||||
-import ch.qos.logback.core.Context;
|
||||
-import ch.qos.logback.core.joran.spi.ElementPath;
|
||||
-import ch.qos.logback.core.joran.spi.JoranException;
|
||||
-import ch.qos.logback.core.spi.ContextAwareBase;
|
||||
-
|
||||
-import javax.xml.stream.XMLEventReader;
|
||||
-import javax.xml.stream.XMLInputFactory;
|
||||
-import javax.xml.stream.XMLStreamException;
|
||||
-import javax.xml.stream.events.Characters;
|
||||
-import javax.xml.stream.events.EndElement;
|
||||
-import javax.xml.stream.events.StartElement;
|
||||
-import javax.xml.stream.events.XMLEvent;
|
||||
-import java.io.InputStream;
|
||||
-import java.util.ArrayList;
|
||||
-import java.util.List;
|
||||
-
|
||||
-public class StaxEventRecorder extends ContextAwareBase {
|
||||
-
|
||||
- List<StaxEvent> eventList = new ArrayList<StaxEvent>();
|
||||
- ElementPath globalElementPath = new ElementPath();
|
||||
-
|
||||
- public StaxEventRecorder(Context context) {
|
||||
- setContext(context);
|
||||
- }
|
||||
-
|
||||
- public void recordEvents(InputStream inputStream) throws JoranException {
|
||||
- try {
|
||||
- XMLEventReader xmlEventReader = XMLInputFactory.newInstance().createXMLEventReader(inputStream);
|
||||
- read(xmlEventReader);
|
||||
- } catch (XMLStreamException e) {
|
||||
- throw new JoranException("Problem parsing XML document. See previously reported errors.", e);
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- public List<StaxEvent> getEventList() {
|
||||
- return eventList;
|
||||
- }
|
||||
-
|
||||
- private void read(XMLEventReader xmlEventReader) throws XMLStreamException {
|
||||
- while (xmlEventReader.hasNext()) {
|
||||
- XMLEvent xmlEvent = xmlEventReader.nextEvent();
|
||||
- switch (xmlEvent.getEventType()) {
|
||||
- case XMLEvent.START_ELEMENT:
|
||||
- addStartElement(xmlEvent);
|
||||
- break;
|
||||
- case XMLEvent.CHARACTERS:
|
||||
- addCharacters(xmlEvent);
|
||||
- break;
|
||||
- case XMLEvent.END_ELEMENT:
|
||||
- addEndEvent(xmlEvent);
|
||||
- break;
|
||||
- default:
|
||||
- break;
|
||||
- }
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- private void addStartElement(XMLEvent xmlEvent) {
|
||||
- StartElement se = xmlEvent.asStartElement();
|
||||
- String tagName = se.getName().getLocalPart();
|
||||
- globalElementPath.push(tagName);
|
||||
- ElementPath current = globalElementPath.duplicate();
|
||||
- StartEvent startEvent = new StartEvent(current, tagName, se.getAttributes(), se.getLocation());
|
||||
- eventList.add(startEvent);
|
||||
- }
|
||||
-
|
||||
- private void addCharacters(XMLEvent xmlEvent) {
|
||||
- Characters characters = xmlEvent.asCharacters();
|
||||
- StaxEvent lastEvent = getLastEvent();
|
||||
-
|
||||
- if (lastEvent instanceof BodyEvent) {
|
||||
- BodyEvent be = (BodyEvent) lastEvent;
|
||||
- be.append(characters.getData());
|
||||
- } else {
|
||||
- // ignore space only text if the previous event is not a BodyEvent
|
||||
- if (!characters.isWhiteSpace()) {
|
||||
- BodyEvent bodyEvent = new BodyEvent(characters.getData(), xmlEvent.getLocation());
|
||||
- eventList.add(bodyEvent);
|
||||
- }
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- private void addEndEvent(XMLEvent xmlEvent) {
|
||||
- EndElement ee = xmlEvent.asEndElement();
|
||||
- String tagName = ee.getName().getLocalPart();
|
||||
- EndEvent endEvent = new EndEvent(tagName, ee.getLocation());
|
||||
- eventList.add(endEvent);
|
||||
- globalElementPath.pop();
|
||||
- }
|
||||
-
|
||||
- StaxEvent getLastEvent() {
|
||||
- if (eventList.isEmpty()) {
|
||||
- return null;
|
||||
- }
|
||||
- int size = eventList.size();
|
||||
- if (size == 0)
|
||||
- return null;
|
||||
- return eventList.get(size - 1);
|
||||
- }
|
||||
-
|
||||
-}
|
||||
--- a/logback-core/src/main/java/ch/qos/logback/core/net/ssl/SSLParametersConfiguration.java
|
||||
+++ b/logback-core/src/main/java/ch/qos/logback/core/net/ssl/SSLParametersConfiguration.java
|
||||
@@ -19,8 +19,6 @@ import java.util.List;
|
||||
|
||||
import javax.net.ssl.SSLEngine;
|
||||
|
||||
-import org.codehaus.janino.Java;
|
||||
-
|
||||
import ch.qos.logback.core.spi.ContextAwareBase;
|
||||
import ch.qos.logback.core.util.OptionHelper;
|
||||
import ch.qos.logback.core.util.StringCollectionUtil;
|
||||
--- /dev/null
|
||||
+++ b/logback-core/src/test/input/joran/event-ssrf.xml
|
||||
@@ -0,0 +1,27 @@
|
||||
+<?xml version="1.0" encoding="UTF-8" ?>
|
||||
+<!--
|
||||
+ ~ Logback: the reliable, generic, fast and flexible logging framework.
|
||||
+ ~ Copyright (C) 1999-2024, QOS.ch. All rights reserved.
|
||||
+ ~
|
||||
+ ~ This program and the accompanying materials are dual-licensed under
|
||||
+ ~ either the terms of the Eclipse Public License v1.0 as published by
|
||||
+ ~ the Eclipse Foundation
|
||||
+ ~
|
||||
+ ~ or (per the licensee's choosing)
|
||||
+ ~
|
||||
+ ~ under the terms of the GNU Lesser General Public License version 2.1
|
||||
+ ~ as published by the Free Software Foundation.
|
||||
+ -->
|
||||
+
|
||||
+<!DOCTYPE test SYSTEM "http://192.168.1.100/">
|
||||
+<test>
|
||||
+
|
||||
+ <!-- this action throws an exception in the Action.begin method -->
|
||||
+ <badBegin>
|
||||
+ <touch/>
|
||||
+ <touch/>
|
||||
+ </badBegin>
|
||||
+
|
||||
+ <hello name="John Doe">XXX&</hello>
|
||||
+
|
||||
+</test>
|
||||
\ No newline at end of file
|
||||
--- a/logback-classic/src/main/java/ch/qos/logback/classic/joran/action/EvaluatorAction.java
|
||||
+++ /dev/null
|
||||
@@ -1,23 +0,0 @@
|
||||
-/**
|
||||
- * Logback: the reliable, generic, fast and flexible logging framework.
|
||||
- * Copyright (C) 1999-2015, QOS.ch. All rights reserved.
|
||||
- *
|
||||
- * This program and the accompanying materials are dual-licensed under
|
||||
- * either the terms of the Eclipse Public License v1.0 as published by
|
||||
- * the Eclipse Foundation
|
||||
- *
|
||||
- * or (per the licensee's choosing)
|
||||
- *
|
||||
- * under the terms of the GNU Lesser General Public License version 2.1
|
||||
- * as published by the Free Software Foundation.
|
||||
- */
|
||||
-package ch.qos.logback.classic.joran.action;
|
||||
-
|
||||
-import ch.qos.logback.classic.boolex.JaninoEventEvaluator;
|
||||
-import ch.qos.logback.core.joran.action.AbstractEventEvaluatorAction;
|
||||
-
|
||||
-public class EvaluatorAction extends AbstractEventEvaluatorAction {
|
||||
- protected String defaultClassName() {
|
||||
- return JaninoEventEvaluator.class.getName();
|
||||
- }
|
||||
-}
|
||||
--- a/logback-classic/src/main/java/ch/qos/logback/classic/joran/JoranConfigurator.java
|
||||
+++ b/logback-classic/src/main/java/ch/qos/logback/classic/joran/JoranConfigurator.java
|
||||
@@ -46,7 +46,6 @@ public class JoranConfigurator extends J
|
||||
rs.addRule(new ElementSelector("configuration/contextName"), new ContextNameAction());
|
||||
rs.addRule(new ElementSelector("configuration/contextListener"), new LoggerContextListenerAction());
|
||||
rs.addRule(new ElementSelector("configuration/insertFromJNDI"), new InsertFromJNDIAction());
|
||||
- rs.addRule(new ElementSelector("configuration/evaluator"), new EvaluatorAction());
|
||||
|
||||
rs.addRule(new ElementSelector("configuration/appender/sift"), new SiftAction());
|
||||
rs.addRule(new ElementSelector("configuration/appender/sift/*"), new NOPAction());
|
||||
--- a/logback-access/src/main/java/ch/qos/logback/access/joran/JoranConfigurator.java
|
||||
+++ b/logback-access/src/main/java/ch/qos/logback/access/joran/JoranConfigurator.java
|
||||
@@ -15,7 +15,6 @@ package ch.qos.logback.access.joran;
|
||||
|
||||
import ch.qos.logback.access.PatternLayout;
|
||||
import ch.qos.logback.access.PatternLayoutEncoder;
|
||||
-import ch.qos.logback.access.boolex.JaninoEventEvaluator;
|
||||
import ch.qos.logback.access.joran.action.ConfigurationAction;
|
||||
import ch.qos.logback.access.joran.action.EvaluatorAction;
|
||||
import ch.qos.logback.access.sift.SiftAction;
|
||||
@@ -67,7 +66,6 @@ public class JoranConfigurator extends J
|
||||
@Override
|
||||
protected void addDefaultNestedComponentRegistryRules(DefaultNestedComponentRegistry registry) {
|
||||
registry.add(AppenderBase.class, "layout", PatternLayout.class);
|
||||
- registry.add(EvaluatorFilter.class, "evaluator", JaninoEventEvaluator.class);
|
||||
|
||||
registry.add(AppenderBase.class, "encoder", PatternLayoutEncoder.class);
|
||||
registry.add(UnsynchronizedAppenderBase.class, "encoder", PatternLayoutEncoder.class);
|
||||
--- a/logback-access/src/main/java/ch/qos/logback/access/joran/action/EvaluatorAction.java
|
||||
+++ b/logback-access/src/main/java/ch/qos/logback/access/joran/action/EvaluatorAction.java
|
||||
@@ -13,13 +13,12 @@
|
||||
*/
|
||||
package ch.qos.logback.access.joran.action;
|
||||
|
||||
-import ch.qos.logback.access.boolex.JaninoEventEvaluator;
|
||||
import ch.qos.logback.core.joran.action.AbstractEventEvaluatorAction;
|
||||
|
||||
public class EvaluatorAction extends AbstractEventEvaluatorAction {
|
||||
|
||||
@Override
|
||||
protected String defaultClassName() {
|
||||
- return JaninoEventEvaluator.class.getName();
|
||||
+ return AbstractEventEvaluatorAction.class.getName();
|
||||
}
|
||||
}
|
||||
@ -1,57 +0,0 @@
|
||||
diff -Nru logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletInputStream.java logback-1.1.7.servlet/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletInputStream.java
|
||||
--- logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletInputStream.java 2016-02-25 22:15:50.000000000 +0100
|
||||
+++ logback-1.1.7.servlet/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletInputStream.java 2016-06-23 17:00:02.886622532 +0200
|
||||
@@ -18,6 +18,7 @@ import java.io.ByteArrayOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
|
||||
+import javax.servlet.ReadListener;
|
||||
import javax.servlet.ServletInputStream;
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
|
||||
@@ -71,4 +71,19 @@
|
||||
byte[] getInputBuffer() {
|
||||
return inputBuffer;
|
||||
}
|
||||
+
|
||||
+ @Override
|
||||
+ public boolean isReady() {
|
||||
+ return false;
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public boolean isFinished() {
|
||||
+ return false;
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public void setReadListener(ReadListener listener) {
|
||||
+ throw new UnsupportedOperationException("Not implemented yet.");
|
||||
+ }
|
||||
}
|
||||
diff -Nru logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletOutputStream.java logback-1.1.7.servlet/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletOutputStream.java
|
||||
--- logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletOutputStream.java 2016-02-25 22:15:50.000000000 +0100
|
||||
+++ logback-1.1.7.servlet/logback-access/src/main/java/ch/qos/logback/access/servlet/TeeServletOutputStream.java 2016-06-23 16:56:24.056883117 +0200
|
||||
@@ -18,6 +18,7 @@ import java.io.IOException;
|
||||
|
||||
import javax.servlet.ServletOutputStream;
|
||||
import javax.servlet.ServletResponse;
|
||||
+import javax.servlet.WriteListener;
|
||||
|
||||
public class TeeServletOutputStream extends ServletOutputStream {
|
||||
|
||||
@@ -82,4 +82,14 @@
|
||||
underlyingStream.flush();
|
||||
baosCopy.flush();
|
||||
}
|
||||
+
|
||||
+ @Override
|
||||
+ public boolean isReady() {
|
||||
+ return false;
|
||||
+ }
|
||||
+
|
||||
+ @Override
|
||||
+ public void setWriteListener(WriteListener listener) {
|
||||
+ throw new UnsupportedOperationException("Not implemented yet.");
|
||||
+ }
|
||||
}
|
||||
@ -1,15 +0,0 @@
|
||||
diff -Nru logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/tomcat/LogbackValve.java logback-1.1.7.tomcat/logback-access/src/main/java/ch/qos/logback/access/tomcat/LogbackValve.java
|
||||
--- logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/tomcat/LogbackValve.java 2016-03-11 09:16:10.000000000 +0100
|
||||
+++ logback-1.1.7.tomcat/logback-access/src/main/java/ch/qos/logback/access/tomcat/LogbackValve.java 2016-06-23 17:21:04.765375897 +0200
|
||||
@@ -328,11 +328,6 @@
|
||||
return aai.detachAppender(name);
|
||||
}
|
||||
|
||||
- @Override
|
||||
- public String getInfo() {
|
||||
- return "Logback's implementation of ValveBase";
|
||||
- }
|
||||
-
|
||||
// Methods from ContextBase:
|
||||
@Override
|
||||
public StatusManager getStatusManager() {
|
||||
@ -1,7 +1,6 @@
|
||||
diff -Nru logback-1.1.7/logback-access/pom.xml logback-1.1.7.jetty/logback-access/pom.xml
|
||||
--- logback-1.1.7/logback-access/pom.xml 2016-03-29 22:09:38.000000000 +0200
|
||||
+++ logback-1.1.7.jetty/logback-access/pom.xml 2016-06-23 17:18:59.640249538 +0200
|
||||
@@ -46,6 +46,12 @@
|
||||
--- logback-1.2.8/logback-access/pom.xml 2021-12-14 12:55:51.000000000 +0100
|
||||
+++ logback-1.2.8/logback-access/pom.xml 2021-12-16 15:35:11.255651389 +0100
|
||||
@@ -47,6 +47,12 @@
|
||||
<optional>true</optional>
|
||||
</dependency>
|
||||
<dependency>
|
||||
@ -14,17 +13,9 @@ diff -Nru logback-1.1.7/logback-access/pom.xml logback-1.1.7.jetty/logback-acces
|
||||
<groupId>org.codehaus.janino</groupId>
|
||||
<artifactId>janino</artifactId>
|
||||
<scope>compile</scope>
|
||||
@@ -173,4 +179,4 @@
|
||||
</profile>
|
||||
</profiles>
|
||||
|
||||
-</project>
|
||||
\ Manca newline alla fine del file
|
||||
+</project>
|
||||
diff -Nru logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/jetty/RequestLogImpl.java logback-1.1.7.jetty/logback-access/src/main/java/ch/qos/logback/access/jetty/RequestLogImpl.java
|
||||
--- logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/jetty/RequestLogImpl.java 2016-02-25 22:15:50.000000000 +0100
|
||||
+++ logback-1.1.7.jetty/logback-access/src/main/java/ch/qos/logback/access/jetty/RequestLogImpl.java 2016-06-23 17:04:46.410310065 +0200
|
||||
@@ -210,11 +210,6 @@
|
||||
--- logback-1.2.8/logback-access/src/main/java/ch/qos/logback/access/jetty/RequestLogImpl.java 2021-12-14 12:55:51.000000000 +0100
|
||||
+++ logback-1.2.8/logback-access/src/main/java/ch/qos/logback/access/jetty/RequestLogImpl.java 2021-12-16 15:35:11.255651389 +0100
|
||||
@@ -209,11 +209,6 @@
|
||||
started = false;
|
||||
}
|
||||
|
||||
@ -36,7 +27,7 @@ diff -Nru logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/jetty
|
||||
public void setFileName(String fileName) {
|
||||
this.fileName = fileName;
|
||||
}
|
||||
@@ -228,26 +223,6 @@
|
||||
@@ -227,26 +222,6 @@
|
||||
return started;
|
||||
}
|
||||
|
||||
@ -63,7 +54,7 @@ diff -Nru logback-1.1.7/logback-access/src/main/java/ch/qos/logback/access/jetty
|
||||
public boolean isQuiet() {
|
||||
return quiet;
|
||||
}
|
||||
@@ -311,13 +286,7 @@
|
||||
@@ -310,13 +285,7 @@
|
||||
return fai.getFilterChainDecision(event);
|
||||
}
|
||||
|
||||
47
logback.spec
47
logback.spec
@ -1,16 +1,14 @@
|
||||
Name: logback
|
||||
Version: 1.1.7
|
||||
Release: 6
|
||||
Version: 1.2.8
|
||||
Release: 4
|
||||
Summary: A Java logging library
|
||||
License: LGPLv2 or EPL
|
||||
License: LGPLv2 or EPL-1.0
|
||||
URL: http://logback.qos.ch/
|
||||
Source0: https://github.com/qos-ch/logback/archive/v_%{version}.tar.gz
|
||||
|
||||
# servlet 3.1 support
|
||||
Patch0001: %{name}-1.1.7-servlet.patch
|
||||
# Remove deprecate methods,otherwise it will cause compilation to fail
|
||||
Patch0002: %{name}-1.1.7-jetty.patch
|
||||
Patch0003: %{name}-1.1.7-tomcat.patch
|
||||
Patch0001: logback-1.2.8-jetty.patch
|
||||
Patch0002: CVE-2023-6378-and-CVE-2023-6481.patch
|
||||
Patch0003: CVE-2024-12798-and-CVE-2024-12801.patch
|
||||
|
||||
BuildRequires: java-devel >= 1:1.6.0 maven-local mvn(javax.mail:mail)
|
||||
BuildRequires: mvn(javax.servlet:javax.servlet-api) mvn(junit:junit) mvn(log4j:log4j:1.2.17)
|
||||
@ -78,9 +76,8 @@ find . -name "*.jar" -delete
|
||||
%pom_remove_plugin -r :maven-dependency-plugin
|
||||
%pom_remove_plugin -r :cobertura-maven-plugin
|
||||
|
||||
sed -i 's/\r//' LICENSE.txt README.txt
|
||||
sed -i 's/\r//' LICENSE.txt
|
||||
|
||||
%pom_change_dep -r :servlet-api javax.servlet:javax.servlet-api:3.1.0
|
||||
sed -i 's#javax.servlet.*;version="2.5"#javax.servlet.*;version="3.1"#' %{name}-access/pom.xml
|
||||
|
||||
rm -r %{name}-*/src/test/java/*
|
||||
@ -93,24 +90,13 @@ rm -r %{name}-*/src/test/java/*
|
||||
%pom_xpath_remove "pom:project/pom:profiles" %{name}-classic
|
||||
|
||||
%pom_xpath_remove "pom:project/pom:profiles/pom:profile[pom:id = 'javadocjar']"
|
||||
%pom_xpath_remove "pom:executions/pom:execution/pom:goals/pom:goal[text() = 'generateTestStubs']" logback-classic
|
||||
%pom_xpath_remove "pom:executions/pom:execution/pom:goals/pom:goal[text() = 'compileTests']" logback-classic
|
||||
|
||||
%pom_disable_module logback-site
|
||||
|
||||
%pom_xpath_remove "pom:build/pom:extensions"
|
||||
|
||||
%pom_remove_plugin :maven-compiler-plugin logback-classic
|
||||
%pom_add_plugin org.codehaus.gmavenplus:gmavenplus-plugin:1.5 logback-classic "
|
||||
<executions>
|
||||
<execution>
|
||||
<goals>
|
||||
<goal>generateStubs</goal>
|
||||
<goal>testGenerateStubs</goal>
|
||||
<!--goal>compile</goal>
|
||||
<goal>testCompile</goal-->
|
||||
</goals>
|
||||
</execution>
|
||||
</executions>"
|
||||
|
||||
%mvn_package ":%{name}-access" access
|
||||
%mvn_package ":%{name}-examples" examples
|
||||
|
||||
@ -126,7 +112,6 @@ install -d -m 755 %{buildroot}%{_datadir}/%{name}/examples
|
||||
cp -r %{name}-examples/pom.xml %{name}-examples/src %{buildroot}%{_datadir}/%{name}/examples
|
||||
|
||||
%files -f .mfiles
|
||||
%doc README.txt
|
||||
%license LICENSE.txt
|
||||
|
||||
%files access -f .mfiles-access
|
||||
@ -139,5 +124,19 @@ cp -r %{name}-examples/pom.xml %{name}-examples/src %{buildroot}%{_datadir}/%{na
|
||||
%files help -f .mfiles-javadoc
|
||||
|
||||
%changelog
|
||||
* Mon Jan 20 2025 yaoxin <1024769339@qq.com> - 1.2.8-4
|
||||
- Fix CVE-2024-12798 and CVE-2024-12801
|
||||
|
||||
* Tue Dec 12 2023 wangkai <13474090681@163.com> - 1.2.8-3
|
||||
- Fix CVE-2023-6378,CVE-2023-6481
|
||||
|
||||
* Mon Aug 8 2022 Chenyx <chenyixiong3@huawei.com> - 1.2.8-2
|
||||
- License compliance rectification
|
||||
|
||||
* Mon Dec 27 2021 houyingchao <houyingchao@huawei.com> - 1.2.8-1
|
||||
- Upgrade to 1.2.8
|
||||
- Fix CVE-2021-42550
|
||||
* Sat Sep 19 2020 wangxiao <wangxiao65@huawei.com> - 1.1.7-7
|
||||
- fix CVE-2017-5929
|
||||
* Wed Mar 4 2020 dingyiming <dingyiming3@huawei.com> - 1.1.7-6
|
||||
- Package init
|
||||
|
||||
4
logback.yaml
Normal file
4
logback.yaml
Normal file
@ -0,0 +1,4 @@
|
||||
version_control: github
|
||||
src_repo: qos-ch/logback/
|
||||
tag_prefix: ^v_
|
||||
separator: .
|
||||
BIN
v_1.1.7.tar.gz
BIN
v_1.1.7.tar.gz
Binary file not shown.
BIN
v_1.2.8.tar.gz
Normal file
BIN
v_1.2.8.tar.gz
Normal file
Binary file not shown.
Loading…
x
Reference in New Issue
Block a user