diff --git a/clang-tools-extra/clangd/include-mapping/gen_std.py b/clang-tools-extra/clangd/include-mapping/gen_std.py --- a/clang-tools-extra/clangd/include-mapping/gen_std.py +++ b/clang-tools-extra/clangd/include-mapping/gen_std.py @@ -114,9 +114,12 @@ abs() (int)
acos()
- Returns a list of tuple (symbol_name, relative_path_to_symbol_page, variant). + Returns a tuple + ( a list of tuple (symbol_name, relative_path_to_symbol_page), + a list of tuple (variant_symbol_name, caption_text) ) """ symbols = [] + variant_symbols = [] soup = BeautifulSoup(index_page_html, "html.parser") for symbol_href in soup.select("a[title]"): # Ignore annotated symbols like "acos<>() (std::complex)". @@ -127,9 +130,12 @@ variant = isinstance(caption, NavigableString) and "(" in caption symbol_tt = symbol_href.find("tt") if symbol_tt: - symbols.append((symbol_tt.text.rstrip("<>()"), # strip any trailing <>() - symbol_href["href"], variant)) - return symbols + symbol_name = symbol_tt.text.rstrip("<>()") # strip any trailing <>() + if variant: + variant_symbols.append((symbol_name, caption)) + else: + symbols.append((symbol_name, symbol_href["href"])) + return (symbols, variant_symbols) class Symbol: @@ -163,11 +169,8 @@ with open(index_page_path, "r") as f: # Read each symbol page in parallel. results = [] # (symbol_name, promise of [header...]) - for symbol_name, symbol_page_path, variant in ParseIndexPage(f.read()): - # Variant symbols (e.g. the std::locale version of isalpha) add ambiguity. - # FIXME: use these as a fallback rather than ignoring entirely. - if variant: - continue + (symbols, variant_symbols) = ParseIndexPage(f.read()) + for symbol_name, symbol_page_path in symbols: path = os.path.join(root_dir, symbol_page_path) results.append((symbol_name, pool.apply_async(ReadSymbolPage, (path, symbol_name)))) @@ -177,6 +180,11 @@ for symbol_name, lazy_headers in results: symbol_headers[symbol_name].update(lazy_headers.get()) + for variant_symbol_name, caption in variant_symbols: + if variant_symbol_name not in symbol_headers: + sys.stderr.write("Ignore variant symbol %s%s\n" % (variant_symbol_name, + caption)) + symbols = [] for name, headers in sorted(symbol_headers.items(), key=lambda t : t[0]): symbols.append(Symbol(name, namespace, list(headers))) diff --git a/clang-tools-extra/clangd/include-mapping/test.py b/clang-tools-extra/clangd/include-mapping/test.py --- a/clang-tools-extra/clangd/include-mapping/test.py +++ b/clang-tools-extra/clangd/include-mapping/test.py @@ -15,26 +15,30 @@ def testParseIndexPage(self): html = """ - abs() (int)
- abs<>() (std::complex)
+ abs()(int)
+ abs<>()(std::complex)
acos()
acosh() (since C++11)
as_bytes<>() (since C++20)
""" - actual = ParseIndexPage(html) - expected = [ - ("abs", "abs.html", True), - ("abs", "complex/abs.html", True), - ("acos", "acos.html", False), - ("acosh", "acosh.html", False), - ("as_bytes", "as_bytes.html", False), + (actual, variant) = ParseIndexPage(html) + expected_actual = [ + ("acos", "acos.html"), + ("acosh", "acosh.html"), + ("as_bytes", "as_bytes.html"), ] - self.assertEqual(len(actual), len(expected)) + expected_variant = [ + ("abs", "(int)"), + ("abs", "(std::complex)") + ] + self.assertEqual(len(actual), len(expected_actual)) for i in range(0, len(actual)): - self.assertEqual(expected[i][0], actual[i][0]) - self.assertTrue(actual[i][1].endswith(expected[i][1])) - self.assertEqual(expected[i][2], actual[i][2]) + self.assertEqual(expected_actual[i][0], actual[i][0]) + self.assertTrue(actual[i][1].endswith(expected_actual[i][1])) + self.assertEqual(len(variant), len(expected_variant)) + for i in range(0, len(variant)): + self.assertEqual(expected_variant[i], variant[i]) def testParseSymbolPage_SingleHeader(self):