docgen now lists macro implementation status in the generated rst files. Adds POSIX definition link property to docgen json API (`posix-definition`) and changes the `defined` property of docgen json API to `c-definition`. Now that docgen's api is getting more specified, adds validation checks to docgen to start codifying the docgen api spec. To make sure this all looks good, I've added POSIX definition links to signal.h as a tester.
88 lines
3.5 KiB
Python
88 lines
3.5 KiB
Python
# ====- Information about standard headers used by docgen ----*- python -*--==#
|
|
#
|
|
# Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
|
# See https://llvm.org/LICENSE.txt for license information.
|
|
# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
|
#
|
|
# ==-------------------------------------------------------------------------==#
|
|
from pathlib import Path
|
|
from typing import Generator
|
|
|
|
|
|
class Header:
|
|
"""
|
|
Maintains implementation information about a standard header file:
|
|
* where does its implementation dir live
|
|
* where is its macros file
|
|
* where is its docgen json file
|
|
|
|
By convention, the macro-only part of a header file is in a header-specific
|
|
file somewhere in the directory tree with root at
|
|
``$LLVM_PROJECT_ROOT/libc/include/llvm-libc-macros``. Docgen expects that
|
|
if a macro is implemented, that it appears in a string
|
|
``#define MACRO_NAME`` in some ``*-macros.h`` file in the directory tree.
|
|
Docgen searches for this string in the file to set the implementation status
|
|
shown in the generated rst docs rendered as html for display at
|
|
<libc.llvm.org>.
|
|
|
|
By convention, each function for a header is implemented in a function-specific
|
|
cpp file somewhere in the directory tree with root at, e.g,
|
|
``$LLVM_PROJECT_ROOT/libc/src/fenv``. Some headers have architecture-specific
|
|
implementations, like ``math``, and some don't, like ``fenv``. Docgen uses the
|
|
presence of this function-specific cpp file to set the implementation status
|
|
shown in the generated rst docs rendered as html for display at
|
|
<libc.llvm.org>.
|
|
"""
|
|
|
|
def __init__(self, header_name: str):
|
|
"""
|
|
:param header_name: e.g., ``"threads.h"`` or ``"signal.h"``
|
|
"""
|
|
self.name = header_name
|
|
self.stem = header_name.rstrip(".h")
|
|
self.docgen_root = Path(__file__).parent
|
|
self.libc_root = self.docgen_root.parent.parent
|
|
self.docgen_json = self.docgen_root / Path(header_name).with_suffix(".json")
|
|
self.fns_dir = Path(self.libc_root, "src", self.stem)
|
|
self.macros_dir = Path(self.libc_root, "include", "llvm-libc-macros")
|
|
|
|
def macro_file_exists(self) -> bool:
|
|
for _ in self.__get_macro_files():
|
|
return True
|
|
|
|
return False
|
|
|
|
def fns_dir_exists(self) -> bool:
|
|
return self.fns_dir.exists() and self.fns_dir.is_dir()
|
|
|
|
def implements_fn(self, fn_name: str) -> bool:
|
|
for _ in self.fns_dir.glob(f"**/{fn_name}.cpp"):
|
|
return True
|
|
|
|
return False
|
|
|
|
def implements_macro(self, m_name: str) -> bool:
|
|
"""
|
|
Some macro files are in, e.g.,
|
|
``$LLVM_PROJECT_ROOT/libc/include/llvm-libc-macros/fenv-macros.h``,
|
|
but others are in subdirectories, e.g., ``signal.h`` has the macro
|
|
definitions in
|
|
``$LLVM_PROJECT_ROOT/libc/include/llvm-libc-macros/linux/signal-macros.h``.
|
|
|
|
:param m_name: name of macro, e.g., ``FE_ALL_EXCEPT``
|
|
"""
|
|
for f in self.__get_macro_files():
|
|
if f"#define {m_name}" in f.read_text():
|
|
return True
|
|
|
|
return False
|
|
|
|
def __get_macro_files(self) -> Generator[Path, None, None]:
|
|
"""
|
|
This function uses a glob on, e.g., ``"**/fcntl.macros.h"`` because the
|
|
macro file might be located in a subdirectory:
|
|
libc/include/llvm-libc-macros/fcntl-macros.h
|
|
libc/include/llvm-libc-macros/linux/fcntl-macros.h
|
|
"""
|
|
return self.macros_dir.glob(f"**/{self.stem}-macros.h")
|