Skip to content

Commit ce1eb96

Browse files
committed
Resolve review comments in sphinx-doc#12162
Signed-off-by: Donald Hunter <[email protected]>
1 parent 40ed176 commit ce1eb96

File tree

2 files changed

+73
-67
lines changed

2 files changed

+73
-67
lines changed

sphinx/domains/c/_ast.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,10 @@ def is_anon(self) -> bool:
5858
def __str__(self) -> str:
5959
return self.identifier
6060

61+
@property
62+
def name(self) -> str:
63+
return self.identifier
64+
6165
def get_display_string(self) -> str:
6266
return "[anonymous]" if self.is_anon() else self.identifier
6367

sphinx/domains/c/_symbol.py

Lines changed: 69 additions & 67 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
from sphinx.util import logging
1212

1313
if TYPE_CHECKING:
14-
from collections.abc import Iterator
14+
from collections.abc import Iterator, Sequence
1515

1616
from typing_extensions import Self
1717

@@ -32,7 +32,7 @@ def __str__(self) -> str:
3232

3333

3434
class SymbolLookupResult:
35-
def __init__(self, symbols: list[Symbol], parentSymbol: Symbol,
35+
def __init__(self, symbols: Sequence[Symbol], parentSymbol: Symbol,
3636
ident: ASTIdentifier) -> None:
3737
self.symbols = symbols
3838
self.parentSymbol = parentSymbol
@@ -101,25 +101,43 @@ def __init__(
101101
self.isRedeclaration = False
102102
self._assert_invariants()
103103

104-
# Remember to modify Symbol.remove if modifications to the parent change.
104+
# These properties store the same children for different access
105+
# patterns. Symbol._add_child and Symbol._remove_child should be
106+
# used for modifying them.
105107
self._childrenByName: dict[str, Symbol] = {}
106-
self._childrenByDocname: dict[str, list[Symbol]] = {}
107-
self._anonChildren: list[Symbol] = []
108-
# note: _children includes _anonChildren
108+
self._childrenByDocname: dict[str, dict[str, Symbol]] = {}
109+
self._anonChildren: set[Symbol] = set()
110+
109111
if self.parent:
110-
self.parent._childrenByName[str(self.ident)] = self
111-
if self.docname in self.parent._childrenByDocname:
112-
self.parent._childrenByDocname[self.docname].append(self)
113-
else:
114-
self.parent._childrenByDocname[self.docname] = [self]
115-
if ident.is_anon():
116-
self.parent._anonChildren.append(self)
112+
self.parent._add_child(self)
117113
if self.declaration:
118114
self.declaration.symbol = self
119115

120116
# Do symbol addition after self._children has been initialised.
121117
self._add_function_params()
122118

119+
@property
120+
def _children(self) -> Sequence[Symbol]:
121+
return self._childrenByName.values()
122+
123+
def _add_child(self, child: Symbol) -> None:
124+
name = child.ident.name
125+
self._childrenByName[name] = child
126+
if child.docname not in self._childrenByDocname:
127+
self._childrenByDocname[child.docname] = {}
128+
self._childrenByDocname[child.docname][name] = child
129+
if child.ident.is_anon():
130+
self._anonChildren.add(child)
131+
132+
def _remove_child(self, child: Symbol) -> None:
133+
name = child.ident.name
134+
self._childrenByName.pop(name)
135+
siblings = self._childrenByDocname.get(child.docname, {})
136+
if name in siblings:
137+
siblings.pop(name)
138+
if child.ident.is_anon() and child in self._anonChildren:
139+
self._anonChildren.remove(child)
140+
123141
def _fill_empty(self, declaration: ASTDeclaration, docname: str, line: int) -> None:
124142
self._assert_invariants()
125143
assert self.declaration is None
@@ -160,23 +178,16 @@ def _add_function_params(self) -> None:
160178
Symbol.debug_indent -= 1
161179

162180
def remove(self) -> None:
163-
if self.parent is None:
164-
return
165-
name = str(self.ident)
166-
assert name in self.parent._childrenByName
167-
del self.parent._childrenByName[name]
168-
if self.docname in self.parent._childrenByDocname:
169-
del self.parent._childrenByDocname[self.docname]
170-
if self.ident.is_anon():
171-
self.parent._anonChildren.remove(self)
172-
self.parent = None
181+
if self.parent:
182+
self.parent._remove_child(self)
183+
self.parent = None
173184

174185
def clear_doc(self, docname: str) -> None:
175186
if docname not in self._childrenByDocname:
176-
for child in self._childrenByName.values():
187+
for child in self._children:
177188
child.clear_doc(docname)
178189
return
179-
for sChild in self._childrenByDocname[docname]:
190+
for sChild in self._childrenByDocname[docname].values():
180191
sChild.declaration = None
181192
sChild.docname = None
182193
sChild.line = None
@@ -186,29 +197,18 @@ def clear_doc(self, docname: str) -> None:
186197
sChild.siblingBelow.siblingAbove = sChild.siblingAbove
187198
sChild.siblingAbove = None
188199
sChild.siblingBelow = None
189-
name = str(sChild.ident)
190-
if name in self._childrenByName:
191-
del self._childrenByName[name]
192-
if sChild.ident.is_anon():
193-
self._anonChildren.remove(sChild)
200+
201+
self._remove_child(sChild)
194202
del self._childrenByDocname[docname]
195203

196204
def get_all_symbols(self) -> Iterator[Symbol]:
197205
yield self
198-
for sChild in self._childrenByName.values():
206+
for sChild in self._children:
199207
yield from sChild.get_all_symbols()
200208

201209
@property
202210
def children(self) -> Iterator[Symbol]:
203-
yield from self._childrenByName.values()
204-
205-
@property
206-
def children_recurse_anon(self) -> Iterator[Symbol]:
207-
for c in self._childrenByName.values():
208-
yield c
209-
if not c.ident.is_anon():
210-
continue
211-
yield from c.children_recurse_anon
211+
yield from self._children
212212

213213
def get_lookup_key(self) -> LookupKey:
214214
# The pickle files for the environment and for each document are distinct.
@@ -275,37 +275,46 @@ def _symbol_lookup(
275275
# walk up until we find the first identifier
276276
firstName = names[0]
277277
while parentSymbol.parent:
278-
if str(firstName) in parentSymbol._childrenByName:
278+
if firstName.name in parentSymbol._childrenByName:
279279
break
280280
parentSymbol = parentSymbol.parent
281281

282+
if Symbol.debug_lookup:
283+
Symbol.debug_print("starting point:")
284+
logger.debug(parentSymbol.to_string(Symbol.debug_indent + 1), end="")
285+
282286
# and now the actual lookup
283287
for ident in names[:-1]:
284-
name = str(ident)
288+
name = ident.name
285289
if name in parentSymbol._childrenByName:
286290
symbol = parentSymbol._childrenByName[name]
287291
else:
288292
symbol = onMissingQualifiedSymbol(parentSymbol, ident)
289293
if symbol is None:
294+
if Symbol.debug_lookup:
295+
Symbol.debug_indent -= 2
290296
return None
291297
parentSymbol = symbol
292298

299+
if Symbol.debug_lookup:
300+
Symbol.debug_print("handle last name from:")
301+
logger.debug(parentSymbol.to_string(Symbol.debug_indent + 1), end="")
302+
293303
# handle the last name
294304
ident = names[-1]
295-
name = str(ident)
296-
symbol = None
297-
if name in parentSymbol._childrenByName:
298-
symbol = parentSymbol._childrenByName[name]
299-
305+
name = ident.name
306+
symbol = parentSymbol._childrenByName.get(name)
300307
if not symbol and recurseInAnon:
301308
for child in parentSymbol._anonChildren:
302309
if name in child._childrenByName:
303310
symbol = child._childrenByName[name]
304311
break
305-
if symbol:
306-
return SymbolLookupResult([symbol], parentSymbol, ident)
307-
else:
308-
return SymbolLookupResult([], parentSymbol, ident)
312+
313+
if Symbol.debug_lookup:
314+
Symbol.debug_indent -= 2
315+
316+
result = [symbol] if symbol else []
317+
return SymbolLookupResult(result, parentSymbol, ident)
309318

310319
def _add_symbols(
311320
self,
@@ -481,12 +490,12 @@ def merge_with(self, other: Symbol, docnames: list[str],
481490
Symbol.debug_print("merge_with:")
482491

483492
assert other is not None
484-
for otherChild in other._childrenByName.values():
485-
otherName = str(otherChild.ident)
493+
for otherChild in other._children:
494+
otherName = otherChild.ident.name
486495
if otherName not in self._childrenByName:
487496
# TODO: hmm, should we prune by docnames?
488-
self._childrenByName[otherName] = otherChild
489497
otherChild.parent = self
498+
self._add_child(otherChild)
490499
otherChild._assert_invariants()
491500
continue
492501
ourChild = self._childrenByName[otherName]
@@ -556,7 +565,7 @@ def find_identifier(self, ident: ASTIdentifier,
556565
Symbol.debug_indent -= 2
557566
if matchSelf and current.ident == ident:
558567
return current
559-
name = str(ident)
568+
name = ident.name
560569
if name in current._childrenByName:
561570
return current._childrenByName[name]
562571
if recurseInAnon:
@@ -575,22 +584,16 @@ def direct_lookup(self, key: LookupKey) -> Symbol | None:
575584
Symbol.debug_indent += 1
576585
s = self
577586
for ident, id_ in key.data:
578-
res = None
579-
name = str(ident)
580-
if name in s._childrenByName:
581-
res = s._childrenByName[name]
582-
s = res
587+
s = s._childrenByName.get(ident.name)
583588
if Symbol.debug_lookup:
584-
Symbol.debug_print("name: ", name)
589+
Symbol.debug_print("name: ", ident.name)
585590
Symbol.debug_print("id: ", id_)
586591
if s is not None:
587592
logger.debug(s.to_string(Symbol.debug_indent + 1), end="")
588593
else:
589594
Symbol.debug_print("not found")
590595
if s is None:
591-
if Symbol.debug_lookup:
592-
Symbol.debug_indent -= 2
593-
return None
596+
break
594597
if Symbol.debug_lookup:
595598
Symbol.debug_indent -= 2
596599
return s
@@ -630,7 +633,7 @@ def to_string(self, indent: int) -> str:
630633
res.append('::')
631634
else:
632635
if self.ident:
633-
res.append(str(self.ident))
636+
res.append(self.ident.name)
634637
else:
635638
res.append(str(self.declaration))
636639
if self.declaration:
@@ -646,5 +649,4 @@ def to_string(self, indent: int) -> str:
646649
return ''.join(res)
647650

648651
def dump(self, indent: int) -> str:
649-
return ''.join([self.to_string(indent),
650-
*(c.dump(indent + 1) for c in self._childrenByName.values())])
652+
return ''.join([self.to_string(indent), *(c.dump(indent + 1) for c in self._children)])

0 commit comments

Comments
 (0)