GP-272 - Gnu Demangler - fixed demangler failure on template that

contained function signature
This commit is contained in:
dragonmacher 2020-11-12 17:35:56 -05:00
parent bf9245d54f
commit c75491d70a
2 changed files with 57 additions and 5 deletions

View file

@ -628,7 +628,11 @@ public class GnuDemanglerParser {
// or
// iterator<boost::function<void ()>
//
i = findBalancedEnd(parameterString, i, '(', ')');
int end = findBalancedEnd(parameterString, i, '(', ')');
if (end == -1) {
end = parameterString.length();
}
i = end;
}
}
if (startIndex < parameterString.length()) {
@ -753,9 +757,8 @@ public class GnuDemanglerParser {
i = i - 1; // back up one space to catch optional templates on next loop pass
}
else {
int startParenCount =
StringUtilities.countOccurrences(datatype.substring(i), '(');
boolean hasPointerParens = startParenCount >= 2;
// e.g., unsigned long (*)(long const &)
boolean hasPointerParens = hasConsecutiveSetsOfParens(datatype.substring(i));
if (hasPointerParens) {
Demangled namespace = ddt.getNamespace();
DemangledFunctionPointer dfp = parseFunctionPointer(datatype);
@ -858,6 +861,25 @@ public class GnuDemanglerParser {
return ddt;
}
private boolean hasConsecutiveSetsOfParens(String text) {
int end = findBalancedEnd(text, 0, '(', ')');
if (end < -1) {
return false;
}
for (int i = end + 1; i < text.length(); i++) {
char c = text.charAt(i);
if (c == '(') {
return true;
}
if (c != ' ') {
return false;
}
}
return false;
}
private DemangledDataType createMemberPointer(String datatype) {
// this is temp code we expect to update as more samples arrive
@ -1072,7 +1094,8 @@ public class GnuDemanglerParser {
//unsigned long (long const &)
int parenStart = functionString.indexOf('(', offset);
int parenEnd = functionString.indexOf(')', parenStart + 1);
int parenEnd = findBalancedEnd(functionString, parenStart, '(', ')');
//int parenEnd = functionString.indexOf(')', parenStart + 1);
String returnType = functionString.substring(0, parenStart).trim();

View file

@ -1346,6 +1346,35 @@ public class GnuDemanglerParserTest extends AbstractGenericTest {
object.getSignature(false));
}
@Test
public void testTemplatesThatContainFunctionSignatures_Regression() throws Exception {
//
// Mangled: _ZN7WebCore27ContentFilterUnblockHandlerC2EN3WTF6StringENSt3__18functionIFvNS4_IFvbEEEEEE
//
// Demangled: WebCore::ContentFilterUnblockHandler::ContentFilterUnblockHandler(WTF::String, std::__1::function<void (std::__1::function<void (bool)>)>)
//
// Note: this parameter name caused an infinite loop
//
// function<void (std::__1::function<void (bool)>)>)
//
DemangledObject object = parser.parse(
"_ZN7WebCore27ContentFilterUnblockHandlerC2EN3WTF6StringENSt3__18functionIFvNS4_IFvbEEEEEE",
"WebCore::ContentFilterUnblockHandler::ContentFilterUnblockHandler(WTF::String, std::__1::function<void (std::__1::function<void (bool)>)>)");
assertNotNull(object);
assertType(object, DemangledFunction.class);
String name = "ContentFilterUnblockHandler";
assertName(object, name, "WebCore", "ContentFilterUnblockHandler");
String signature = object.getSignature(false);
assertEquals(
"undefined WebCore::ContentFilterUnblockHandler::ContentFilterUnblockHandler(WTF::String,std::__1::function<void (std::__1::function<void (bool)>)>)",
signature);
}
@Test
public void testVtableParsingError_NoSpaceBeforeTrailingDigits() throws Exception {
//