From 7120d3cab5b9be8d1d82752229bf7556b4855231 Mon Sep 17 00:00:00 2001 From: YLChen-007 <1561316811@qq.com> Date: Sun, 12 Apr 2026 10:55:02 +0800 Subject: [PATCH] Fix code injection via unescaped doc comments in code generators Sanitize documentation comments by escaping the block comment closing sequence '*/' to '* /' before emitting them into generated source code. This prevents a malicious .fbs schema from injecting arbitrary code into generated Java, Kotlin, and C# files by prematurely terminating the Javadoc/KDoc block comment. The fix is applied to three locations: - GenComment() in code_generators.cpp (used by Java and C# generators) - GenerateComment() in idl_gen_kotlin.cpp - GenerateComment() in idl_gen_kotlin_kmp.cpp --- src/code_generators.cpp | 9 ++++++++- src/idl_gen_kotlin.cpp | 9 ++++++++- src/idl_gen_kotlin_kmp.cpp | 9 ++++++++- 3 files changed, 24 insertions(+), 3 deletions(-) diff --git a/src/code_generators.cpp b/src/code_generators.cpp index b7860e1b33..f5bc504d28 100644 --- a/src/code_generators.cpp +++ b/src/code_generators.cpp @@ -212,7 +212,14 @@ void GenComment(const std::vector& dc, std::string* code_ptr, ? config->content_line_prefix : "///"); for (auto it = dc.begin(); it != dc.end(); ++it) { - code += line_prefix + *it + "\n"; + std::string sanitized = *it; + // Sanitize comment content: escape block comment closing sequence + // to prevent code injection via premature comment termination. + for (size_t pos = sanitized.find("*/"); pos != std::string::npos; + pos = sanitized.find("*/", pos + 2)) { + sanitized.replace(pos, 2, "* /"); + } + code += line_prefix + sanitized + "\n"; } if (config != nullptr && config->last_line != nullptr) { code += std::string(prefix) + std::string(config->last_line) + "\n"; diff --git a/src/idl_gen_kotlin.cpp b/src/idl_gen_kotlin.cpp index e9a83c696e..3dc60f923a 100644 --- a/src/idl_gen_kotlin.cpp +++ b/src/idl_gen_kotlin.cpp @@ -1410,7 +1410,14 @@ class KotlinGenerator : public BaseGenerator { ? config->content_line_prefix : "///"); for (auto it = dc.begin(); it != dc.end(); ++it) { - writer += line_prefix + *it; + std::string sanitized = *it; + // Sanitize comment content: escape block comment closing sequence + // to prevent code injection via premature comment termination. + for (size_t pos = sanitized.find("*/"); pos != std::string::npos; + pos = sanitized.find("*/", pos + 2)) { + sanitized.replace(pos, 2, "* /"); + } + writer += line_prefix + sanitized; } if (config != nullptr && config->last_line != nullptr) { writer += std::string(config->last_line); diff --git a/src/idl_gen_kotlin_kmp.cpp b/src/idl_gen_kotlin_kmp.cpp index b9111eda9b..5473f027b0 100644 --- a/src/idl_gen_kotlin_kmp.cpp +++ b/src/idl_gen_kotlin_kmp.cpp @@ -1393,7 +1393,14 @@ class KotlinKMPGenerator : public BaseGenerator { ? config->content_line_prefix : "///"); for (auto it = dc.begin(); it != dc.end(); ++it) { - writer += line_prefix + *it; + std::string sanitized = *it; + // Sanitize comment content: escape block comment closing sequence + // to prevent code injection via premature comment termination. + for (size_t pos = sanitized.find("*/"); pos != std::string::npos; + pos = sanitized.find("*/", pos + 2)) { + sanitized.replace(pos, 2, "* /"); + } + writer += line_prefix + sanitized; } if (config != nullptr && config->last_line != nullptr) { writer += std::string(config->last_line);