summaryrefslogtreecommitdiff
path: root/sphinx/domains/cpp.py
diff options
context:
space:
mode:
Diffstat (limited to 'sphinx/domains/cpp.py')
-rw-r--r--sphinx/domains/cpp.py182
1 files changed, 10 insertions, 172 deletions
diff --git a/sphinx/domains/cpp.py b/sphinx/domains/cpp.py
index 8180384da..79b6b9b03 100644
--- a/sphinx/domains/cpp.py
+++ b/sphinx/domains/cpp.py
@@ -21,7 +21,6 @@ from sphinx import addnodes
from sphinx.addnodes import desc_signature, pending_xref
from sphinx.application import Sphinx
from sphinx.builders import Builder
-from sphinx.config import Config
from sphinx.directives import ObjectDescription
from sphinx.domains import Domain, ObjType
from sphinx.environment import BuildEnvironment
@@ -32,7 +31,7 @@ from sphinx.transforms import SphinxTransform
from sphinx.transforms.post_transforms import ReferencesResolver
from sphinx.util import logging
from sphinx.util.cfamily import (
- NoOldIdError, ASTBaseBase, verify_description_mode, StringifyTransform,
+ NoOldIdError, ASTBaseBase, ASTAttribute, verify_description_mode, StringifyTransform,
BaseParser, DefinitionError, UnsupportedMultiCharacterCharLiteral,
identifier_re, anon_identifier_re, integer_literal_re, octal_literal_re,
hex_literal_re, binary_literal_re, float_literal_re,
@@ -770,89 +769,6 @@ class ASTNestedName(ASTBase):
################################################################################
-# Attributes
-################################################################################
-
-class ASTAttribute(ASTBase):
- def describe_signature(self, signode: TextElement) -> None:
- raise NotImplementedError(repr(self))
-
-
-class ASTCPPAttribute(ASTAttribute):
- def __init__(self, arg: str) -> None:
- self.arg = arg
-
- def _stringify(self, transform: StringifyTransform) -> str:
- return "[[" + self.arg + "]]"
-
- def describe_signature(self, signode: TextElement) -> None:
- txt = str(self)
- signode.append(nodes.Text(txt, txt))
-
-
-class ASTGnuAttribute(ASTBase):
- def __init__(self, name: str, args: Any) -> None:
- self.name = name
- self.args = args
-
- def _stringify(self, transform: StringifyTransform) -> str:
- res = [self.name]
- if self.args:
- res.append('(')
- res.append(transform(self.args))
- res.append(')')
- return ''.join(res)
-
-
-class ASTGnuAttributeList(ASTAttribute):
- def __init__(self, attrs: List[ASTGnuAttribute]) -> None:
- self.attrs = attrs
-
- def _stringify(self, transform: StringifyTransform) -> str:
- res = ['__attribute__((']
- first = True
- for attr in self.attrs:
- if not first:
- res.append(', ')
- first = False
- res.append(transform(attr))
- res.append('))')
- return ''.join(res)
-
- def describe_signature(self, signode: TextElement) -> None:
- txt = str(self)
- signode.append(nodes.Text(txt, txt))
-
-
-class ASTIdAttribute(ASTAttribute):
- """For simple attributes defined by the user."""
-
- def __init__(self, id: str) -> None:
- self.id = id
-
- def _stringify(self, transform: StringifyTransform) -> str:
- return self.id
-
- def describe_signature(self, signode: TextElement) -> None:
- signode.append(nodes.Text(self.id, self.id))
-
-
-class ASTParenAttribute(ASTAttribute):
- """For paren attributes defined by the user."""
-
- def __init__(self, id: str, arg: str) -> None:
- self.id = id
- self.arg = arg
-
- def _stringify(self, transform: StringifyTransform) -> str:
- return self.id + '(' + self.arg + ')'
-
- def describe_signature(self, signode: TextElement) -> None:
- txt = str(self)
- signode.append(nodes.Text(txt, txt))
-
-
-################################################################################
# Expressions
################################################################################
@@ -4667,16 +4583,18 @@ class DefinitionParser(BaseParser):
_prefix_keys = ('class', 'struct', 'enum', 'union', 'typename')
- def __init__(self, definition: str, *,
- location: Union[nodes.Node, Tuple[str, int]],
- config: "Config") -> None:
- super().__init__(definition, location=location)
- self.config = config
-
@property
def language(self) -> str:
return 'C++'
+ @property
+ def id_attributes(self):
+ return self.config.cpp_id_attributes
+
+ @property
+ def paren_attributes(self):
+ return self.config.cpp_paren_attributes
+
def _parse_string(self) -> str:
if self.current_char != '"':
return None
@@ -4696,85 +4614,6 @@ class DefinitionParser(BaseParser):
self.pos += 1
return self.definition[startPos:self.pos]
- def _parse_balanced_token_seq(self, end: List[str]) -> str:
- # TODO: add handling of string literals and similar
- brackets = {'(': ')', '[': ']', '{': '}'}
- startPos = self.pos
- symbols = [] # type: List[str]
- while not self.eof:
- if len(symbols) == 0 and self.current_char in end:
- break
- if self.current_char in brackets.keys():
- symbols.append(brackets[self.current_char])
- elif len(symbols) > 0 and self.current_char == symbols[-1]:
- symbols.pop()
- elif self.current_char in ")]}":
- self.fail("Unexpected '%s' in balanced-token-seq." % self.current_char)
- self.pos += 1
- if self.eof:
- self.fail("Could not find end of balanced-token-seq starting at %d."
- % startPos)
- return self.definition[startPos:self.pos]
-
- def _parse_attribute(self) -> ASTAttribute:
- self.skip_ws()
- # try C++11 style
- startPos = self.pos
- if self.skip_string_and_ws('['):
- if not self.skip_string('['):
- self.pos = startPos
- else:
- # TODO: actually implement the correct grammar
- arg = self._parse_balanced_token_seq(end=[']'])
- if not self.skip_string_and_ws(']'):
- self.fail("Expected ']' in end of attribute.")
- if not self.skip_string_and_ws(']'):
- self.fail("Expected ']' in end of attribute after [[...]")
- return ASTCPPAttribute(arg)
-
- # try GNU style
- if self.skip_word_and_ws('__attribute__'):
- if not self.skip_string_and_ws('('):
- self.fail("Expected '(' after '__attribute__'.")
- if not self.skip_string_and_ws('('):
- self.fail("Expected '(' after '__attribute__('.")
- attrs = []
- while 1:
- if self.match(identifier_re):
- name = self.matched_text
- self.skip_ws()
- if self.skip_string_and_ws('('):
- self.fail('Parameterized GNU style attribute not yet supported.')
- attrs.append(ASTGnuAttribute(name, None))
- # TODO: parse arguments for the attribute
- if self.skip_string_and_ws(','):
- continue
- elif self.skip_string_and_ws(')'):
- break
- else:
- self.fail("Expected identifier, ')', or ',' in __attribute__.")
- if not self.skip_string_and_ws(')'):
- self.fail("Expected ')' after '__attribute__((...)'")
- return ASTGnuAttributeList(attrs)
-
- # try the simple id attributes defined by the user
- for id in self.config.cpp_id_attributes:
- if self.skip_word_and_ws(id):
- return ASTIdAttribute(id)
-
- # try the paren attributes defined by the user
- for id in self.config.cpp_paren_attributes:
- if not self.skip_string_and_ws(id):
- continue
- if not self.skip_string('('):
- self.fail("Expected '(' after user-defined paren-attribute.")
- arg = self._parse_balanced_token_seq(end=[')'])
- if not self.skip_string(')'):
- self.fail("Expected ')' to end user-defined paren-attribute.")
- return ASTParenAttribute(id, arg)
-
- return None
-
def _parse_literal(self) -> ASTLiteral:
# -> integer-literal
# | character-literal
@@ -7200,8 +7039,7 @@ class CPPDomain(Domain):
# add parens again for those that could be functions
if typ == 'any' or typ == 'func':
target += '()'
- parser = DefinitionParser(target, location=node,
- config=env.config)
+ parser = DefinitionParser(target, location=node, config=env.config)
try:
ast, isShorthand = parser.parse_xref_object()
except DefinitionError as e: