diff options
-rw-r--r-- | docs/devel/qapi-code-gen.rst | 10 | ||||
-rw-r--r-- | scripts/qapi/parser.py | 73 | ||||
-rw-r--r-- | tests/qapi-schema/doc-bad-indent.err | 2 | ||||
-rw-r--r-- | tests/qapi-schema/doc-bad-indent.json | 3 | ||||
-rw-r--r-- | tests/qapi-schema/doc-good.json | 3 | ||||
-rw-r--r-- | tests/qapi-schema/doc-good.out | 3 |
6 files changed, 32 insertions, 62 deletions
diff --git a/docs/devel/qapi-code-gen.rst b/docs/devel/qapi-code-gen.rst index 6386b58..875f893 100644 --- a/docs/devel/qapi-code-gen.rst +++ b/docs/devel/qapi-code-gen.rst @@ -1074,10 +1074,14 @@ Indentation matters. Bad example:: # @none: None (no memory side cache in this proximity domain, # or cache associativity unknown) + # (since 5.0) -The description is parsed as a definition list with term "None (no -memory side cache in this proximity domain," and definition "or cache -associativity unknown)". +The last line's de-indent is wrong. The second and subsequent lines +need to line up with each other, like this:: + + # @none: None (no memory side cache in this proximity domain, + # or cache associativity unknown) + # (since 5.0) Section tags are case-sensitive and end with a colon. Good example:: diff --git a/scripts/qapi/parser.py b/scripts/qapi/parser.py index a4ff9b6..285c9ff 100644 --- a/scripts/qapi/parser.py +++ b/scripts/qapi/parser.py @@ -474,17 +474,21 @@ class QAPIDoc: self._parser = parser # optional section name (argument/member or section name) self.name = name + # section text without section name self.text = '' - # the expected indent level of the text of this section - self._indent = indent + # indentation to strip (None means indeterminate) + self._indent = None if self.name else 0 def append(self, line: str) -> None: - # Strip leading spaces corresponding to the expected indent level - # Blank lines are always OK. + line = line.rstrip() + if line: indent = must_match(r'\s*', line).end() - if self._indent < 0: - self._indent = indent + if self._indent is None: + # indeterminate indentation + if self.text != '': + # non-blank, non-first line determines indentation + self._indent = indent elif indent < self._indent: raise QAPIParseError( self._parser, @@ -492,7 +496,7 @@ class QAPIDoc: self._indent) line = line[self._indent:] - self.text += line.rstrip() + '\n' + self.text += line + '\n' class ArgSection(Section): def __init__(self, parser: QAPISchemaParser, @@ -622,22 +626,8 @@ class QAPIDoc: """ match = self._match_at_name_colon(line) if match: - # If line is "@arg: first line of description", find - # the index of 'f', which is the indent we expect for any - # following lines. We then remove the leading "@arg:" - # from line and replace it with spaces so that 'f' has the - # same index as it did in the original line and can be - # handled the same way we will handle following lines. - name = match.group(1) - indent = match.end() - line = line[indent:] - if not line: - # Line was just the "@arg:" header - # The next non-blank line determines expected indent - indent = -1 - else: - line = ' ' * indent + line - self._start_args_section(name, indent) + line = line[match.end():] + self._start_args_section(match.group(1), 0) elif self._match_section_tag(line): self._append_line = self._append_various_line self._append_various_line(line) @@ -657,22 +647,8 @@ class QAPIDoc: def _append_features_line(self, line: str) -> None: match = self._match_at_name_colon(line) if match: - # If line is "@arg: first line of description", find - # the index of 'f', which is the indent we expect for any - # following lines. We then remove the leading "@arg:" - # from line and replace it with spaces so that 'f' has the - # same index as it did in the original line and can be - # handled the same way we will handle following lines. - name = match.group(1) - indent = match.end() - line = line[indent:] - if not line: - # Line was just the "@arg:" header - # The next non-blank line determines expected indent - indent = -1 - else: - line = ' ' * indent + line - self._start_features_section(name, indent) + line = line[match.end():] + self._start_features_section(match.group(1), 0) elif self._match_section_tag(line): self._append_line = self._append_various_line self._append_various_line(line) @@ -704,21 +680,8 @@ class QAPIDoc: % (match.group(1), self.sections[0].name)) match = self._match_section_tag(line) if match: - # If line is "Section: first line of description", find - # the index of 'f', which is the indent we expect for any - # following lines. We then remove the leading "Section:" - # from line and replace it with spaces so that 'f' has the - # same index as it did in the original line and can be - # handled the same way we will handle following lines. - indent = must_match(r'\S*:\s*', line).end() - line = line[indent:] - if not line: - # Line was just the "Section:" header - # The next non-blank line determines expected indent - indent = 0 - else: - line = ' ' * indent + line - self._start_section(match.group(1), indent) + line = line[match.end():] + self._start_section(match.group(1), 0) self._append_freeform(line) @@ -754,7 +717,7 @@ class QAPIDoc: self.sections.append(new_section) def _switch_section(self, new_section: 'QAPIDoc.Section') -> None: - text = self._section.text = self._section.text.strip() + text = self._section.text = self._section.text.strip('\n') # Only the 'body' section is allowed to have an empty body. # All other sections, including anonymous ones, must have text. diff --git a/tests/qapi-schema/doc-bad-indent.err b/tests/qapi-schema/doc-bad-indent.err index 6784453..3c9699a 100644 --- a/tests/qapi-schema/doc-bad-indent.err +++ b/tests/qapi-schema/doc-bad-indent.err @@ -1 +1 @@ -doc-bad-indent.json:6:1: unexpected de-indent (expected at least 4 spaces) +doc-bad-indent.json:7:1: unexpected de-indent (expected at least 2 spaces) diff --git a/tests/qapi-schema/doc-bad-indent.json b/tests/qapi-schema/doc-bad-indent.json index edde8f2..3f22a27 100644 --- a/tests/qapi-schema/doc-bad-indent.json +++ b/tests/qapi-schema/doc-bad-indent.json @@ -3,6 +3,7 @@ ## # @foo: # @a: line one -# line two is wrongly indented +# line two +# line three is wrongly indented ## { 'command': 'foo', 'data': { 'a': 'int' } } diff --git a/tests/qapi-schema/doc-good.json b/tests/qapi-schema/doc-good.json index 34c3dcb..354dfdf 100644 --- a/tests/qapi-schema/doc-good.json +++ b/tests/qapi-schema/doc-good.json @@ -144,7 +144,8 @@ # description starts on a new line, # indented # -# @arg2: the second argument +# @arg2: description starts on the same line +# remainder indented differently # # Features: # @cmd-feat1: a feature diff --git a/tests/qapi-schema/doc-good.out b/tests/qapi-schema/doc-good.out index 277371a..24d9ea9 100644 --- a/tests/qapi-schema/doc-good.out +++ b/tests/qapi-schema/doc-good.out @@ -161,7 +161,8 @@ doc symbol=cmd description starts on a new line, indented arg=arg2 -the second argument +description starts on the same line +remainder indented differently arg=arg3 feature=cmd-feat1 |