docs: begin building the documentation style guide.
This commit is contained in:
parent
877a1062a6
commit
8c1c9f2d26
|
@ -875,7 +875,7 @@ class Value(metaclass=ABCMeta):
|
|||
|
||||
The shape of the result is the same as the shape of :py:`self`, even for unsigned values.
|
||||
|
||||
.. important::
|
||||
.. warning::
|
||||
|
||||
In Python, :py:`~0` equals :py:`-1`. In Amaranth, :py:`~C(0)` equals :py:`C(1)`.
|
||||
This is the only case where an Amaranth operator deviates from the Python operator
|
||||
|
|
|
@ -14,7 +14,7 @@ __all__ = ["FrozenMemory", "MemoryData", "Memory", "ReadPort", "WritePort", "Dum
|
|||
|
||||
@final
|
||||
class FrozenMemory(Exception):
|
||||
"""This exception is raised when a memory array is being modified after elaboration."""
|
||||
"""Exception raised when a memory array is being modified after elaboration."""
|
||||
|
||||
|
||||
@final
|
||||
|
@ -194,7 +194,7 @@ class MemoryData:
|
|||
value that can be used to read and write the selected memory row in a simulation testbench,
|
||||
without having to create a memory port.
|
||||
|
||||
.. important::
|
||||
.. tip::
|
||||
|
||||
Even in a simulation, the value returned by this function cannot be used in a module;
|
||||
it can only be used with :py:`sim.get()` and :py:`sim.set()`.
|
||||
|
|
|
@ -689,7 +689,7 @@ class Signature(metaclass=SignatureMeta):
|
|||
:class:`Signature` can be used as a base class to define :ref:`customized <wiring-customizing>`
|
||||
signatures and interface objects.
|
||||
|
||||
.. important::
|
||||
.. warning::
|
||||
|
||||
:class:`Signature` objects are immutable. Classes inheriting from :class:`Signature` must
|
||||
ensure this remains the case when additional functionality is added.
|
||||
|
@ -1143,7 +1143,7 @@ class PureInterface:
|
|||
:meth:`Signature.create`, but it can also be used in any other context where an interface
|
||||
object needs to be created without the overhead of defining a class for it.
|
||||
|
||||
.. important::
|
||||
.. tip::
|
||||
|
||||
Any object can be an interface object; it only needs a :py:`signature` property containing
|
||||
a compliant signature. It is **not** necessary to use :class:`PureInterface` in order to
|
||||
|
@ -1678,7 +1678,7 @@ class Component(Elaboratable):
|
|||
def signature(self):
|
||||
"""The signature of the component.
|
||||
|
||||
.. important::
|
||||
.. warning::
|
||||
|
||||
Do not override this property. Once a component is constructed, its :attr:`signature`
|
||||
property must always return the same :class:`Signature` instance. The constructor
|
||||
|
|
|
@ -103,14 +103,49 @@ Occasionally, the documentation builder will persist in rendering an incorrect o
|
|||
$ pdm run document-live -a
|
||||
|
||||
|
||||
Documentation style guide
|
||||
=========================
|
||||
|
||||
.. warning::
|
||||
|
||||
Our documentation style guidelines are evolving, and this section is incomplete.
|
||||
|
||||
Some of the fundamental guidelines are:
|
||||
|
||||
* **Document the contract and the affordances,** not the implementation. This is especially important because the Amaranth documentation is *the* source of truth for its semantics; the tests and the implementation source code are secondary to it, and the RFCs exist to record the process rather than document the outcome.
|
||||
* **Shape the code to be documentable.** This is a corollary to the previous guideline. If an interface is difficult to describe in a way that is readily understood, then it may need to be changed. Many breaking changes in Amaranth were done to make the language and libraries easier to understand.
|
||||
* **Be consistent.** Take inspiration from existing documentation for similar modules. However, don't be consistent at the expense of clarity.
|
||||
* **Be concise.** It is easy to write boilerplate, and difficult to navigate through it.
|
||||
|
||||
* In particular, if the `Parameters` section of the class docstring describes a parameter, it is expected that the same parameter will be available as a class attribute (usually, but not always, read-only), and there is no need to additionally document this fact. If there isn't a corresponding attribute it should likely be added.
|
||||
* There is no need to individually document every argument and every return value of every method. This mainly creates clutter. The goal in writing documentation is transferring knowledge, not ticking boxes.
|
||||
|
||||
Some of the formatting guidelines are:
|
||||
|
||||
* Limit code (including docstrings, where possible--some of the Sphinx syntax does not allow wrapping) to 100 columns in ``.py`` files, but do not break paragraphs in ``.rst`` files.
|
||||
* Use ``###...#`` for first-level headings, ``===...=`` for second-level headings, ``---...-`` for third-level headings.
|
||||
* Use the ``:py:`...``` syntax for inline Python code references (even trivial ones, e.g. ``:py:`var_name```), ``.. testcode::`` for most Python code blocks (use ``.. code::`` where the code cannot or should not be tested), ``.. doctest::`` for doctests.
|
||||
* Use admonitions sparingly, and only of the following kinds:
|
||||
|
||||
* ``.. warning::`` for text which MUST be paid attention to, or else unexpected bad things may happen. This is the most noticeable kind, rendered in yellow at the moment.
|
||||
* ``.. tip::`` for text which SHOULD be paid attention to, otherwise annoyance may happen. This is the second most noticeable kind, rendered in bright blue-green at the moment.
|
||||
* ``.. note::`` for text which MAY be paid attention to, but which is not key for understanding of the topic as a whole. This is the least noticeable kind, rendered in faint blue at the moment.
|
||||
* ``.. todo::`` may also be used for incomplete sections.
|
||||
|
||||
* For methods, phrase the short description (first line of docstring) like ``Do the thing.``, i.e. as an imperative sentence.
|
||||
* For properties, phrase the short description (first line of docstring) like ``Value of thing.``, i.e. as a declarative sentence.
|
||||
* When documenting signatures of interfaces, as well as components, use the (non-standard) `Members` section to document their interface members, and only that section; do not document them in an `Attributes` section.
|
||||
* If an anchor for a section is needed, namespace it, e.g. the ``.. _lang-assignable:`` anchor is a part of the ``lang`` namespace. Anchor names are global.
|
||||
|
||||
|
||||
Contributing your changes
|
||||
=========================
|
||||
|
||||
.. attention::
|
||||
.. warning::
|
||||
|
||||
Our code style guidelines are evolving, and we will eventually have a formal document listing them.
|
||||
Our code style guidelines are evolving, and we do not yet have a formal document listing them.
|
||||
|
||||
At the moment there is no formal style guide for source code. We ask that you do your best effort to keep the code that you add or modify similar in style as well as in spirit to the code surrounding it, and we may ask you to change it during review. When in doubt, submit your code as-is.
|
||||
We ask that you do your best effort to keep the code that you add or modify similar in style as well as in spirit to the code surrounding it, and we may ask you to change it during review. When in doubt, submit your code as-is.
|
||||
|
||||
|
||||
Weekly meetings
|
||||
|
|
|
@ -811,9 +811,9 @@ Crucially, this means that any Python object can be added to an array; the only
|
|||
|
||||
An array becomes immutable after it is indexed for the first time. The elements of the array do not themselves become immutable, but it is not recommended to mutate them as the behavior can become unpredictable.
|
||||
|
||||
.. important::
|
||||
.. warning::
|
||||
|
||||
Each time an array proxy object with ``n`` elements is used in an expression, it generates a multiplexer with ``n`` branches. However, using ``k`` of such array proxy objects in an expression generates a multiplexer with ``n**k`` branches. This can generate extremely large circuits that may quickly exhaust the resources of the synthesis target or even the available RAM.
|
||||
Each time an array proxy object with :py:`n` elements is used in an expression, it generates a multiplexer with :py:`n` branches. However, using :py:`k` of such array proxy objects in an expression generates a multiplexer with :py:`n**k` branches. This can generate extremely large circuits that may quickly exhaust the resources of the synthesis target or even the available RAM.
|
||||
|
||||
|
||||
.. _lang-data:
|
||||
|
@ -1499,7 +1499,7 @@ The :meth:`~Elaboratable.elaborate` method must either return an instance of :cl
|
|||
|
||||
The :py:`platform` argument received by the :meth:`~Elaboratable.elaborate` method can be :py:`None`, an instance of :ref:`a built-in platform <platform>`, or a custom object. It is used for `dependency injection <https://en.wikipedia.org/wiki/Dependency_injection>`_ and to contain the state of a design while it is being elaborated.
|
||||
|
||||
.. important::
|
||||
.. warning::
|
||||
|
||||
The :meth:`~Elaboratable.elaborate` method should not modify the ``self`` object it receives other than for debugging and experimentation. Elaborating the same design twice with two identical platform objects should produce two identical netlists. If the design needs to be modified after construction, this should happen before elaboration.
|
||||
|
||||
|
@ -1665,7 +1665,7 @@ The renaming of the ``sync`` clock domain in it causes the behavior of the final
|
|||
m.d.video += count.eq(count + 1)
|
||||
m.d.comb += zero.eq(count == 0)
|
||||
|
||||
.. tip::
|
||||
.. warning::
|
||||
|
||||
A combinatorial signal can change synchronously to a clock domain, as in the example above, in which case it may only be sampled from the same clock domain unless explicitly synchronized. Renaming a clock domain must be assumed to potentially affect any output of an elaboratable.
|
||||
|
||||
|
|
Loading…
Reference in a new issue