From 6d65f8365e3a51bd3bbae49415d6113a2b220ea9 Mon Sep 17 00:00:00 2001 From: Sebastian Huber Date: Tue, 24 Nov 2020 09:15:24 +0100 Subject: interfacedoc: Support macros --- rtemsspec/content.py | 11 ++-- rtemsspec/interfacedoc.py | 29 ++++++--- rtemsspec/tests/test_interfacedoc.py | 119 ++++++++++++++++++++++++++++++++++- 3 files changed, 144 insertions(+), 15 deletions(-) diff --git a/rtemsspec/content.py b/rtemsspec/content.py index 7d56dec0..c8e32afa 100644 --- a/rtemsspec/content.py +++ b/rtemsspec/content.py @@ -767,7 +767,8 @@ class CContent(Content): def call_function(self, ret: Optional[str], name: str, - params: Optional[List[str]] = None) -> None: + params: Optional[List[str]] = None, + semicolon: str = ";") -> None: """ Adds a function call. """ if ret: space = " " @@ -779,16 +780,16 @@ class CContent(Content): param_line = "( " + ", ".join(params) + " )" else: param_line = "()" - line = f"{ret}{space}{name}{param_line};" + line = f"{ret}{space}{name}{param_line}{semicolon}" if len(self._indent) + len(line) > 79: if params: - self._function(ret, name, params, param_line, space, ";") + self._function(ret, name, params, param_line, space, semicolon) elif ret: self.add(ret) with self.indent(): - self.add(f"{name}();") + self.add(f"{name}(){semicolon}") else: - self.add(f"{name}();") + self.add(f"{name}(){semicolon}") else: self.add(line) diff --git a/rtemsspec/interfacedoc.py b/rtemsspec/interfacedoc.py index e77bd675..6109a711 100644 --- a/rtemsspec/interfacedoc.py +++ b/rtemsspec/interfacedoc.py @@ -28,7 +28,7 @@ This module provides functions for the generation of interface documentation. import functools import os -from typing import Any, Callable, Dict, List, Tuple +from typing import Any, Dict, List, Tuple from rtemsspec.content import CContent, enabled_by_to_exp, ExpressionMapper from rtemsspec.sphinxcontent import get_label, get_reference, SphinxContent, \ @@ -36,7 +36,6 @@ from rtemsspec.sphinxcontent import get_label, get_reference, SphinxContent, \ from rtemsspec.items import Item, ItemCache, ItemGetValueContext, ItemMapper ItemMap = Dict[str, Item] -AddDefinition = Callable[[CContent, ItemMapper, Item, Dict[str, Any]], None] INTERFACE = "Interface" @@ -69,6 +68,7 @@ class _Mapper(SphinxMapper): def __init__(self, item: Item): super().__init__(item) self.add_get_value("interface/function:/name", _get_value_function) + self.add_get_value("interface/macro:/name", _get_value_function) def _generate_introduction(target: str, group: Item, @@ -107,17 +107,30 @@ def _generate_introduction(target: str, group: Item, def _add_function_definition(content: CContent, mapper: ItemMapper, item: Item, value: Dict[str, Any]) -> None: - name = item["name"] ret = mapper.substitute(value["return"]) + name = item["name"] params = [mapper.substitute(param) for param in value["params"]] content.declare_function(ret, name, params) +def _add_macro_definition(content: CContent, _mapper: ItemMapper, item: Item, + _value: Dict[str, Any]) -> None: + ret = "#define" + name = item["name"] + params = [param["name"] for param in item["params"]] + content.call_function(ret, name, params, semicolon="") + + +_ADD_DEFINITION = { + "interface/function": _add_function_definition, + "interface/macro": _add_macro_definition, +} + + def _add_definition(content: CContent, mapper: ItemMapper, item: Item, - prefix: str, value: Dict[str, Any], - add_definition: AddDefinition) -> None: + prefix: str, value: Dict[str, Any]) -> None: # pylint: disable=too-many-arguments - assert item.type == "interface/function" + add_definition = _ADD_DEFINITION[item.type] default = value["default"] variants = value["variants"] if variants: @@ -149,7 +162,7 @@ def _generate_directive(content: SphinxContent, mapper: _Mapper, with content.directive("code-block", "c"): code = CContent() _add_definition(code, code_mapper, item, "definition", - item["definition"], _add_function_definition) + item["definition"]) content.add(code) if item["params"]: content.add(".. rubric:: PARAMETERS:") @@ -229,7 +242,7 @@ def generate(config: list, item_cache: ItemCache) -> None: group = item_cache[doc_config["group"]] assert group.type == "interface/group" for child in group.children("interface-ingroup"): - if child.type == "interface/function": + if child.type in ["interface/function", "interface/macro"]: items.append(child) items.sort(key=functools.partial( _directive_key, list(group.parents("placement-order")))) diff --git a/rtemsspec/tests/test_interfacedoc.py b/rtemsspec/tests/test_interfacedoc.py index 5109478c..e7073027 100644 --- a/rtemsspec/tests/test_interfacedoc.py +++ b/rtemsspec/tests/test_interfacedoc.py @@ -78,6 +78,9 @@ Introduction .. spec:/func4 .. spec:/func2 .. spec:/func3 +.. spec:/macro +.. spec:/macro2 +.. spec:/macro3 The directives provided by the Group B are: @@ -87,6 +90,12 @@ The directives provided by the Group B are: * :ref:`InterfaceVeryLongFunction` - Very long function brief description. * :ref:`InterfaceVoidFunction` + +* :ref:`InterfaceVERYLONGMACRO` - Very long macro brief description. + +* :ref:`InterfaceMACRO` - Short macro brief description. + +* :ref:`InterfaceMACRO` - Macro without parameters. """ assert content == src.read() @@ -227,6 +236,112 @@ VoidFunction() #if 1 void VoidFunction( void ); #endif + +.. Generated from spec:/macro + +.. raw:: latex + + \\clearpage + +.. index:: VERY_LONG_MACRO() + +.. _InterfaceVERYLONGMACRO: + +VERY_LONG_MACRO() +----------------- + +Very long macro brief description. + +.. rubric:: CALLING SEQUENCE: + +.. code-block:: c + + #define VERY_LONG_MACRO( + VeryLongParam0, + VeryLongParam1, + VeryLongParam2, + VeryLongParam3 + ) + +.. rubric:: PARAMETERS: + +``VeryLongParam0`` + This parameter is very long parameter 0 with some super important and extra + very long description which makes a lot of sense. + +``VeryLongParam1`` + This parameter is very long parameter 1. + +``VeryLongParam2`` + This parameter is very long parameter 2. + +``VeryLongParam3`` + This parameter is very long parameter 3. + +.. rubric:: RETURN VALUES: + +``1`` + is returned, in case A. + +``2`` + is returned, in case B. + +Sometimes some value. + +.. Generated from spec:/macro2 + +.. raw:: latex + + \\clearpage + +.. index:: MACRO() + +.. _InterfaceMACRO: + +MACRO() +------- + +Short macro brief description. + +.. rubric:: CALLING SEQUENCE: + +.. code-block:: c + + #if defined(0) + #define MACRO( Param0 ) + #else + #define MACRO( Param0 ) + #endif + +.. rubric:: PARAMETERS: + +``Param0`` + This parameter is parameter 0. + +.. rubric:: RETURN VALUES: + +Sometimes some value. + +.. Generated from spec:/macro3 + +.. raw:: latex + + \\clearpage + +.. index:: MACRO() + +.. _InterfaceMACRO: + +MACRO() +------- + +Macro without parameters. + +.. rubric:: CALLING SEQUENCE: + +.. code-block:: c + + #define MACRO() """ assert content == src.read() @@ -328,7 +443,7 @@ Function brief description. Function description. References to :ref:`InterfaceVeryLongFunction`, :c:type:`Integer`, :c:type:`Enum`, :c:macro:`DEFINE`, -:c:func:`VERY_LONG_MACRO`, Variable, :c:macro:`ENUMERATOR_0`, :c:type:`Struct`, -:ref:`a`, and interface. +:ref:`InterfaceVERYLONGMACRO`, Variable, :c:macro:`ENUMERATOR_0`, +:c:type:`Struct`, :ref:`a`, and interface. """ assert content == src.read() -- cgit v1.2.3