Skip to content

Commit 88a3b90

Browse files
authored
Change pre-22 poison pill to only log once per affected message type. (#21754)
1 parent 320eafa commit 88a3b90

File tree

3 files changed

+71
-34
lines changed

3 files changed

+71
-34
lines changed

java/core/src/main/java/com/google/protobuf/GeneratedMessage.java

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -21,9 +21,11 @@
2121
import java.lang.reflect.Method;
2222
import java.util.ArrayList;
2323
import java.util.Collections;
24+
import java.util.HashSet;
2425
import java.util.Iterator;
2526
import java.util.List;
2627
import java.util.Map;
28+
import java.util.Set;
2729
import java.util.TreeMap;
2830
import java.util.logging.Logger;
2931

@@ -329,21 +331,30 @@ public int getSerializedSize() {
329331
+ " security vulnerability:"
330332
+ " https://github.com/protocolbuffers/protobuf/security/advisories/GHSA-h4h5-3hr4-j3g2";
331333

332-
static void warnPre22Gencode() {
334+
private static final Set<String> loggedPre22TypeNames
335+
= Collections.synchronizedSet(new HashSet<String>());
336+
static void warnPre22Gencode(Class<?> messageClass) {
333337
if (System.getProperty(PRE22_GENCODE_SILENCE_PROPERTY) != null) {
334338
return;
335339
}
336-
UnsupportedOperationException exception =
337-
new UnsupportedOperationException(PRE22_GENCODE_VULNERABILITY_MESSAGE);
340+
String messageName = messageClass.getName();
341+
String vulnerabilityMessage =
342+
"Vulnerable protobuf generated type in use: " + messageName + "\n" +
343+
PRE22_GENCODE_VULNERABILITY_MESSAGE;
344+
338345
if (System.getProperty(PRE22_GENCODE_ERROR_PROPERTY) != null) {
339-
throw exception;
346+
throw new UnsupportedOperationException(vulnerabilityMessage);
347+
}
348+
349+
if (!loggedPre22TypeNames.add(messageName)) {
350+
return;
340351
}
341-
logger.warning(exception.toString());
352+
logger.warning(vulnerabilityMessage);
342353
}
343354

344355
/** Used by parsing constructors in generated classes. */
345356
protected void makeExtensionsImmutable() {
346-
warnPre22Gencode();
357+
warnPre22Gencode(getClass());
347358
}
348359

349360
/**
@@ -933,7 +944,7 @@ protected boolean parseUnknownField(
933944
/** Used by parsing constructors in generated classes. */
934945
@Override
935946
protected void makeExtensionsImmutable() {
936-
warnPre22Gencode();
947+
warnPre22Gencode(getClass());
937948
extensions.makeImmutable();
938949
}
939950

java/core/src/main/java/com/google/protobuf/GeneratedMessageV3.java

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -528,7 +528,7 @@ protected Object newInstance(UnusedPrivateParameter unused) {
528528
*/
529529
protected void makeExtensionsImmutable() {
530530
// Noop for messages without extensions.
531-
GeneratedMessage.warnPre22Gencode();
531+
GeneratedMessage.warnPre22Gencode(getClass());
532532
}
533533

534534
/**
@@ -1276,7 +1276,7 @@ protected boolean parseUnknownFieldProto3(
12761276
*/
12771277
@Override
12781278
protected void makeExtensionsImmutable() {
1279-
GeneratedMessage.warnPre22Gencode();
1279+
GeneratedMessage.warnPre22Gencode(getClass());
12801280
extensions.makeImmutable();
12811281
}
12821282

java/core/src/test/java/com/google/protobuf/GeneratedMessageTest.java

Lines changed: 51 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -2015,39 +2015,58 @@ private TestUtil.TestLogHandler setupLogger() {
20152015
@Test
20162016
public void generatedMessage_makeExtensionsImmutableShouldLog() {
20172017
TestUtil.TestLogHandler logHandler = setupLogger();
2018-
GeneratedMessageV3 msg =
2019-
new GeneratedMessageV3() {
2020-
@Override
2021-
protected FieldAccessorTable internalGetFieldAccessorTable() {
2022-
return null;
2023-
}
2024-
2025-
@Override
2026-
protected Message.Builder newBuilderForType(BuilderParent parent) {
2027-
return null;
2028-
}
2018+
class TestMessage1 extends GeneratedMessageV3 {
2019+
@Override
2020+
protected FieldAccessorTable internalGetFieldAccessorTable() {
2021+
return null;
2022+
}
2023+
2024+
@Override
2025+
protected Message.Builder newBuilderForType(BuilderParent parent) {
2026+
return null;
2027+
}
2028+
2029+
@Override
2030+
public Message.Builder newBuilderForType() {
2031+
return null;
2032+
}
2033+
2034+
@Override
2035+
public Message.Builder toBuilder() {
2036+
return null;
2037+
}
2038+
2039+
@Override
2040+
public Message getDefaultInstanceForType() {
2041+
return null;
2042+
}
2043+
}
20292044

2030-
@Override
2031-
public Message.Builder newBuilderForType() {
2032-
return null;
2033-
}
2045+
class TestMessage2 extends TestMessage1 {}
20342046

2035-
@Override
2036-
public Message.Builder toBuilder() {
2037-
return null;
2038-
}
2039-
2040-
@Override
2041-
public Message getDefaultInstanceForType() {
2042-
return null;
2043-
}
2044-
};
2047+
TestMessage1 msg = new TestMessage1();
20452048
msg.makeExtensionsImmutable();
20462049
List<LogRecord> logs = logHandler.getStoredLogRecords();
20472050
assertThat(logs).hasSize(1);
20482051
String message = logs.get(0).getMessage();
2052+
// The generated type
2053+
assertThat(message).contains(
2054+
"Vulnerable protobuf generated type in use: " +
2055+
"com.google.protobuf.GeneratedMessageTest$1TestMessage1");
20492056
assertThat(message).contains(GeneratedMessage.PRE22_GENCODE_VULNERABILITY_MESSAGE);
20502057
assertThat(message).contains(GeneratedMessage.PRE22_GENCODE_SILENCE_PROPERTY);
2058+
2059+
// Subsequent calls for the same type do not log again.
2060+
msg.makeExtensionsImmutable();
2061+
assertThat(logHandler.getStoredLogRecords()).hasSize(1);
2062+
2063+
// A call on a second type does log for that type.
2064+
TestMessage2 msg2 = new TestMessage2();
2065+
msg2.makeExtensionsImmutable();
2066+
assertThat(logHandler.getStoredLogRecords()).hasSize(2);
2067+
// And not again (only once per type).
2068+
msg2.makeExtensionsImmutable();
2069+
assertThat(logHandler.getStoredLogRecords()).hasSize(2);
20512070
}
20522071

20532072
@Test
@@ -2059,7 +2078,14 @@ public void extendableMessage_makeExtensionsImmutableShouldThrow() {
20592078
List<LogRecord> logs = logHandler.getStoredLogRecords();
20602079
assertThat(logs).hasSize(1);
20612080
String message = logs.get(0).getMessage();
2081+
assertThat(message).contains(
2082+
"Vulnerable protobuf generated type in use: " +
2083+
"protobuf_unittest.UnittestProto$TestAllExtensions");
20622084
assertThat(message).contains(GeneratedMessage.PRE22_GENCODE_VULNERABILITY_MESSAGE);
20632085
assertThat(message).contains(GeneratedMessage.PRE22_GENCODE_SILENCE_PROPERTY);
2086+
2087+
// Subsequent calls for the same type do not log again.
2088+
msg.makeExtensionsImmutable();
2089+
assertThat(logHandler.getStoredLogRecords()).hasSize(1);
20642090
}
20652091
}

0 commit comments

Comments
 (0)