From e422638774420ad264a0cab78a8a2ab6f099544c Mon Sep 17 00:00:00 2001 From: Martin Belanger Date: Fri, 7 Aug 2026 16:26:40 -0400 Subject: [PATCH 1/2] libnvme: rename sysfs to attrs and move generated files to a subdir "sysfs" is Linux-only terminology for a mechanism meant to work on Windows too (and possibly others). Also moves the generated .c/.h files into src/nvme/generated/ Signed-off-by: Martin Belanger --- ...ccessors.md => generate_attr_accessors.md} | 70 +++--- .../libnvme3/{ctrl-sysfs.i => ctrl-attrs.i} | 2 +- libnvme/libnvme3/meson.build | 4 +- libnvme/libnvme3/{ns-sysfs.i => ns-attrs.i} | 2 +- libnvme/libnvme3/nvme.i | 8 +- .../libnvme3/{path-sysfs.i => path-attrs.i} | 2 +- .../{subsys-sysfs.i => subsys-attrs.i} | 2 +- libnvme/src/{ctrl-sysfs.ld => ctrl-attrs.ld} | 2 +- libnvme/src/libnvme.h.in | 8 +- libnvme/src/meson.build | 57 +++-- libnvme/src/{ns-sysfs.ld => ns-attrs.ld} | 2 +- ...ssors_specs.py => attr_accessors_specs.py} | 126 +++++----- ...-fabrics.c => ctrl-attrs-custom-fabrics.c} | 10 +- ...stom-linux.c => ctrl-attrs-custom-linux.c} | 20 +- ...brics.c => ctrl-attrs-custom-no-fabrics.c} | 0 ...s-custom-win.c => ctrl-attrs-custom-win.c} | 24 +- .../{ctrl-sysfs.c => generated/ctrl-attrs.c} | 236 +++++++++--------- .../{ctrl-sysfs.h => generated/ctrl-attrs.h} | 18 +- .../nvme/{ns-sysfs.c => generated/ns-attrs.c} | 56 ++--- .../nvme/{ns-sysfs.h => generated/ns-attrs.h} | 14 +- .../path-attrs-linux.c} | 56 ++--- .../path-attrs-win.c} | 0 .../{path-sysfs.c => generated/path-attrs.c} | 28 +-- .../{path-sysfs.h => generated/path-attrs.h} | 14 +- .../subsys-attrs.c} | 88 +++---- .../subsys-attrs.h} | 14 +- ...custom-linux.c => ns-attrs-custom-linux.c} | 162 ++++++------ ...sfs-custom-win.c => ns-attrs-custom-win.c} | 76 +++--- ...custom-win.c => path-attrs-custom-linux.c} | 4 +- ...custom-linux.c => path-attrs-custom-win.c} | 4 +- libnvme/src/nvme/private-tree.h | 18 +- libnvme/src/nvme/private.h | 26 +- libnvme/src/nvme/tree-fabrics.c | 4 +- libnvme/src/nvme/tree-linux.c | 6 +- libnvme/src/nvme/tree-win.c | 6 +- libnvme/src/nvme/tree.c | 24 +- libnvme/src/{path-sysfs.ld => path-attrs.ld} | 2 +- .../src/{subsys-sysfs.ld => subsys-attrs.ld} | 2 +- libnvme/test/meson.build | 4 +- libnvme/tools/check-public-symbols.py | 10 +- libnvme/tools/generator/generate_accessors.py | 134 +++++----- ...ccessors.py => generate_attr_accessors.py} | 87 ++++--- libnvme/tools/generator/meson.build | 12 +- ...-accessors.sh => update-attr-accessors.sh} | 43 ++-- 44 files changed, 764 insertions(+), 723 deletions(-) rename libnvme/design/tooling/{generate_sysfs_accessors.md => generate_attr_accessors.md} (68%) rename libnvme/libnvme3/{ctrl-sysfs.i => ctrl-attrs.i} (99%) rename libnvme/libnvme3/{ns-sysfs.i => ns-attrs.i} (98%) rename libnvme/libnvme3/{path-sysfs.i => path-attrs.i} (98%) rename libnvme/libnvme3/{subsys-sysfs.i => subsys-attrs.i} (97%) rename libnvme/src/{ctrl-sysfs.ld => ctrl-attrs.ld} (98%) rename libnvme/src/{ns-sysfs.ld => ns-attrs.ld} (97%) rename libnvme/src/nvme/{sysfs_accessors_specs.py => attr_accessors_specs.py} (81%) rename libnvme/src/nvme/{ctrl-sysfs-custom-fabrics.c => ctrl-attrs-custom-fabrics.c} (81%) rename libnvme/src/nvme/{ctrl-sysfs-custom-linux.c => ctrl-attrs-custom-linux.c} (73%) rename libnvme/src/nvme/{ctrl-sysfs-custom-no-fabrics.c => ctrl-attrs-custom-no-fabrics.c} (100%) rename libnvme/src/nvme/{ctrl-sysfs-custom-win.c => ctrl-attrs-custom-win.c} (70%) rename libnvme/src/nvme/{ctrl-sysfs.c => generated/ctrl-attrs.c} (59%) rename libnvme/src/nvme/{ctrl-sysfs.h => generated/ctrl-attrs.h} (96%) rename libnvme/src/nvme/{ns-sysfs.c => generated/ns-attrs.c} (72%) rename libnvme/src/nvme/{ns-sysfs.h => generated/ns-attrs.h} (96%) rename libnvme/src/nvme/{path-sysfs-linux.c => generated/path-attrs-linux.c} (71%) rename libnvme/src/nvme/{path-sysfs-win.c => generated/path-attrs-win.c} (100%) rename libnvme/src/nvme/{path-sysfs.c => generated/path-attrs.c} (72%) rename libnvme/src/nvme/{path-sysfs.h => generated/path-attrs.h} (93%) rename libnvme/src/nvme/{subsys-sysfs.c => generated/subsys-attrs.c} (58%) rename libnvme/src/nvme/{subsys-sysfs.h => generated/subsys-attrs.h} (91%) rename libnvme/src/nvme/{ns-sysfs-custom-linux.c => ns-attrs-custom-linux.c} (69%) rename libnvme/src/nvme/{ns-sysfs-custom-win.c => ns-attrs-custom-win.c} (70%) rename libnvme/src/nvme/{path-sysfs-custom-win.c => path-attrs-custom-linux.c} (74%) rename libnvme/src/nvme/{path-sysfs-custom-linux.c => path-attrs-custom-win.c} (74%) rename libnvme/src/{path-sysfs.ld => path-attrs.ld} (97%) rename libnvme/src/{subsys-sysfs.ld => subsys-attrs.ld} (97%) rename libnvme/tools/generator/{generate_sysfs_accessors.py => generate_attr_accessors.py} (88%) mode change 100644 => 100755 rename libnvme/tools/generator/{update-sysfs-accessors.sh => update-attr-accessors.sh} (85%) diff --git a/libnvme/design/tooling/generate_sysfs_accessors.md b/libnvme/design/tooling/generate_attr_accessors.md similarity index 68% rename from libnvme/design/tooling/generate_sysfs_accessors.md rename to libnvme/design/tooling/generate_attr_accessors.md index f3e756b4cf..b65a8a7d1e 100644 --- a/libnvme/design/tooling/generate_sysfs_accessors.md +++ b/libnvme/design/tooling/generate_attr_accessors.md @@ -1,12 +1,12 @@ -# Generate Sysfs Accessors Tool +# Generate Attribute Accessors Tool -This tool generates an **opaque, sysfs-backed C struct** and its accessor functions from a **Python dict**, rather than from an annotated header the way `generate_accessors.py` does. It drives `struct libnvme_ctrl_sysfs`, `struct libnvme_path_sysfs`, `struct libnvme_ns_sysfs`, and `struct libnvme_subsystem_sysfs`. +This tool generates an **opaque, lazily-loaded C struct** and its accessor functions from a **Python dict**, rather than from an annotated header the way `generate_accessors.py` does. It drives `struct libnvme_ctrl_attrs`, `struct libnvme_path_attrs`, `struct libnvme_ns_attrs`, and `struct libnvme_subsystem_attrs`. ------ ## Why this tool exists, separate from `generate_accessors.py` -`generate_accessors.py`'s whole model is "parse a struct out of a shared header, emit accessors alongside it — the struct keeps living in that header." A sysfs-backed struct needs the opposite: nobody outside a small, fixed set of generated `.c` files may ever see its layout, not even via a private header, since anything sitting in a header eventually gets included by someone. That means the struct definition itself must be generator *output*, emitted straight into each consuming `.c` file, never generator *input* — there is no header to parse, so a dict is the input instead. +`generate_accessors.py`'s whole model is "parse a struct out of a shared header, emit accessors alongside it — the struct keeps living in that header." A lazily-loaded struct needs the opposite: nobody outside a small, fixed set of generated `.c` files may ever see its layout, not even via a private header, since anything sitting in a header eventually gets included by someone. That means the struct definition itself must be generator *output*, emitted straight into each consuming `.c` file, never generator *input* — there is no header to parse, so a dict is the input instead. This tool does not duplicate `generate_accessors.py`'s machinery. It imports it as a library and reuses its `Member` model and its emitters (the getter/setter bodies, the SWIG fragment, the `.ld` placement); only the frontend differs. @@ -14,7 +14,7 @@ This tool does not duplicate `generate_accessors.py`'s machinery. It imports it ## Getter shape: every getter returns `int` and takes a caller default -Every sysfs-backed getter returns `int` and delivers its value through an out-param, plus a caller-supplied default: +Every lazily-loaded getter returns `int` and delivers its value through an out-param, plus a caller-supplied default: ```c int libnvme_ctrl_get_model(const struct libnvme_ctrl *p, const char **val, const char *dflt); @@ -38,7 +38,7 @@ Setters keep their original shape (`void`) — a `writable` member's value is al ## Scope: what's deliberately excluded -`transport`, `traddr`, `trsvcid`, `host_traddr`, `host_iface`, `subsysnqn`, and `address` are **not** in `CTRL_SYSFS`, even though they're also read from sysfs. Each is set exactly once, unconditionally, at ctrl-creation time (from connect-time params or from resolving the ctrl's identity during a scan), and is read regardless of whether any getter is ever called. Laziness buys nothing for a value that's always resolved immediately either way — the whole point of this mechanism is deferring reads a caller might never need. These fields stay plain, eager fields on the owning struct. +`transport`, `traddr`, `trsvcid`, `host_traddr`, `host_iface`, `subsysnqn`, and `address` are **not** in `CTRL_ATTRS`, even though they're also read from sysfs. Each is set exactly once, unconditionally, at ctrl-creation time (from connect-time params or from resolving the ctrl's identity during a scan), and is read regardless of whether any getter is ever called. Laziness buys nothing for a value that's always resolved immediately either way — the whole point of this mechanism is deferring reads a caller might never need. These fields stay plain, eager fields on the owning struct. ------ @@ -50,23 +50,23 @@ meson compile -C update-accessors regenerates every spec's `.h`/`.c`/`.i` alongside the other accessor families (aliased target, same as `update-common-accessors` and `update-fabrics-accessors`). Configuring with `-Dcheck-accessors=true` runs the same target read-only, for CI drift detection. -Every spec's `.ld` is **not** part of that auto-update — same as `accessors.ld`/`accessors-fabrics.ld`, which version section a symbol belongs to is a maintainer decision, so `update-sysfs-accessors.sh` only diffs it and prints a `Symbols to ADD`/`Symbols to REMOVE` report; you edit the file by hand. Pre-3.0, "add" means adding the line to the spec's existing top-level section, and "remove" means deleting the line, since ABI breaks are intentional and permitted before the 3.0 release. After a stable release, a symbol that genuinely needs to disappear is an ABI break no `.ld` edit can express by itself — it needs a SONAME bump (`libnvme_so_version` in the top-level `meson.build`), not just a version-script change. A brand-new spec's `.ld` does not exist yet the first time it is generated; the script reports every symbol as "to add" and tells you to create the file by hand with a fresh top-level tag. +Every spec's `.ld` is **not** part of that auto-update — same as `accessors.ld`/`accessors-fabrics.ld`, which version section a symbol belongs to is a maintainer decision, so `update-attr-accessors.sh` only diffs it and prints a `Symbols to ADD`/`Symbols to REMOVE` report; you edit the file by hand. Pre-3.0, "add" means adding the line to the spec's existing top-level section, and "remove" means deleting the line, since ABI breaks are intentional and permitted before the 3.0 release. After a stable release, a symbol that genuinely needs to disappear is an ABI break no `.ld` edit can express by itself — it needs a SONAME bump (`libnvme_so_version` in the top-level `meson.build`), not just a version-script change. A brand-new spec's `.ld` does not exist yet the first time it is generated; the script reports every symbol as "to add" and tells you to create the file by hand with a fresh top-level tag. To run this generator on its own, without the other two: ``` -./generate_sysfs_accessors.py --specs --out-dir [--ld-out-dir ] [--swig-out-dir ] [--check] +./generate_attr_accessors.py --specs --out-dir [--ld-out-dir ] [--swig-out-dir ] [--check] ``` -`--specs` is the path to the module providing `SYSFS_SPECS` (e.g. `../../src/nvme/sysfs_accessors_specs.py`) — a list of struct spec dicts. Every entry in the list is generated in this one run; there is no per-struct selection flag. `--out-dir` is the directory to write the generated `.h`/`.c` files into. `--ld-out-dir` is where the `.ld` file goes, alongside the other version scripts (defaults to `--out-dir`). `--swig-out-dir` is where the `.i` fragment goes (defaults to `--out-dir`). `--check` runs read-only: it exits non-zero and lists which files are stale instead of writing them. +`--specs` is the path to the module providing `ATTR_SPECS` (e.g. `../../src/nvme/attr_accessors_specs.py`) — a list of struct spec dicts. Every entry in the list is generated in this one run; there is no per-struct selection flag. `--out-dir` is the directory whose `generated/` subdirectory receives the generated `.h`/`.c` files (see "Generated file layout" below for why they're kept in their own subdirectory). `--ld-out-dir` is where the `.ld` file goes, alongside the other version scripts (defaults to `--out-dir`, not its `generated/` subdirectory — the `.ld` is hand-maintained, not generator-owned). `--swig-out-dir` is where the `.i` fragment goes (defaults to `--out-dir`). `--check` runs read-only: it exits non-zero and lists which files are stale instead of writing them. ------ -## How to add a new plain sysfs attribute +## How to add a new plain attribute -Most changes to a sysfs-backed struct are this case: one new field, backed by one sysfs attribute file, no special loader, present the same way on every platform. +Most changes to a lazily-loaded struct are this case: one new field, backed by one sysfs attribute file, no special loader, present the same way on every platform. -1. Open `sysfs_accessors_specs.py` and find the relevant spec's `['members']` list. +1. Open `attr_accessors_specs.py` and find the relevant spec's `['members']` list. 2. Add a new dict entry: ```python { @@ -78,11 +78,11 @@ Most changes to a sysfs-backed struct are this case: one new field, backed by on ``` 3. Decide `reconfigure_reset`: - `True` if the kernel can legitimately change this value under a live connection (a firmware update, a counter) — the field is invalidated on rescan and re-read from sysfs on next access. - - `False` (or omit it) if the value is part of the object's identity and cannot change without it becoming a different object (an address/NQN-shaped field), **or** if the owning object is never reconfigured in place at all (e.g. `libnvme_path` — a path is always destroyed and recreated on rescan, never updated, so `reconfigure_reset` is meaningless for any `PATH_SYSFS` member and every one omits it). + - `False` (or omit it) if the value is part of the object's identity and cannot change without it becoming a different object (an address/NQN-shaped field), **or** if the owning object is never reconfigured in place at all (e.g. `libnvme_path` — a path is always destroyed and recreated on rescan, never updated, so `reconfigure_reset` is meaningless for any `PATH_ATTRS` member and every one omits it). 4. If the field needs a numeric type instead of `char *` (e.g. `long`, `int`, an `enum`), set `'type'` accordingly — see "Cached vs. volatile, string vs. numeric" below for what changes underneath. Only `char *` and numeric types are supported; there is no array/struct member support here (unlike `generate_accessors.py`, which handles those cases for non-lazy structs). 5. Regenerate and review the diff: ``` - ./generate_sysfs_accessors.py --specs sysfs_accessors_specs.py --out-dir ../../src/nvme --ld-out-dir ../../src --swig-out-dir ../../libnvme3 + ./generate_attr_accessors.py --specs attr_accessors_specs.py --out-dir ../../src/nvme --ld-out-dir ../../src --swig-out-dir ../../libnvme3 ``` 6. Run `make checkpatch-diff` on the regenerated files. @@ -96,7 +96,7 @@ Four independent axes combine into the getter body the generator picks — there | | `char *` | numeric (`int`/`long`/`enum ...`) | |---|---|---| -| **cached** (no `volatile`) | plain pointer field; `NULL` = not loaded, `NO_SYSFS_ATTR` = absent, real pointer = value | **boxed**: `TYPE *` field, same NULL/`NO_SYSFS_ATTR`/real-pointer tri-state — the bare type has no spare value to mean "not loaded" (`0` is a legitimate reading), so a numeric member reuses the string members' mechanism via one heap allocation instead of inventing a second one | +| **cached** (no `volatile`) | plain pointer field; `NULL` = not loaded, `NO_ATTR` = absent, real pointer = value | **boxed**: `TYPE *` field, same NULL/`NO_ATTR`/real-pointer tri-state — the bare type has no spare value to mean "not loaded" (`0` is a legitimate reading), so a numeric member reuses the string members' mechanism via one heap allocation instead of inventing a second one | | **`volatile: True`** | plain `char *` field, re-read every call, freed and replaced only when the new read differs from the cached copy (so a caller holding the returned pointer across two calls reading the same value never sees it freed under it) | plain value field (`volatile long`/`volatile int` in C too — a real qualifier, not just documentation, since the value is deliberately never cached), re-parsed on every call | Both cached and volatile getters return `-ENOENT` if the attribute cannot be read, and `-EINVAL` (or `-ENOMEM` for the boxed-numeric allocation) if it can be read but not parsed — never the previous cached value on failure, always the caller-supplied `dflt` (see "Getter shape" above). @@ -121,7 +121,7 @@ Both cached and volatile getters return `-ENOENT` if the attribute cannot be rea ## How to add a member that needs a public setter (`writable`) -`writable: True` does **not** mean the sysfs attribute itself is writable — every member in this dict is sysfs-observed and read-only from the kernel's side. It means libnvme needs a way to inject a value into the cache from somewhere other than the normal lazy sysfs read. There are two situations where that comes up: +`writable: True` does **not** mean the sysfs attribute itself is writable — every member in this dict is sysfs-observed and read-only from the kernel's side. It means libnvme needs a way to inject a value into the cache from somewhere other than the normal lazy read. There are two situations where that comes up: - **Dual-direction fields**: the value is set from connect-time config on one code path and observed from sysfs on another (e.g. `dhchap_host_key`, `keyring`). - **Backfill fallback**: a caller needs to supply a value sysfs doesn't provide on older kernels (e.g. `cntrltype`/`dctype`'s legacy-kernel Identify-based fallback in `fabrics.c`, used when those two sysfs attributes don't exist), or on a platform with no sysfs at all (e.g. subsystem `model`/`serial`/`firmware`, pushed from Windows's ctrl map). @@ -142,7 +142,7 @@ Use a group instead of a plain member when one sysfs read naturally produces **s 'members': ['field_a', 'field_b'], }, ``` -2. `loader` is a C function name. The generated getter calls it as `loader(w)`, passing the owning struct pointer, and propagates a nonzero return to its own caller unchanged (the load itself failed, not just "attribute absent"). Declare it once in the generated header (automatic — `generate_header()` emits a prototype for every group's `loader`, but only when the spec has at least one group) and define it in whichever hand-written `*-custom-*.c` file(s) actually need to fill this group — see "Generated file layout" below. +2. `loader` is a C function name. The generated getter calls it as `loader(w)`, passing the owning struct pointer, and propagates a nonzero return to its own caller unchanged (the load itself failed, not just "attribute absent"). Declare it once in the generated header (automatic — `generate_header()` emits a prototype for every group's `loader`, but only when the spec has at least one group) and define it in whichever hand-written `*-attrs-custom-*.c` file(s) actually need to fill this group — see "Generated file layout" below. 3. The first access to *any* member of the group triggers the loader; every other member's cache-miss guard then finds its value already loaded and never calls the loader again. Loaders must leave every member they don't fill at `NULL` (not garbage) so the generated accessor can stamp the "read, absent" sentinel correctly. 4. If the loader body genuinely needs to differ by `CONFIG_FABRICS` (or any axis other than OS), that's a fact about the hand-written `.c` files, not about this dict — there's no key to set. A one-line comment above the group entry noting "loader body varies by CONFIG_FABRICS" (or similar) is enough; see the existing `identity` and `fabrics` groups for the pattern. If the loader (or the *grouping itself*) needs to differ by **OS**, see "Per-OS resolution" below instead — that is a real, first-class axis this generator understands, unlike fabrics-or-other build flags. 5. Groups themselves are not yet OS-resolved (a spec's `['groups']` list is a single, OS-invariant list) — no current spec needs a group whose loader or membership differs per OS. Extend `build_members()` the same way member resolution works, if one ever does. @@ -158,14 +158,16 @@ A member only needs a `'linux'`/`'win'` override when its **value source** — w 'win': {'absent': True}}, ``` -**Most members do not need this.** `libnvme_get_{ctrl,ns,path,subsys}_attr()` already has a Windows implementation that unconditionally returns `NULL` — so for a plain `'attr'` member, Windows absence falls out of the existing attr-reader stub for free; the generated getter body is identical C on both platforms, it just behaves differently at runtime because the function it calls does. Only add an override when a *different function* needs to be called, or the *grouping* itself changes — no current spec needs that case; `'absent': True` (every `PATH_SYSFS` member on Windows) is the only override in use today. A member whose OS difference can't be expressed by changing what one function returns (e.g. `NS_SYSFS`'s `lba_*` members: Linux calls two small loaders, Windows calls one big Identify command) uses `'custom': True` instead — a hand-written getter body in `*-custom-.c`, with only the prototype and the struct field generated (see `sysfs_accessors_specs.py`'s `NS_SYSFS` entry for worked examples). +**Most members do not need this.** `libnvme_get_{ctrl,ns,path,subsys}_attr()` already has a Windows implementation that unconditionally returns `NULL` — so for a plain `'attr'` member, Windows absence falls out of the existing attr-reader stub for free; the generated getter body is identical C on both platforms, it just behaves differently at runtime because the function it calls does. Only add an override when a *different function* needs to be called, or the *grouping* itself changes — no current spec needs that case; `'absent': True` (every `PATH_ATTRS` member on Windows) is the only override in use today. A member whose OS difference can't be expressed by changing what one function returns (e.g. `NS_ATTRS`'s `lba_*` members: Linux calls two small loaders, Windows calls one big Identify command) uses `'custom': True` instead — a hand-written getter body in `*-attrs-custom-.c`, with only the prototype and the struct field generated (see `attr_accessors_specs.py`'s `NS_ATTRS` entry for worked examples). -`'absent': True` means the platform has no source for the member at all: the generated getter writes `dflt` to the out-param and always returns `-ENOENT`, no attribute read or loader call ever happens, and (for `PATH_SYSFS`, where every member is absent on Windows) the owning-struct parameter is `__shr_unused` since the body never touches it. +`'absent': True` means the platform has no source for the member at all: the generated getter writes `dflt` to the out-param and always returns `-ENOENT`, no attribute read or loader call ever happens, and (for `PATH_ATTRS`, where every member is absent on Windows) the owning-struct parameter is `__shr_unused` since the body never touches it. `'type'` and `'writable'` are never valid inside a `'linux'`/`'win'` override — a member's public signature (name, type, whether a setter exists) must be identical on every platform; only where a value comes from may vary. Enforcing this is currently a documentation convention, not a generator-level check. ### Generated file layout +The generated `.h`/`.c` files live in `src/nvme/generated/`, a dedicated subdirectory kept separate from the hand-written `*-attrs-custom-*.c` files that `#include` them — that separation exists so a reader browsing `src/nvme/` can tell generator-owned files (never hand-edited, `generated/`) apart from hand-written ones (everything else) at a glance. The `.ld` files stay in `src/`, alongside every other version script; the `.i` fragments stay in `libnvme3/`, alongside the other SWIG input. + The generator resolves each member's effective Linux and Windows definition and decides where its getter body goes: - **identical on both** → the spec's shared `.c` file (`source` key) @@ -173,17 +175,17 @@ The generator resolves each member's effective Linux and Windows definition and The struct definition, `_alloc()`/`_reset()`/`_free()`, and every OS-common getter always live in the shared file — **the struct never splits**, even when some of its members' getters do, because every cached member (string or boxed numeric) has the same storage shape regardless of which loader fills it. -For `PATH_SYSFS`, every member differs (absent on Windows), so the shared file holds only the struct definition and lifecycle functions, and both `path-sysfs-linux.c` and `path-sysfs-win.c` exist. For `CTRL_SYSFS`, no member differs at all, so only the shared `ctrl-sysfs.c` exists — exactly the file this generator has always produced. `NS_SYSFS` is the case where a spec's shared file is non-trivial *and* both per-OS files exist alongside it (its `lba_*`/`csi`/`eui64`/`nguid`/`uuid` members are `'custom': True`, hand-written in `ns-sysfs-custom-linux.c`/`ns-sysfs-custom-win.c`, while its `diag/*` counters are OS-common and live in the shared `ns-sysfs.c`). +For `PATH_ATTRS`, every member differs (absent on Windows), so the shared file holds only the struct definition and lifecycle functions, and both `path-attrs-linux.c` and `path-attrs-win.c` exist. For `CTRL_ATTRS`, no member differs at all, so only the shared `ctrl-attrs.c` exists — exactly the file this generator has always produced. `NS_ATTRS` is the case where a spec's shared file is non-trivial *and* both per-OS files exist alongside it (its `lba_*`/`csi`/`eui64`/`nguid`/`uuid` members are `'custom': True`, hand-written in `ns-attrs-custom-linux.c`/`ns-attrs-custom-win.c`, while its `diag/*` counters are OS-common and live in the shared `ns-attrs.c`). -The per-OS `.c` files carry no `#include`s of their own — they rely on being `#include`d *after* the shared file in the hand-written `*-custom-.c`, which brings the struct definition and everything else into scope first: +The per-OS `.c` files carry no `#include`s of their own — they rely on being `#include`d *after* the shared file in the hand-written `*-attrs-custom-.c`, which brings the struct definition and everything else into scope first: ```c -// path-sysfs-custom-linux.c (hand-written) -#include "path-sysfs.c" // struct def + OS-common getters -#include "path-sysfs-linux.c" // Linux-only getters, generated +// path-attrs-custom-linux.c (hand-written, lives in src/nvme/) +#include "generated/path-attrs.c" // struct def + OS-common getters +#include "generated/path-attrs-linux.c" // Linux-only getters, generated ``` -Exactly one of `*-custom-linux.c` / `*-custom-win.c` is ever listed in `meson.build`'s `sources` (the OS axis, same mechanism as `ctrl-sysfs-custom-linux.c`/`-win.c`). If a spec also needs a `CONFIG_FABRICS` split (as `CTRL_SYSFS` does for its fabrics group), that nesting happens inside whichever `*-custom-.c` is compiled, exactly as today — fabrics is a build flag, not an OS, and stays entirely a hand-written-file concern. +Exactly one of `*-attrs-custom-linux.c` / `*-attrs-custom-win.c` is ever listed in `meson.build`'s `sources` (the OS axis, same mechanism as `ctrl-attrs-custom-linux.c`/`-win.c`). If a spec also needs a `CONFIG_FABRICS` split (as `CTRL_ATTRS` does for its fabrics group), that nesting happens inside whichever `*-attrs-custom-.c` is compiled, exactly as today — fabrics is a build flag, not an OS, and stays entirely a hand-written-file concern. One trade-off worth knowing: a spec's shared `.c` (and any per-OS `.c`) is never listed in `meson.build`'s `sources` directly (only reached via the `#include` chain above) — but since it contains real accessor functions, adding it to `sources` by mistake would produce duplicate-symbol *link* errors. @@ -207,19 +209,19 @@ These identify the generated artifact itself and are set once, not per-member: | Key | Meaning | |---|---| -| `struct_name` | The generated C struct's tag name (`libnvme_ctrl_sysfs`, `libnvme_path_sysfs`, ...). | +| `struct_name` | The generated C struct's tag name (`libnvme_ctrl_attrs`, `libnvme_path_attrs`, ...). | | `owner_type` | The struct this one nests inside (`libnvme_ctrl`, `libnvme_path`, ...). | -| `owner_field` | The pointer field name on `owner_type` (`sysfs`, so generated field paths read `sysfs->model`). | +| `owner_field` | The pointer field name on `owner_type` (`attrs`, so generated field paths read `attrs->model`). | | `attr_reader` | The C function name for reading one plain sysfs attribute — see above. | -| `source` | Filename of the generated shared `.c` (struct definition + every OS-common accessor). | -| `source_linux` | Filename of the Linux-only `.c`. Only required if some member's resolution actually differs per OS; omit otherwise. | +| `source` | Filename of the generated shared `.c` (struct definition + every OS-common accessor), written under `generated/`. | +| `source_linux` | Filename of the Linux-only `.c`, written under `generated/`. Only required if some member's resolution actually differs per OS; omit otherwise. | | `source_win` | Likewise, for Windows. | -| `header` | Filename of the generated common header. | -| `ld` | Filename of the generated linker version-script. | +| `header` | Filename of the generated common header, written under `generated/`. | +| `ld` | Filename of the generated linker version-script, written alongside the other `.ld` files (not under `generated/` — hand-maintained, see "Usage" above). | | `swig` | Filename of the generated SWIG fragment. | -| `ld_section` | Version-script section name the symbols nest inside — needs its own top-level tag distinct from every other spec's (`ld` rejects two `--version-script` files defining the same tag). A placeholder like `LIBNVME_CTRL_SYSFS_NEXT`, not a real version number: the committed `.ld` is hand-written and never auto-overwritten (see "Usage" above), so this string only feeds the generator's own scratch copy — never diffed, never enforced, never echoed back to the maintainer. The real tag is a maintainer decision made by hand at commit time. | +| `ld_section` | Version-script section name the symbols nest inside — needs its own top-level tag distinct from every other spec's (`ld` rejects two `--version-script` files defining the same tag). A placeholder like `LIBNVME_CTRL_ATTRS_NEXT`, not a real version number: the committed `.ld` is hand-written and never auto-overwritten (see "Usage" above), so this string only feeds the generator's own scratch copy — never diffed, never enforced, never echoed back to the maintainer. The real tag is a maintainer decision made by hand at commit time. | -Add a new spec dict to `sysfs_accessors_specs.py` with its own set of these keys and append it to `SYSFS_SPECS`. +Add a new spec dict to `attr_accessors_specs.py` with its own set of these keys and append it to `ATTR_SPECS`. ------ @@ -233,10 +235,10 @@ SWIG's `%extend struct X { TYPE member; }` "property" convention only works when The wrapper always passes `NULL` (string) or `0` (numeric) as the real getter's `dflt` argument — it never reads the out-param on a non-`0` return anyway, so which default the C call used is irrelevant to the Python-visible result. -Adding a Python conversion for a new numeric type means adding one entry to `_PY_FROM` in `generate_sysfs_accessors.py` (mirrors `generate_accessors.py`'s own `_SCANF_FMT` table) — deliberately not a general type mapper, add an entry only when a real member needs it. +Adding a Python conversion for a new numeric type means adding one entry to `_PY_FROM` in `generate_attr_accessors.py` (mirrors `generate_accessors.py`'s own `_SCANF_FMT` table) — deliberately not a general type mapper, add an entry only when a real member needs it. ------ ## What you never need to hand-edit -The struct definition, all getters/setters, the alloc/reset/free functions, the header, the `.ld` file, and the SWIG fragment are all generated — never hand-edit a spec's `.h`, `.c` (shared or per-OS), `.ld`, or `.i`. The only hand-written files are the `*-custom-.c` loader bodies — see "Generated file layout" above for how they pull in the generated struct definition. +The struct definition, all getters/setters, the alloc/reset/free functions, the header, the `.ld` file, and the SWIG fragment are all generated — never hand-edit a spec's `.h`, `.c` (shared or per-OS, all under `generated/`), `.ld`, or `.i`. The only hand-written files are the `*-attrs-custom-.c` loader bodies — see "Generated file layout" above for how they pull in the generated struct definition. diff --git a/libnvme/libnvme3/ctrl-sysfs.i b/libnvme/libnvme3/ctrl-attrs.i similarity index 99% rename from libnvme/libnvme3/ctrl-sysfs.i rename to libnvme/libnvme3/ctrl-attrs.i index 46e7b8d45b..3306eeca61 100644 --- a/libnvme/libnvme3/ctrl-sysfs.i +++ b/libnvme/libnvme3/ctrl-attrs.i @@ -18,7 +18,7 @@ * Or: make update-accessors */ -/* struct libnvme_ctrl -- sysfs-backed properties */ +/* struct libnvme_ctrl -- lazily-loaded properties */ %rename(libnvme_ctrl_firmware_set) libnvme_ctrl_set_firmware; %rename(libnvme_ctrl_model_set) libnvme_ctrl_set_model; %rename(libnvme_ctrl_serial_set) libnvme_ctrl_set_serial; diff --git a/libnvme/libnvme3/meson.build b/libnvme/libnvme3/meson.build index 7079ad1c5f..210014b54f 100644 --- a/libnvme/libnvme3/meson.build +++ b/libnvme/libnvme3/meson.build @@ -26,8 +26,8 @@ if want_python depend_files: [ 'accessors.i', 'accessors-fabrics.i', - 'ctrl-sysfs.i', - 'subsys-sysfs.i', + 'ctrl-attrs.i', + 'subsys-attrs.i', 'nvme-manual-bridges.i', 'fctx_field_tables.h', ], diff --git a/libnvme/libnvme3/ns-sysfs.i b/libnvme/libnvme3/ns-attrs.i similarity index 98% rename from libnvme/libnvme3/ns-sysfs.i rename to libnvme/libnvme3/ns-attrs.i index e8e185d825..aadbad22d2 100644 --- a/libnvme/libnvme3/ns-sysfs.i +++ b/libnvme/libnvme3/ns-attrs.i @@ -18,7 +18,7 @@ * Or: make update-accessors */ -/* struct libnvme_ns -- sysfs-backed properties */ +/* struct libnvme_ns -- lazily-loaded properties */ %{ static PyObject *libnvme_ns_lba_size_get(const struct libnvme_ns *p) { diff --git a/libnvme/libnvme3/nvme.i b/libnvme/libnvme3/nvme.i index 248ce27c79..e034805f50 100644 --- a/libnvme/libnvme3/nvme.i +++ b/libnvme/libnvme3/nvme.i @@ -1300,10 +1300,10 @@ def exclusion_match(ctx, transport=None, traddr=None, trsvcid=None, */ %include "nvme-manual-bridges.i" %include "accessors.i" -%include "ctrl-sysfs.i" -%include "path-sysfs.i" -%include "ns-sysfs.i" -%include "subsys-sysfs.i" +%include "ctrl-attrs.i" +%include "path-attrs.i" +%include "ns-attrs.i" +%include "subsys-attrs.i" %include "accessors-fabrics.i" /* Propagate any Python exception set inside the helper function. diff --git a/libnvme/libnvme3/path-sysfs.i b/libnvme/libnvme3/path-attrs.i similarity index 98% rename from libnvme/libnvme3/path-sysfs.i rename to libnvme/libnvme3/path-attrs.i index 71753548e6..a23cecc5a7 100644 --- a/libnvme/libnvme3/path-sysfs.i +++ b/libnvme/libnvme3/path-attrs.i @@ -18,7 +18,7 @@ * Or: make update-accessors */ -/* struct libnvme_path -- sysfs-backed properties */ +/* struct libnvme_path -- lazily-loaded properties */ %{ static const char *libnvme_path_ana_state_get(const struct libnvme_path *p) { diff --git a/libnvme/libnvme3/subsys-sysfs.i b/libnvme/libnvme3/subsys-attrs.i similarity index 97% rename from libnvme/libnvme3/subsys-sysfs.i rename to libnvme/libnvme3/subsys-attrs.i index eba146a012..11cf25cc5e 100644 --- a/libnvme/libnvme3/subsys-sysfs.i +++ b/libnvme/libnvme3/subsys-attrs.i @@ -18,7 +18,7 @@ * Or: make update-accessors */ -/* struct libnvme_subsystem -- sysfs-backed properties */ +/* struct libnvme_subsystem -- lazily-loaded properties */ %rename(libnvme_subsystem_model_set) libnvme_subsystem_set_model; %rename(libnvme_subsystem_serial_set) libnvme_subsystem_set_serial; %rename(libnvme_subsystem_firmware_set) libnvme_subsystem_set_firmware; diff --git a/libnvme/src/ctrl-sysfs.ld b/libnvme/src/ctrl-attrs.ld similarity index 98% rename from libnvme/src/ctrl-sysfs.ld rename to libnvme/src/ctrl-attrs.ld index 0e6eacf31a..0ea9751451 100644 --- a/libnvme/src/ctrl-sysfs.ld +++ b/libnvme/src/ctrl-attrs.ld @@ -15,7 +15,7 @@ * Or: make update-accessors */ -LIBNVME_CTRL_SYSFS_3 { +LIBNVME_CTRL_ATTRS_3 { global: libnvme_ctrl_get_numa_node; libnvme_ctrl_get_queue_count; diff --git a/libnvme/src/libnvme.h.in b/libnvme/src/libnvme.h.in index 5b64f4940e..2cd2fc8207 100644 --- a/libnvme/src/libnvme.h.in +++ b/libnvme/src/libnvme.h.in @@ -13,10 +13,10 @@ extern "C" { #endif #include -#include -#include -#include -#include +#include +#include +#include +#include #include #include #include diff --git a/libnvme/src/meson.build b/libnvme/src/meson.build index 0a41db2295..4bcfaa4a61 100644 --- a/libnvme/src/meson.build +++ b/libnvme/src/meson.build @@ -7,19 +7,19 @@ # sources = [ 'nvme/accessors.c', + 'nvme/generated/subsys-attrs.c', 'nvme/ioctl.c', 'nvme/lib.c', 'nvme/log.c', 'nvme/nvme-cmds.c', - 'nvme/subsys-sysfs.c', 'nvme/tree.c', 'nvme/util.c', ] if host_system == 'linux' sources += [ - 'nvme/ctrl-sysfs-custom-linux.c', - 'nvme/path-sysfs-custom-linux.c', - 'nvme/ns-sysfs-custom-linux.c', + 'nvme/ctrl-attrs-custom-linux.c', + 'nvme/path-attrs-custom-linux.c', + 'nvme/ns-attrs-custom-linux.c', 'nvme/ioctl-linux.c', 'nvme/lib-linux.c', 'nvme/mem-linux.c', @@ -29,9 +29,9 @@ if host_system == 'linux' elif host_system == 'windows' sources += [ 'nvme/ctrl-map.c', - 'nvme/ctrl-sysfs-custom-win.c', - 'nvme/path-sysfs-custom-win.c', - 'nvme/ns-sysfs-custom-win.c', + 'nvme/ctrl-attrs-custom-win.c', + 'nvme/path-attrs-custom-win.c', + 'nvme/ns-attrs-custom-win.c', 'nvme/ioctl-win.c', 'nvme/lib-win.c', 'nvme/mem-win.c', @@ -41,9 +41,6 @@ elif host_system == 'windows' endif headers = [ 'nvme/accessors.h', - 'nvme/ctrl-sysfs.h', - 'nvme/path-sysfs.h', - 'nvme/ns-sysfs.h', 'nvme/endian.h', 'nvme/ioctl.h', 'nvme/lib-types.h', @@ -62,12 +59,21 @@ headers = [ 'nvme/nvme-types-zns.h', 'nvme/nvme-types.h', 'nvme/scan.h', - 'nvme/subsys-sysfs.h', 'nvme/tree.h', 'nvme/types.h', 'nvme/util.h', ] +# Generator-owned headers (never hand-touched, unlike everything else in +# headers above) -- kept in their own subdirectory and installed under +# nvme/generated/ so libnvme.h.in can #include them by that same path. +generated_headers = [ + 'nvme/generated/ctrl-attrs.h', + 'nvme/generated/path-attrs.h', + 'nvme/generated/ns-attrs.h', + 'nvme/generated/subsys-attrs.h', +] + if want_fabrics sources += [ 'nvme/accessors-fabrics.c', @@ -147,10 +153,10 @@ nvmf_ld = meson.current_source_dir() / 'libnvmf.ld' mi_ld = meson.current_source_dir() / 'libnvme-mi.ld' accessors_ld = meson.current_source_dir() / 'accessors.ld' nvmf_accessors_ld = meson.current_source_dir() / 'accessors-fabrics.ld' -ctrl_sysfs_ld = meson.current_source_dir() / 'ctrl-sysfs.ld' -path_sysfs_ld = meson.current_source_dir() / 'path-sysfs.ld' -ns_sysfs_ld = meson.current_source_dir() / 'ns-sysfs.ld' -subsys_sysfs_ld = meson.current_source_dir() / 'subsys-sysfs.ld' +ctrl_attrs_ld = meson.current_source_dir() / 'ctrl-attrs.ld' +path_attrs_ld = meson.current_source_dir() / 'path-attrs.ld' +ns_attrs_ld = meson.current_source_dir() / 'ns-attrs.ld' +subsys_attrs_ld = meson.current_source_dir() / 'subsys-attrs.ld' # Version scripts filter the exported symbols. GNU ld honours --version-script # for PE/COFF too, but LLVM's lld does not accept the option at all, so the @@ -170,10 +176,10 @@ if want_version_scripts link_args += [ '-Wl,--version-script=@0@'.format(nvme_ld), '-Wl,--version-script=@0@'.format(accessors_ld), - '-Wl,--version-script=@0@'.format(ctrl_sysfs_ld), - '-Wl,--version-script=@0@'.format(path_sysfs_ld), - '-Wl,--version-script=@0@'.format(ns_sysfs_ld), - '-Wl,--version-script=@0@'.format(subsys_sysfs_ld), + '-Wl,--version-script=@0@'.format(ctrl_attrs_ld), + '-Wl,--version-script=@0@'.format(path_attrs_ld), + '-Wl,--version-script=@0@'.format(ns_attrs_ld), + '-Wl,--version-script=@0@'.format(subsys_attrs_ld), ] endif @@ -205,11 +211,18 @@ libnvme_header = configure_file( install_dir: prefixdir / get_option('includedir') / libnvme_api_name ) +# Needed so a quoted #include (e.g. "private.h") from nvme/generated/*.c +# still resolves against nvme/ -- the compiler's own current-file-directory +# rule only reaches siblings, not a parent, and generated/*.c sits one +# level deeper than the hand-written files it's #include'd from. +nvme_incdir = include_directories('nvme') + libnvme = library( libnvme_link_name, # produces libnvme.so sources, version: libnvme_so_version, c_args: ['-fvisibility=hidden'], + include_directories: nvme_incdir, link_args: link_args, dependencies: deps, install: true, @@ -236,6 +249,7 @@ libnvme_dep = declare_dependency( libnvme_test = library( libnvme_link_name + '-test', sources, + include_directories: nvme_incdir, dependencies: deps, install: false, ) @@ -252,6 +266,11 @@ install_headers( subdir: libnvme_api_name / 'nvme', install_mode: mode, ) +install_headers( + generated_headers, + subdir: libnvme_api_name / 'nvme' / 'generated', + install_mode: mode, +) if want_mi install_headers( [ diff --git a/libnvme/src/ns-sysfs.ld b/libnvme/src/ns-attrs.ld similarity index 97% rename from libnvme/src/ns-sysfs.ld rename to libnvme/src/ns-attrs.ld index 316d93a98c..cc0ffa8b8a 100644 --- a/libnvme/src/ns-sysfs.ld +++ b/libnvme/src/ns-attrs.ld @@ -15,7 +15,7 @@ * Or: make update-accessors */ -LIBNVME_NS_SYSFS_3 { +LIBNVME_NS_ATTRS_3 { global: libnvme_ns_get_lba_size; libnvme_ns_get_lba_shift; diff --git a/libnvme/src/nvme/sysfs_accessors_specs.py b/libnvme/src/nvme/attr_accessors_specs.py similarity index 81% rename from libnvme/src/nvme/sysfs_accessors_specs.py rename to libnvme/src/nvme/attr_accessors_specs.py index ec23485f67..26a37acb25 100644 --- a/libnvme/src/nvme/sysfs_accessors_specs.py +++ b/libnvme/src/nvme/attr_accessors_specs.py @@ -1,26 +1,26 @@ # SPDX-License-Identifier: LGPL-2.1-or-later """ -sysfs_accessors_specs.py — Input dicts for generate_sysfs_accessors.py. +attr_accessors_specs.py — Input dicts for generate_attr_accessors.py. -One dict per opaque, sysfs-backed struct. Every dict must be added to -SYSFS_SPECS at the bottom of this file -- that is the only thing -generate_sysfs_accessors.py actually imports; it generates every entry in -one run. See ../../design/tooling/generate_sysfs_accessors.md for the +One dict per opaque, lazily-loaded struct. Every dict must be added to +ATTR_SPECS at the bottom of this file -- that is the only thing +generate_attr_accessors.py actually imports; it generates every entry in +one run. See ../../design/tooling/generate_attr_accessors.md for the schema each dict follows and how to add a new member. """ -CTRL_SYSFS = { - 'struct_name': 'libnvme_ctrl_sysfs', +CTRL_ATTRS = { + 'struct_name': 'libnvme_ctrl_attrs', 'owner_type': 'libnvme_ctrl', - 'owner_field': 'sysfs', + 'owner_field': 'attrs', 'attr_reader': 'libnvme_get_ctrl_attr', - 'source': 'ctrl-sysfs.c', - 'header': 'ctrl-sysfs.h', - 'ld': 'ctrl-sysfs.ld', - 'swig': 'ctrl-sysfs.i', + 'source': 'ctrl-attrs.c', + 'header': 'ctrl-attrs.h', + 'ld': 'ctrl-attrs.ld', + 'swig': 'ctrl-attrs.i', # A distinct top-level tag, not LIBNVME_ACCESSORS_3: ld rejects two # --version-script files both defining the same tag (confirmed the - # hard way -- "duplicate version tag" -- ctrl-sysfs.ld and + # hard way -- "duplicate version tag" -- ctrl-attrs.ld and # accessors.ld are separate generator outputs, so a shared tag isn't # achievable without hand-merging one into the other on every # regeneration of either). Matches the existing precedent of @@ -28,14 +28,14 @@ # own independent tag rather than chaining. # # NEXT, not a real version number: the committed .ld is hand-written - # and never auto-overwritten (see update-sysfs-accessors.sh), so + # and never auto-overwritten (see update-attr-accessors.sh), so # this string only ever appears in this file's own generated scratch # copy -- it is not diffed, not enforced, and never echoed back to # the maintainer. Which version tag a symbol actually lands under is # entirely the maintainer's call at commit time (see # accessor-workflow.md); a real-looking version number here would # just go stale the first time that tag chains past _3. - 'ld_section': 'LIBNVME_CTRL_SYSFS_NEXT', + 'ld_section': 'LIBNVME_CTRL_ATTRS_NEXT', 'members': [ { 'name': 'numa_node', @@ -87,7 +87,7 @@ # get a setter they don't strictly need as a result -- a # deliberate tradeoff over splitting the group and risking # a second Identify call. Loader body varies by OS -- see - # ctrl-sysfs-custom-linux.c / ctrl-sysfs-custom-win.c. + # ctrl-attrs-custom-linux.c / ctrl-attrs-custom-win.c. 'loader': 'libnvme_ctrl_load_identity', 'reconfigure_reset': True, 'writable': True, @@ -101,8 +101,8 @@ ], }, { - # Loader body varies by OS -- see ctrl-sysfs-custom-linux.c / - # ctrl-sysfs-custom-win.c. + # Loader body varies by OS -- see ctrl-attrs-custom-linux.c / + # ctrl-attrs-custom-win.c. 'loader': 'libnvme_ctrl_load_phy_slot', 'reconfigure_reset': True, 'members': [ @@ -111,7 +111,7 @@ }, { # Loader body varies by CONFIG_FABRICS -- see - # ctrl-sysfs-custom-fabrics.c / ctrl-sysfs-custom-no-fabrics.c. + # ctrl-attrs-custom-fabrics.c / ctrl-attrs-custom-no-fabrics.c. 'loader': 'libnvmf_ctrl_load_fabrics_attrs', 'reconfigure_reset': True, 'writable': True, @@ -124,21 +124,21 @@ ], } -PATH_SYSFS = { - 'struct_name': 'libnvme_path_sysfs', +PATH_ATTRS = { + 'struct_name': 'libnvme_path_attrs', 'owner_type': 'libnvme_path', - 'owner_field': 'sysfs', + 'owner_field': 'attrs', 'attr_reader': 'libnvme_get_path_attr', - 'source': 'path-sysfs.c', - 'source_linux': 'path-sysfs-linux.c', - 'source_win': 'path-sysfs-win.c', - 'header': 'path-sysfs.h', - 'ld': 'path-sysfs.ld', - 'swig': 'path-sysfs.i', - # See CTRL_SYSFS's ld_section comment above: NEXT, not a real + 'source': 'path-attrs.c', + 'source_linux': 'path-attrs-linux.c', + 'source_win': 'path-attrs-win.c', + 'header': 'path-attrs.h', + 'ld': 'path-attrs.ld', + 'swig': 'path-attrs.i', + # See CTRL_ATTRS's ld_section comment above: NEXT, not a real # version number -- this string is never diffed or enforced, only # read by a human deciding the actual tag by hand. - 'ld_section': 'LIBNVME_PATH_SYSFS_NEXT', + 'ld_section': 'LIBNVME_PATH_ATTRS_NEXT', # No reconfigure_reset on any member: a path is never updated in # place on rescan -- libnvme_ctrl_scan_path() always calloc()s a new # one -- so there is no in-place-invalidate event these fields would @@ -202,18 +202,18 @@ 'groups': [], } -NS_SYSFS = { - 'struct_name': 'libnvme_ns_sysfs', +NS_ATTRS = { + 'struct_name': 'libnvme_ns_attrs', 'owner_type': 'libnvme_ns', - 'owner_field': 'sysfs', + 'owner_field': 'attrs', 'attr_reader': 'libnvme_get_ns_attr', - 'source': 'ns-sysfs.c', - 'header': 'ns-sysfs.h', - 'ld': 'ns-sysfs.ld', - 'swig': 'ns-sysfs.i', - # See CTRL_SYSFS's ld_section comment above: NEXT, not a real + 'source': 'ns-attrs.c', + 'header': 'ns-attrs.h', + 'ld': 'ns-attrs.ld', + 'swig': 'ns-attrs.i', + # See CTRL_ATTRS's ld_section comment above: NEXT, not a real # version number. - 'ld_section': 'LIBNVME_NS_SYSFS_NEXT', + 'ld_section': 'LIBNVME_NS_ATTRS_NEXT', # No reconfigure_reset on any member: like libnvme_path, an ns is # never updated in place on rescan -- libnvme_ctrl_scan_namespace() # always finds-or-frees the old one and installs a fresh one -- so @@ -222,9 +222,9 @@ 'members': [ # lba_size/lba_shift/lba_count/lba_util/meta_size/csi are all # 'custom': True -- the struct field (boxed, same NULL/ - # NO_SYSFS_ATTR/real-value tri-state every other cached numeric + # NO_ATTR/real-value tri-state every other cached numeric # member uses) and the header prototype are generated as usual, - # but the getter body is hand-written in ns-sysfs-custom-.c, + # but the getter body is hand-written in ns-attrs-custom-.c, # not generated. Needed because none of the three axes this # generator understands (plain attr, volatile attr, loader # group) can express what these six actually require: lba_shift @@ -272,8 +272,8 @@ # while the public getter hands back a pointer-to-const view of # it (see _pub_type()) -- int fn(p, const TYPE **val, const # TYPE *dflt), same shape as any other lazy getter, no new axis - # needed. Bodies are hand-written in ns-sysfs-custom-linux.c - # (real sysfs reads) and ns-sysfs-custom-win.c (always -ENOENT, + # needed. Bodies are hand-written in ns-attrs-custom-linux.c + # (real sysfs reads) and ns-attrs-custom-win.c (always -ENOENT, # Windows never had a source for these either -- same as csi's # Windows getter). { @@ -292,9 +292,9 @@ 'custom': True, }, # The four diag/* counters need no per-OS override: like most - # CTRL_SYSFS members, Windows absence falls out of the existing + # CTRL_ATTRS members, Windows absence falls out of the existing # libnvme_get_ns_attr() stub (unconditionally NULL) for free -- - # unlike PATH_SYSFS, libnvme_ns as a whole is not Windows-absent + # unlike PATH_ATTRS, libnvme_ns as a whole is not Windows-absent # (the six custom members above have real Windows sources), so # there is no reason to mark these explicitly absent either. { @@ -325,31 +325,31 @@ 'groups': [], } -SUBSYS_SYSFS = { - 'struct_name': 'libnvme_subsystem_sysfs', +SUBSYS_ATTRS = { + 'struct_name': 'libnvme_subsystem_attrs', 'owner_type': 'libnvme_subsystem', - 'owner_field': 'sysfs', + 'owner_field': 'attrs', 'attr_reader': 'libnvme_get_subsys_attr', - 'source': 'subsys-sysfs.c', - 'header': 'subsys-sysfs.h', - 'ld': 'subsys-sysfs.ld', - 'swig': 'subsys-sysfs.i', - # See CTRL_SYSFS's ld_section comment above: NEXT, not a real + 'source': 'subsys-attrs.c', + 'header': 'subsys-attrs.h', + 'ld': 'subsys-attrs.ld', + 'swig': 'subsys-attrs.i', + # See CTRL_ATTRS's ld_section comment above: NEXT, not a real # version number. - 'ld_section': 'LIBNVME_SUBSYS_SYSFS_NEXT', + 'ld_section': 'LIBNVME_SUBSYS_ATTRS_NEXT', # No reconfigure_reset on any member: a subsystem is never updated # in place -- libnvme_get_subsystem() always looks up an existing # one by name/subsysnqn or creates a fresh one, there is no # deconfigure/rescan hook that touches an existing subsystem's - # cached fields -- same rationale as PATH_SYSFS. + # cached fields -- same rationale as PATH_ATTRS. 'members': [ - # No group/loader needed, unlike CTRL_SYSFS's identity group: + # No group/loader needed, unlike CTRL_ATTRS's identity group: # Windows already has model/serial/firmware for free from the # ctrl map by the time a subsystem is scanned (no extra # Identify round trip to batch), so each is just a plain # attr member with writable=True and pushed in directly -- # the exact "platform with no sysfs at all" backfill case - # generate_sysfs_accessors.md's writable section already + # generate_attr_accessors.md's writable section already # names by example. { 'name': 'model', @@ -384,10 +384,10 @@ 'groups': [], } -# generate_sysfs_accessors.py generates every entry here in one run. -SYSFS_SPECS = [ - CTRL_SYSFS, - PATH_SYSFS, - NS_SYSFS, - SUBSYS_SYSFS, +# generate_attr_accessors.py generates every entry here in one run. +ATTR_SPECS = [ + CTRL_ATTRS, + PATH_ATTRS, + NS_ATTRS, + SUBSYS_ATTRS, ] diff --git a/libnvme/src/nvme/ctrl-sysfs-custom-fabrics.c b/libnvme/src/nvme/ctrl-attrs-custom-fabrics.c similarity index 81% rename from libnvme/src/nvme/ctrl-sysfs-custom-fabrics.c rename to libnvme/src/nvme/ctrl-attrs-custom-fabrics.c index 1b4fa18772..12ea9a313b 100644 --- a/libnvme/src/nvme/ctrl-sysfs-custom-fabrics.c +++ b/libnvme/src/nvme/ctrl-attrs-custom-fabrics.c @@ -17,8 +17,8 @@ int libnvmf_ctrl_load_fabrics_attrs(struct libnvme_ctrl *c) host_key = NULL; } if (host_key) { - SYSFS_FREE(c->sysfs->dhchap_host_key); - c->sysfs->dhchap_host_key = host_key; + ATTR_FREE(c->attrs->dhchap_host_key); + c->attrs->dhchap_host_key = host_key; } ctrl_key = libnvme_get_ctrl_attr(c, "dhchap_ctrl_secret"); @@ -27,8 +27,8 @@ int libnvmf_ctrl_load_fabrics_attrs(struct libnvme_ctrl *c) ctrl_key = NULL; } if (ctrl_key) { - SYSFS_FREE(c->sysfs->dhchap_ctrl_key); - c->sysfs->dhchap_ctrl_key = ctrl_key; + ATTR_FREE(c->attrs->dhchap_ctrl_key); + c->attrs->dhchap_ctrl_key = ctrl_key; } /* @@ -39,7 +39,7 @@ int libnvmf_ctrl_load_fabrics_attrs(struct libnvme_ctrl *c) */ tls_key = libnvme_get_ctrl_attr(c, "tls_key"); if (tls_key) - c->sysfs->keyring = libnvme_get_ctrl_attr(c, "tls_keyring"); + c->attrs->keyring = libnvme_get_ctrl_attr(c, "tls_keyring"); return 0; } diff --git a/libnvme/src/nvme/ctrl-sysfs-custom-linux.c b/libnvme/src/nvme/ctrl-attrs-custom-linux.c similarity index 73% rename from libnvme/src/nvme/ctrl-sysfs-custom-linux.c rename to libnvme/src/nvme/ctrl-attrs-custom-linux.c index e7f30e0792..99d9b2bff5 100644 --- a/libnvme/src/nvme/ctrl-sysfs-custom-linux.c +++ b/libnvme/src/nvme/ctrl-attrs-custom-linux.c @@ -12,22 +12,22 @@ #include "cleanup-linux.h" #include "lib.h" -#include "ctrl-sysfs.c" +#include "generated/ctrl-attrs.c" #ifdef CONFIG_FABRICS -# include "ctrl-sysfs-custom-fabrics.c" +# include "ctrl-attrs-custom-fabrics.c" #else -# include "ctrl-sysfs-custom-no-fabrics.c" +# include "ctrl-attrs-custom-no-fabrics.c" #endif int libnvme_ctrl_load_identity(struct libnvme_ctrl *c) { - c->sysfs->firmware = libnvme_get_ctrl_attr(c, "firmware_rev"); - c->sysfs->model = libnvme_get_ctrl_attr(c, "model"); - c->sysfs->serial = libnvme_get_ctrl_attr(c, "serial"); - c->sysfs->cntrltype = libnvme_get_ctrl_attr(c, "cntrltype"); - c->sysfs->cntlid = libnvme_get_ctrl_attr(c, "cntlid"); - c->sysfs->dctype = libnvme_get_ctrl_attr(c, "dctype"); + c->attrs->firmware = libnvme_get_ctrl_attr(c, "firmware_rev"); + c->attrs->model = libnvme_get_ctrl_attr(c, "model"); + c->attrs->serial = libnvme_get_ctrl_attr(c, "serial"); + c->attrs->cntrltype = libnvme_get_ctrl_attr(c, "cntrltype"); + c->attrs->cntlid = libnvme_get_ctrl_attr(c, "cntlid"); + c->attrs->dctype = libnvme_get_ctrl_attr(c, "dctype"); return 0; } @@ -72,7 +72,7 @@ int libnvme_ctrl_load_phy_slot(struct libnvme_ctrl *c) if (strcmp(addr, target_addr)) continue; - c->sysfs->phy_slot = strdup(entry->d_name); + c->attrs->phy_slot = strdup(entry->d_name); return 0; } diff --git a/libnvme/src/nvme/ctrl-sysfs-custom-no-fabrics.c b/libnvme/src/nvme/ctrl-attrs-custom-no-fabrics.c similarity index 100% rename from libnvme/src/nvme/ctrl-sysfs-custom-no-fabrics.c rename to libnvme/src/nvme/ctrl-attrs-custom-no-fabrics.c diff --git a/libnvme/src/nvme/ctrl-sysfs-custom-win.c b/libnvme/src/nvme/ctrl-attrs-custom-win.c similarity index 70% rename from libnvme/src/nvme/ctrl-sysfs-custom-win.c rename to libnvme/src/nvme/ctrl-attrs-custom-win.c index cd0ae80de6..3609db0fd7 100644 --- a/libnvme/src/nvme/ctrl-sysfs-custom-win.c +++ b/libnvme/src/nvme/ctrl-attrs-custom-win.c @@ -12,12 +12,12 @@ #include "lib.h" #include "private-ctrl-map.h" -#include "ctrl-sysfs.c" +#include "generated/ctrl-attrs.c" #ifdef CONFIG_FABRICS -# include "ctrl-sysfs-custom-fabrics.c" +# include "ctrl-attrs-custom-fabrics.c" #else -# include "ctrl-sysfs-custom-no-fabrics.c" +# include "ctrl-attrs-custom-no-fabrics.c" #endif int libnvme_ctrl_load_identity(struct libnvme_ctrl *c) @@ -50,25 +50,25 @@ int libnvme_ctrl_load_identity(struct libnvme_ctrl *c) return ret; } - c->sysfs->firmware = libnvme_ctrl_map_entry_get_firmware(ctrl_entry); - if (!c->sysfs->firmware) + c->attrs->firmware = libnvme_ctrl_map_entry_get_firmware(ctrl_entry); + if (!c->attrs->firmware) return -ENOMEM; - c->sysfs->model = libnvme_ctrl_map_entry_get_model(ctrl_entry); - if (!c->sysfs->model) + c->attrs->model = libnvme_ctrl_map_entry_get_model(ctrl_entry); + if (!c->attrs->model) return -ENOMEM; - c->sysfs->serial = libnvme_ctrl_map_entry_get_serial(ctrl_entry); - if (!c->sysfs->serial) + c->attrs->serial = libnvme_ctrl_map_entry_get_serial(ctrl_entry); + if (!c->attrs->serial) return -ENOMEM; - if (asprintf(&c->sysfs->cntrltype, "%u", id_ctrl.cntrltype) < 0) + if (asprintf(&c->attrs->cntrltype, "%u", id_ctrl.cntrltype) < 0) return -ENOMEM; - if (asprintf(&c->sysfs->cntlid, "%u", le16_to_cpu(id_ctrl.cntlid)) < 0) + if (asprintf(&c->attrs->cntlid, "%u", le16_to_cpu(id_ctrl.cntlid)) < 0) return -ENOMEM; - if (asprintf(&c->sysfs->dctype, "%u", id_ctrl.dctype) < 0) + if (asprintf(&c->attrs->dctype, "%u", id_ctrl.dctype) < 0) return -ENOMEM; return 0; diff --git a/libnvme/src/nvme/ctrl-sysfs.c b/libnvme/src/nvme/generated/ctrl-attrs.c similarity index 59% rename from libnvme/src/nvme/ctrl-sysfs.c rename to libnvme/src/nvme/generated/ctrl-attrs.c index 514d1cc89b..57303cc128 100644 --- a/libnvme/src/nvme/ctrl-sysfs.c +++ b/libnvme/src/nvme/generated/ctrl-attrs.c @@ -27,9 +27,9 @@ #include "private.h" #include "private-tree.h" -#include "ctrl-sysfs.h" +#include "ctrl-attrs.h" -struct libnvme_ctrl_sysfs { +struct libnvme_ctrl_attrs { char *numa_node; char *queue_count; char *sqsize; @@ -48,39 +48,39 @@ struct libnvme_ctrl_sysfs { char *keyring; }; -struct libnvme_ctrl_sysfs *libnvme_ctrl_sysfs_alloc(void) +struct libnvme_ctrl_attrs *libnvme_ctrl_attrs_alloc(void) { - return calloc(1, sizeof(struct libnvme_ctrl_sysfs)); + return calloc(1, sizeof(struct libnvme_ctrl_attrs)); } -void libnvme_ctrl_sysfs_reset( - struct libnvme_ctrl_sysfs *sysfs) +void libnvme_ctrl_attrs_reset( + struct libnvme_ctrl_attrs *attrs) { - if (!sysfs) + if (!attrs) return; - SYSFS_FREE(sysfs->numa_node); - SYSFS_FREE(sysfs->queue_count); - SYSFS_FREE(sysfs->sqsize); - SYSFS_FREE(sysfs->firmware); - SYSFS_FREE(sysfs->model); - SYSFS_FREE(sysfs->serial); - SYSFS_FREE(sysfs->cntrltype); - SYSFS_FREE(sysfs->cntlid); - SYSFS_FREE(sysfs->dctype); - SYSFS_FREE(sysfs->phy_slot); - SYSFS_FREE(sysfs->dhchap_host_key); - SYSFS_FREE(sysfs->dhchap_ctrl_key); - SYSFS_FREE(sysfs->keyring); + ATTR_FREE(attrs->numa_node); + ATTR_FREE(attrs->queue_count); + ATTR_FREE(attrs->sqsize); + ATTR_FREE(attrs->firmware); + ATTR_FREE(attrs->model); + ATTR_FREE(attrs->serial); + ATTR_FREE(attrs->cntrltype); + ATTR_FREE(attrs->cntlid); + ATTR_FREE(attrs->dctype); + ATTR_FREE(attrs->phy_slot); + ATTR_FREE(attrs->dhchap_host_key); + ATTR_FREE(attrs->dhchap_ctrl_key); + ATTR_FREE(attrs->keyring); } -void libnvme_ctrl_sysfs_free( - struct libnvme_ctrl_sysfs *sysfs) +void libnvme_ctrl_attrs_free( + struct libnvme_ctrl_attrs *attrs) { - if (!sysfs) + if (!attrs) return; - free(sysfs); + free(attrs); } __shr_public int libnvme_ctrl_get_numa_node( @@ -92,16 +92,16 @@ __shr_public int libnvme_ctrl_get_numa_node( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->numa_node))) { - c->sysfs->numa_node = libnvme_get_ctrl_attr(c, "numa_node"); - if (!c->sysfs->numa_node) - c->sysfs->numa_node = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->numa_node))) { + c->attrs->numa_node = libnvme_get_ctrl_attr(c, "numa_node"); + if (!c->attrs->numa_node) + c->attrs->numa_node = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->numa_node)) + if (ATTR_IS_ABSENT(c->attrs->numa_node)) return -ENOENT; - *val = c->sysfs->numa_node; + *val = c->attrs->numa_node; return 0; } @@ -114,16 +114,16 @@ __shr_public int libnvme_ctrl_get_queue_count( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->queue_count))) { - c->sysfs->queue_count = libnvme_get_ctrl_attr(c, "queue_count"); - if (!c->sysfs->queue_count) - c->sysfs->queue_count = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->queue_count))) { + c->attrs->queue_count = libnvme_get_ctrl_attr(c, "queue_count"); + if (!c->attrs->queue_count) + c->attrs->queue_count = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->queue_count)) + if (ATTR_IS_ABSENT(c->attrs->queue_count)) return -ENOENT; - *val = c->sysfs->queue_count; + *val = c->attrs->queue_count; return 0; } @@ -136,16 +136,16 @@ __shr_public int libnvme_ctrl_get_sqsize( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->sqsize))) { - c->sysfs->sqsize = libnvme_get_ctrl_attr(c, "sqsize"); - if (!c->sysfs->sqsize) - c->sysfs->sqsize = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->sqsize))) { + c->attrs->sqsize = libnvme_get_ctrl_attr(c, "sqsize"); + if (!c->attrs->sqsize) + c->attrs->sqsize = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->sqsize)) + if (ATTR_IS_ABSENT(c->attrs->sqsize)) return -ENOENT; - *val = c->sysfs->sqsize; + *val = c->attrs->sqsize; return 0; } @@ -163,10 +163,10 @@ __shr_public int libnvme_ctrl_get_command_error_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->command_error_count) != 1) + if (sscanf(str, "%ld", &c->attrs->command_error_count) != 1) return -EINVAL; - *val = c->sysfs->command_error_count; + *val = c->attrs->command_error_count; return 0; } @@ -184,10 +184,10 @@ __shr_public int libnvme_ctrl_get_reset_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->reset_count) != 1) + if (sscanf(str, "%ld", &c->attrs->reset_count) != 1) return -EINVAL; - *val = c->sysfs->reset_count; + *val = c->attrs->reset_count; return 0; } @@ -205,10 +205,10 @@ __shr_public int libnvme_ctrl_get_reconnect_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->reconnect_count) != 1) + if (sscanf(str, "%ld", &c->attrs->reconnect_count) != 1) return -EINVAL; - *val = c->sysfs->reconnect_count; + *val = c->attrs->reconnect_count; return 0; } @@ -216,8 +216,8 @@ __shr_public void libnvme_ctrl_set_firmware( struct libnvme_ctrl *p, const char *firmware) { - SYSFS_FREE(p->sysfs->firmware); - p->sysfs->firmware = firmware ? strdup(firmware) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->firmware); + p->attrs->firmware = firmware ? strdup(firmware) : NO_ATTR; } __shr_public int libnvme_ctrl_get_firmware( @@ -230,18 +230,18 @@ __shr_public int libnvme_ctrl_get_firmware( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->firmware))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->firmware))) { ret = libnvme_ctrl_load_identity(c); if (ret) return ret; - if (!c->sysfs->firmware) - c->sysfs->firmware = NO_SYSFS_ATTR; + if (!c->attrs->firmware) + c->attrs->firmware = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->firmware)) + if (ATTR_IS_ABSENT(c->attrs->firmware)) return -ENOENT; - *val = c->sysfs->firmware; + *val = c->attrs->firmware; return 0; } @@ -249,8 +249,8 @@ __shr_public void libnvme_ctrl_set_model( struct libnvme_ctrl *p, const char *model) { - SYSFS_FREE(p->sysfs->model); - p->sysfs->model = model ? strdup(model) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->model); + p->attrs->model = model ? strdup(model) : NO_ATTR; } __shr_public int libnvme_ctrl_get_model( @@ -263,18 +263,18 @@ __shr_public int libnvme_ctrl_get_model( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->model))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->model))) { ret = libnvme_ctrl_load_identity(c); if (ret) return ret; - if (!c->sysfs->model) - c->sysfs->model = NO_SYSFS_ATTR; + if (!c->attrs->model) + c->attrs->model = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->model)) + if (ATTR_IS_ABSENT(c->attrs->model)) return -ENOENT; - *val = c->sysfs->model; + *val = c->attrs->model; return 0; } @@ -282,8 +282,8 @@ __shr_public void libnvme_ctrl_set_serial( struct libnvme_ctrl *p, const char *serial) { - SYSFS_FREE(p->sysfs->serial); - p->sysfs->serial = serial ? strdup(serial) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->serial); + p->attrs->serial = serial ? strdup(serial) : NO_ATTR; } __shr_public int libnvme_ctrl_get_serial( @@ -296,18 +296,18 @@ __shr_public int libnvme_ctrl_get_serial( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->serial))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->serial))) { ret = libnvme_ctrl_load_identity(c); if (ret) return ret; - if (!c->sysfs->serial) - c->sysfs->serial = NO_SYSFS_ATTR; + if (!c->attrs->serial) + c->attrs->serial = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->serial)) + if (ATTR_IS_ABSENT(c->attrs->serial)) return -ENOENT; - *val = c->sysfs->serial; + *val = c->attrs->serial; return 0; } @@ -315,8 +315,8 @@ __shr_public void libnvme_ctrl_set_cntrltype( struct libnvme_ctrl *p, const char *cntrltype) { - SYSFS_FREE(p->sysfs->cntrltype); - p->sysfs->cntrltype = cntrltype ? strdup(cntrltype) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->cntrltype); + p->attrs->cntrltype = cntrltype ? strdup(cntrltype) : NO_ATTR; } __shr_public int libnvme_ctrl_get_cntrltype( @@ -329,18 +329,18 @@ __shr_public int libnvme_ctrl_get_cntrltype( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->cntrltype))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->cntrltype))) { ret = libnvme_ctrl_load_identity(c); if (ret) return ret; - if (!c->sysfs->cntrltype) - c->sysfs->cntrltype = NO_SYSFS_ATTR; + if (!c->attrs->cntrltype) + c->attrs->cntrltype = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->cntrltype)) + if (ATTR_IS_ABSENT(c->attrs->cntrltype)) return -ENOENT; - *val = c->sysfs->cntrltype; + *val = c->attrs->cntrltype; return 0; } @@ -348,8 +348,8 @@ __shr_public void libnvme_ctrl_set_cntlid( struct libnvme_ctrl *p, const char *cntlid) { - SYSFS_FREE(p->sysfs->cntlid); - p->sysfs->cntlid = cntlid ? strdup(cntlid) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->cntlid); + p->attrs->cntlid = cntlid ? strdup(cntlid) : NO_ATTR; } __shr_public int libnvme_ctrl_get_cntlid( @@ -362,18 +362,18 @@ __shr_public int libnvme_ctrl_get_cntlid( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->cntlid))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->cntlid))) { ret = libnvme_ctrl_load_identity(c); if (ret) return ret; - if (!c->sysfs->cntlid) - c->sysfs->cntlid = NO_SYSFS_ATTR; + if (!c->attrs->cntlid) + c->attrs->cntlid = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->cntlid)) + if (ATTR_IS_ABSENT(c->attrs->cntlid)) return -ENOENT; - *val = c->sysfs->cntlid; + *val = c->attrs->cntlid; return 0; } @@ -381,8 +381,8 @@ __shr_public void libnvme_ctrl_set_dctype( struct libnvme_ctrl *p, const char *dctype) { - SYSFS_FREE(p->sysfs->dctype); - p->sysfs->dctype = dctype ? strdup(dctype) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->dctype); + p->attrs->dctype = dctype ? strdup(dctype) : NO_ATTR; } __shr_public int libnvme_ctrl_get_dctype( @@ -395,18 +395,18 @@ __shr_public int libnvme_ctrl_get_dctype( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->dctype))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->dctype))) { ret = libnvme_ctrl_load_identity(c); if (ret) return ret; - if (!c->sysfs->dctype) - c->sysfs->dctype = NO_SYSFS_ATTR; + if (!c->attrs->dctype) + c->attrs->dctype = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->dctype)) + if (ATTR_IS_ABSENT(c->attrs->dctype)) return -ENOENT; - *val = c->sysfs->dctype; + *val = c->attrs->dctype; return 0; } @@ -420,18 +420,18 @@ __shr_public int libnvme_ctrl_get_phy_slot( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->phy_slot))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->phy_slot))) { ret = libnvme_ctrl_load_phy_slot(c); if (ret) return ret; - if (!c->sysfs->phy_slot) - c->sysfs->phy_slot = NO_SYSFS_ATTR; + if (!c->attrs->phy_slot) + c->attrs->phy_slot = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->phy_slot)) + if (ATTR_IS_ABSENT(c->attrs->phy_slot)) return -ENOENT; - *val = c->sysfs->phy_slot; + *val = c->attrs->phy_slot; return 0; } @@ -439,9 +439,9 @@ __shr_public void libnvme_ctrl_set_dhchap_host_key( struct libnvme_ctrl *p, const char *dhchap_host_key) { - SYSFS_FREE(p->sysfs->dhchap_host_key); - p->sysfs->dhchap_host_key = - dhchap_host_key ? strdup(dhchap_host_key) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->dhchap_host_key); + p->attrs->dhchap_host_key = + dhchap_host_key ? strdup(dhchap_host_key) : NO_ATTR; } __shr_public int libnvme_ctrl_get_dhchap_host_key( @@ -454,18 +454,18 @@ __shr_public int libnvme_ctrl_get_dhchap_host_key( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->dhchap_host_key))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->dhchap_host_key))) { ret = libnvmf_ctrl_load_fabrics_attrs(c); if (ret) return ret; - if (!c->sysfs->dhchap_host_key) - c->sysfs->dhchap_host_key = NO_SYSFS_ATTR; + if (!c->attrs->dhchap_host_key) + c->attrs->dhchap_host_key = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->dhchap_host_key)) + if (ATTR_IS_ABSENT(c->attrs->dhchap_host_key)) return -ENOENT; - *val = c->sysfs->dhchap_host_key; + *val = c->attrs->dhchap_host_key; return 0; } @@ -473,9 +473,9 @@ __shr_public void libnvme_ctrl_set_dhchap_ctrl_key( struct libnvme_ctrl *p, const char *dhchap_ctrl_key) { - SYSFS_FREE(p->sysfs->dhchap_ctrl_key); - p->sysfs->dhchap_ctrl_key = - dhchap_ctrl_key ? strdup(dhchap_ctrl_key) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->dhchap_ctrl_key); + p->attrs->dhchap_ctrl_key = + dhchap_ctrl_key ? strdup(dhchap_ctrl_key) : NO_ATTR; } __shr_public int libnvme_ctrl_get_dhchap_ctrl_key( @@ -488,18 +488,18 @@ __shr_public int libnvme_ctrl_get_dhchap_ctrl_key( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->dhchap_ctrl_key))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->dhchap_ctrl_key))) { ret = libnvmf_ctrl_load_fabrics_attrs(c); if (ret) return ret; - if (!c->sysfs->dhchap_ctrl_key) - c->sysfs->dhchap_ctrl_key = NO_SYSFS_ATTR; + if (!c->attrs->dhchap_ctrl_key) + c->attrs->dhchap_ctrl_key = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->dhchap_ctrl_key)) + if (ATTR_IS_ABSENT(c->attrs->dhchap_ctrl_key)) return -ENOENT; - *val = c->sysfs->dhchap_ctrl_key; + *val = c->attrs->dhchap_ctrl_key; return 0; } @@ -507,8 +507,8 @@ __shr_public void libnvme_ctrl_set_keyring( struct libnvme_ctrl *p, const char *keyring) { - SYSFS_FREE(p->sysfs->keyring); - p->sysfs->keyring = keyring ? strdup(keyring) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->keyring); + p->attrs->keyring = keyring ? strdup(keyring) : NO_ATTR; } __shr_public int libnvme_ctrl_get_keyring( @@ -521,18 +521,18 @@ __shr_public int libnvme_ctrl_get_keyring( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->keyring))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->keyring))) { ret = libnvmf_ctrl_load_fabrics_attrs(c); if (ret) return ret; - if (!c->sysfs->keyring) - c->sysfs->keyring = NO_SYSFS_ATTR; + if (!c->attrs->keyring) + c->attrs->keyring = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->keyring)) + if (ATTR_IS_ABSENT(c->attrs->keyring)) return -ENOENT; - *val = c->sysfs->keyring; + *val = c->attrs->keyring; return 0; } diff --git a/libnvme/src/nvme/ctrl-sysfs.h b/libnvme/src/nvme/generated/ctrl-attrs.h similarity index 96% rename from libnvme/src/nvme/ctrl-sysfs.h rename to libnvme/src/nvme/generated/ctrl-attrs.h index a2ef83ee88..39366b7724 100644 --- a/libnvme/src/nvme/ctrl-sysfs.h +++ b/libnvme/src/nvme/generated/ctrl-attrs.h @@ -20,26 +20,26 @@ #pragma once -/* Opaque: defined only in the generated ctrl-sysfs.c. No +/* Opaque: defined only in the generated ctrl-attrs.c. No * other file may see its layout -- every field is reachable * only through the accessors below. */ -struct libnvme_ctrl_sysfs; +struct libnvme_ctrl_attrs; /* Internal: allocate/reset/free the opaque struct. Not part * of the public API, not listed in any .ld. */ -struct libnvme_ctrl_sysfs *libnvme_ctrl_sysfs_alloc(void); -void libnvme_ctrl_sysfs_reset( - struct libnvme_ctrl_sysfs *sysfs); -void libnvme_ctrl_sysfs_free( - struct libnvme_ctrl_sysfs *sysfs); +struct libnvme_ctrl_attrs *libnvme_ctrl_attrs_alloc(void); +void libnvme_ctrl_attrs_reset( + struct libnvme_ctrl_attrs *attrs); +void libnvme_ctrl_attrs_free( + struct libnvme_ctrl_attrs *attrs); /* Internal: loader callbacks, one per group above. Each * fills every member of its group in a single call, * returning 0 on success or a negative errno. Defined in - * whichever hand-written *-custom-*.c matches the build - * (see that file's own #ifdef/#include selection). + * whichever hand-written *-attrs-custom-*.c matches the + * build (see that file's own #ifdef/#include selection). */ int libnvme_ctrl_load_identity(struct libnvme_ctrl *c); int libnvme_ctrl_load_phy_slot(struct libnvme_ctrl *c); diff --git a/libnvme/src/nvme/ns-sysfs.c b/libnvme/src/nvme/generated/ns-attrs.c similarity index 72% rename from libnvme/src/nvme/ns-sysfs.c rename to libnvme/src/nvme/generated/ns-attrs.c index cf2624654e..9cd414aac1 100644 --- a/libnvme/src/nvme/ns-sysfs.c +++ b/libnvme/src/nvme/generated/ns-attrs.c @@ -27,9 +27,9 @@ #include "private.h" #include "private-tree.h" -#include "ns-sysfs.h" +#include "ns-attrs.h" -struct libnvme_ns_sysfs { +struct libnvme_ns_attrs { int *lba_size; int *lba_shift; uint64_t *lba_count; @@ -45,35 +45,35 @@ struct libnvme_ns_sysfs { long io_fail_no_available_path_count; }; -struct libnvme_ns_sysfs *libnvme_ns_sysfs_alloc(void) +struct libnvme_ns_attrs *libnvme_ns_attrs_alloc(void) { - return calloc(1, sizeof(struct libnvme_ns_sysfs)); + return calloc(1, sizeof(struct libnvme_ns_attrs)); } -void libnvme_ns_sysfs_reset( - struct libnvme_ns_sysfs *sysfs) +void libnvme_ns_attrs_reset( + struct libnvme_ns_attrs *attrs) { - if (!sysfs) + if (!attrs) return; } -void libnvme_ns_sysfs_free( - struct libnvme_ns_sysfs *sysfs) +void libnvme_ns_attrs_free( + struct libnvme_ns_attrs *attrs) { - if (!sysfs) + if (!attrs) return; - SYSFS_FREE(sysfs->lba_size); - SYSFS_FREE(sysfs->lba_shift); - SYSFS_FREE(sysfs->lba_count); - SYSFS_FREE(sysfs->lba_util); - SYSFS_FREE(sysfs->meta_size); - SYSFS_FREE(sysfs->csi); - SYSFS_FREE(sysfs->eui64); - SYSFS_FREE(sysfs->nguid); - SYSFS_FREE(sysfs->uuid); - free(sysfs); + ATTR_FREE(attrs->lba_size); + ATTR_FREE(attrs->lba_shift); + ATTR_FREE(attrs->lba_count); + ATTR_FREE(attrs->lba_util); + ATTR_FREE(attrs->meta_size); + ATTR_FREE(attrs->csi); + ATTR_FREE(attrs->eui64); + ATTR_FREE(attrs->nguid); + ATTR_FREE(attrs->uuid); + free(attrs); } __shr_public int libnvme_ns_get_command_retry_count( @@ -90,10 +90,10 @@ __shr_public int libnvme_ns_get_command_retry_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->command_retry_count) != 1) + if (sscanf(str, "%ld", &c->attrs->command_retry_count) != 1) return -EINVAL; - *val = c->sysfs->command_retry_count; + *val = c->attrs->command_retry_count; return 0; } @@ -111,10 +111,10 @@ __shr_public int libnvme_ns_get_command_error_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->command_error_count) != 1) + if (sscanf(str, "%ld", &c->attrs->command_error_count) != 1) return -EINVAL; - *val = c->sysfs->command_error_count; + *val = c->attrs->command_error_count; return 0; } @@ -132,10 +132,10 @@ __shr_public int libnvme_ns_get_io_requeue_no_usable_path_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->io_requeue_no_usable_path_count) != 1) + if (sscanf(str, "%ld", &c->attrs->io_requeue_no_usable_path_count) != 1) return -EINVAL; - *val = c->sysfs->io_requeue_no_usable_path_count; + *val = c->attrs->io_requeue_no_usable_path_count; return 0; } @@ -153,10 +153,10 @@ __shr_public int libnvme_ns_get_io_fail_no_available_path_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->io_fail_no_available_path_count) != 1) + if (sscanf(str, "%ld", &c->attrs->io_fail_no_available_path_count) != 1) return -EINVAL; - *val = c->sysfs->io_fail_no_available_path_count; + *val = c->attrs->io_fail_no_available_path_count; return 0; } diff --git a/libnvme/src/nvme/ns-sysfs.h b/libnvme/src/nvme/generated/ns-attrs.h similarity index 96% rename from libnvme/src/nvme/ns-sysfs.h rename to libnvme/src/nvme/generated/ns-attrs.h index 67ad8d4c5c..5c84bf4358 100644 --- a/libnvme/src/nvme/ns-sysfs.h +++ b/libnvme/src/nvme/generated/ns-attrs.h @@ -20,20 +20,20 @@ #pragma once -/* Opaque: defined only in the generated ns-sysfs.c. No +/* Opaque: defined only in the generated ns-attrs.c. No * other file may see its layout -- every field is reachable * only through the accessors below. */ -struct libnvme_ns_sysfs; +struct libnvme_ns_attrs; /* Internal: allocate/reset/free the opaque struct. Not part * of the public API, not listed in any .ld. */ -struct libnvme_ns_sysfs *libnvme_ns_sysfs_alloc(void); -void libnvme_ns_sysfs_reset( - struct libnvme_ns_sysfs *sysfs); -void libnvme_ns_sysfs_free( - struct libnvme_ns_sysfs *sysfs); +struct libnvme_ns_attrs *libnvme_ns_attrs_alloc(void); +void libnvme_ns_attrs_reset( + struct libnvme_ns_attrs *attrs); +void libnvme_ns_attrs_free( + struct libnvme_ns_attrs *attrs); /** * libnvme_ns_get_lba_size() - Get lba_size. diff --git a/libnvme/src/nvme/path-sysfs-linux.c b/libnvme/src/nvme/generated/path-attrs-linux.c similarity index 71% rename from libnvme/src/nvme/path-sysfs-linux.c rename to libnvme/src/nvme/generated/path-attrs-linux.c index c84c66049c..b20ac07275 100644 --- a/libnvme/src/nvme/path-sysfs-linux.c +++ b/libnvme/src/nvme/generated/path-attrs-linux.c @@ -32,14 +32,14 @@ __shr_public int libnvme_path_get_ana_state( if (!str) return -ENOENT; - if (!c->sysfs->ana_state || strcmp(str, c->sysfs->ana_state)) { - free(c->sysfs->ana_state); - c->sysfs->ana_state = strdup(str); - if (!c->sysfs->ana_state) + if (!c->attrs->ana_state || strcmp(str, c->attrs->ana_state)) { + free(c->attrs->ana_state); + c->attrs->ana_state = strdup(str); + if (!c->attrs->ana_state) return -ENOMEM; } - *val = c->sysfs->ana_state; + *val = c->attrs->ana_state; return 0; } @@ -52,16 +52,16 @@ __shr_public int libnvme_path_get_numa_nodes( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->numa_nodes))) { - c->sysfs->numa_nodes = libnvme_get_path_attr(c, "numa_nodes"); - if (!c->sysfs->numa_nodes) - c->sysfs->numa_nodes = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->numa_nodes))) { + c->attrs->numa_nodes = libnvme_get_path_attr(c, "numa_nodes"); + if (!c->attrs->numa_nodes) + c->attrs->numa_nodes = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->numa_nodes)) + if (ATTR_IS_ABSENT(c->attrs->numa_nodes)) return -ENOENT; - *val = c->sysfs->numa_nodes; + *val = c->attrs->numa_nodes; return 0; } @@ -74,28 +74,28 @@ __shr_public int libnvme_path_get_grpid( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->grpid))) { + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->grpid))) { __cleanup_free char *str = NULL; str = libnvme_get_path_attr(c, "ana_grpid"); if (!str) - c->sysfs->grpid = (int *)NO_SYSFS_ATTR; + c->attrs->grpid = (int *)NO_ATTR; else { - c->sysfs->grpid = malloc(sizeof(int)); - if (!c->sysfs->grpid) + c->attrs->grpid = malloc(sizeof(int)); + if (!c->attrs->grpid) return -ENOMEM; - if (sscanf(str, "%d", c->sysfs->grpid) != 1) { - free(c->sysfs->grpid); - c->sysfs->grpid = NULL; + if (sscanf(str, "%d", c->attrs->grpid) != 1) { + free(c->attrs->grpid); + c->attrs->grpid = NULL; return -EINVAL; } } } - if (SYSFS_IS_ABSENT(c->sysfs->grpid)) + if (ATTR_IS_ABSENT(c->attrs->grpid)) return -ENOENT; - *val = *c->sysfs->grpid; + *val = *c->attrs->grpid; return 0; } @@ -113,10 +113,10 @@ __shr_public int libnvme_path_get_queue_depth( if (!str) return -ENOENT; - if (sscanf(str, "%d", &c->sysfs->queue_depth) != 1) + if (sscanf(str, "%d", &c->attrs->queue_depth) != 1) return -EINVAL; - *val = c->sysfs->queue_depth; + *val = c->attrs->queue_depth; return 0; } @@ -134,10 +134,10 @@ __shr_public int libnvme_path_get_multipath_failover_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->multipath_failover_count) != 1) + if (sscanf(str, "%ld", &c->attrs->multipath_failover_count) != 1) return -EINVAL; - *val = c->sysfs->multipath_failover_count; + *val = c->attrs->multipath_failover_count; return 0; } @@ -155,10 +155,10 @@ __shr_public int libnvme_path_get_command_retry_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->command_retry_count) != 1) + if (sscanf(str, "%ld", &c->attrs->command_retry_count) != 1) return -EINVAL; - *val = c->sysfs->command_retry_count; + *val = c->attrs->command_retry_count; return 0; } @@ -176,10 +176,10 @@ __shr_public int libnvme_path_get_command_error_count( if (!str) return -ENOENT; - if (sscanf(str, "%ld", &c->sysfs->command_error_count) != 1) + if (sscanf(str, "%ld", &c->attrs->command_error_count) != 1) return -EINVAL; - *val = c->sysfs->command_error_count; + *val = c->attrs->command_error_count; return 0; } diff --git a/libnvme/src/nvme/path-sysfs-win.c b/libnvme/src/nvme/generated/path-attrs-win.c similarity index 100% rename from libnvme/src/nvme/path-sysfs-win.c rename to libnvme/src/nvme/generated/path-attrs-win.c diff --git a/libnvme/src/nvme/path-sysfs.c b/libnvme/src/nvme/generated/path-attrs.c similarity index 72% rename from libnvme/src/nvme/path-sysfs.c rename to libnvme/src/nvme/generated/path-attrs.c index f4f03310e9..a9a2d8f2cd 100644 --- a/libnvme/src/nvme/path-sysfs.c +++ b/libnvme/src/nvme/generated/path-attrs.c @@ -27,9 +27,9 @@ #include "private.h" #include "private-tree.h" -#include "path-sysfs.h" +#include "path-attrs.h" -struct libnvme_path_sysfs { +struct libnvme_path_attrs { char *ana_state; char *numa_nodes; int *grpid; @@ -39,28 +39,28 @@ struct libnvme_path_sysfs { long command_error_count; }; -struct libnvme_path_sysfs *libnvme_path_sysfs_alloc(void) +struct libnvme_path_attrs *libnvme_path_attrs_alloc(void) { - return calloc(1, sizeof(struct libnvme_path_sysfs)); + return calloc(1, sizeof(struct libnvme_path_attrs)); } -void libnvme_path_sysfs_reset( - struct libnvme_path_sysfs *sysfs) +void libnvme_path_attrs_reset( + struct libnvme_path_attrs *attrs) { - if (!sysfs) + if (!attrs) return; } -void libnvme_path_sysfs_free( - struct libnvme_path_sysfs *sysfs) +void libnvme_path_attrs_free( + struct libnvme_path_attrs *attrs) { - if (!sysfs) + if (!attrs) return; - SYSFS_FREE(sysfs->ana_state); - SYSFS_FREE(sysfs->numa_nodes); - SYSFS_FREE(sysfs->grpid); - free(sysfs); + ATTR_FREE(attrs->ana_state); + ATTR_FREE(attrs->numa_nodes); + ATTR_FREE(attrs->grpid); + free(attrs); } diff --git a/libnvme/src/nvme/path-sysfs.h b/libnvme/src/nvme/generated/path-attrs.h similarity index 93% rename from libnvme/src/nvme/path-sysfs.h rename to libnvme/src/nvme/generated/path-attrs.h index 8e547a351e..6c8af96fcd 100644 --- a/libnvme/src/nvme/path-sysfs.h +++ b/libnvme/src/nvme/generated/path-attrs.h @@ -20,20 +20,20 @@ #pragma once -/* Opaque: defined only in the generated path-sysfs.c. No +/* Opaque: defined only in the generated path-attrs.c. No * other file may see its layout -- every field is reachable * only through the accessors below. */ -struct libnvme_path_sysfs; +struct libnvme_path_attrs; /* Internal: allocate/reset/free the opaque struct. Not part * of the public API, not listed in any .ld. */ -struct libnvme_path_sysfs *libnvme_path_sysfs_alloc(void); -void libnvme_path_sysfs_reset( - struct libnvme_path_sysfs *sysfs); -void libnvme_path_sysfs_free( - struct libnvme_path_sysfs *sysfs); +struct libnvme_path_attrs *libnvme_path_attrs_alloc(void); +void libnvme_path_attrs_reset( + struct libnvme_path_attrs *attrs); +void libnvme_path_attrs_free( + struct libnvme_path_attrs *attrs); /** * libnvme_path_get_ana_state() - Get ana_state. diff --git a/libnvme/src/nvme/subsys-sysfs.c b/libnvme/src/nvme/generated/subsys-attrs.c similarity index 58% rename from libnvme/src/nvme/subsys-sysfs.c rename to libnvme/src/nvme/generated/subsys-attrs.c index 3e65aad463..2db7eef1e1 100644 --- a/libnvme/src/nvme/subsys-sysfs.c +++ b/libnvme/src/nvme/generated/subsys-attrs.c @@ -27,47 +27,47 @@ #include "private.h" #include "private-tree.h" -#include "subsys-sysfs.h" +#include "subsys-attrs.h" -struct libnvme_subsystem_sysfs { +struct libnvme_subsystem_attrs { char *model; char *serial; char *firmware; char *iopolicy; }; -struct libnvme_subsystem_sysfs *libnvme_subsystem_sysfs_alloc(void) +struct libnvme_subsystem_attrs *libnvme_subsystem_attrs_alloc(void) { - return calloc(1, sizeof(struct libnvme_subsystem_sysfs)); + return calloc(1, sizeof(struct libnvme_subsystem_attrs)); } -void libnvme_subsystem_sysfs_reset( - struct libnvme_subsystem_sysfs *sysfs) +void libnvme_subsystem_attrs_reset( + struct libnvme_subsystem_attrs *attrs) { - if (!sysfs) + if (!attrs) return; } -void libnvme_subsystem_sysfs_free( - struct libnvme_subsystem_sysfs *sysfs) +void libnvme_subsystem_attrs_free( + struct libnvme_subsystem_attrs *attrs) { - if (!sysfs) + if (!attrs) return; - SYSFS_FREE(sysfs->model); - SYSFS_FREE(sysfs->serial); - SYSFS_FREE(sysfs->firmware); - SYSFS_FREE(sysfs->iopolicy); - free(sysfs); + ATTR_FREE(attrs->model); + ATTR_FREE(attrs->serial); + ATTR_FREE(attrs->firmware); + ATTR_FREE(attrs->iopolicy); + free(attrs); } __shr_public void libnvme_subsystem_set_model( struct libnvme_subsystem *p, const char *model) { - SYSFS_FREE(p->sysfs->model); - p->sysfs->model = model ? strdup(model) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->model); + p->attrs->model = model ? strdup(model) : NO_ATTR; } __shr_public int libnvme_subsystem_get_model( @@ -79,16 +79,16 @@ __shr_public int libnvme_subsystem_get_model( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->model))) { - c->sysfs->model = libnvme_get_subsys_attr(c, "model"); - if (!c->sysfs->model) - c->sysfs->model = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->model))) { + c->attrs->model = libnvme_get_subsys_attr(c, "model"); + if (!c->attrs->model) + c->attrs->model = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->model)) + if (ATTR_IS_ABSENT(c->attrs->model)) return -ENOENT; - *val = c->sysfs->model; + *val = c->attrs->model; return 0; } @@ -96,8 +96,8 @@ __shr_public void libnvme_subsystem_set_serial( struct libnvme_subsystem *p, const char *serial) { - SYSFS_FREE(p->sysfs->serial); - p->sysfs->serial = serial ? strdup(serial) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->serial); + p->attrs->serial = serial ? strdup(serial) : NO_ATTR; } __shr_public int libnvme_subsystem_get_serial( @@ -109,16 +109,16 @@ __shr_public int libnvme_subsystem_get_serial( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->serial))) { - c->sysfs->serial = libnvme_get_subsys_attr(c, "serial"); - if (!c->sysfs->serial) - c->sysfs->serial = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->serial))) { + c->attrs->serial = libnvme_get_subsys_attr(c, "serial"); + if (!c->attrs->serial) + c->attrs->serial = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->serial)) + if (ATTR_IS_ABSENT(c->attrs->serial)) return -ENOENT; - *val = c->sysfs->serial; + *val = c->attrs->serial; return 0; } @@ -126,8 +126,8 @@ __shr_public void libnvme_subsystem_set_firmware( struct libnvme_subsystem *p, const char *firmware) { - SYSFS_FREE(p->sysfs->firmware); - p->sysfs->firmware = firmware ? strdup(firmware) : NO_SYSFS_ATTR; + ATTR_FREE(p->attrs->firmware); + p->attrs->firmware = firmware ? strdup(firmware) : NO_ATTR; } __shr_public int libnvme_subsystem_get_firmware( @@ -139,16 +139,16 @@ __shr_public int libnvme_subsystem_get_firmware( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(c->sysfs->firmware))) { - c->sysfs->firmware = libnvme_get_subsys_attr(c, "firmware_rev"); - if (!c->sysfs->firmware) - c->sysfs->firmware = NO_SYSFS_ATTR; + if (__shr_unlikely(!ATTR_IS_LOADED(c->attrs->firmware))) { + c->attrs->firmware = libnvme_get_subsys_attr(c, "firmware_rev"); + if (!c->attrs->firmware) + c->attrs->firmware = NO_ATTR; } - if (SYSFS_IS_ABSENT(c->sysfs->firmware)) + if (ATTR_IS_ABSENT(c->attrs->firmware)) return -ENOENT; - *val = c->sysfs->firmware; + *val = c->attrs->firmware; return 0; } @@ -166,14 +166,14 @@ __shr_public int libnvme_subsystem_get_iopolicy( if (!str) return -ENOENT; - if (!c->sysfs->iopolicy || strcmp(str, c->sysfs->iopolicy)) { - free(c->sysfs->iopolicy); - c->sysfs->iopolicy = strdup(str); - if (!c->sysfs->iopolicy) + if (!c->attrs->iopolicy || strcmp(str, c->attrs->iopolicy)) { + free(c->attrs->iopolicy); + c->attrs->iopolicy = strdup(str); + if (!c->attrs->iopolicy) return -ENOMEM; } - *val = c->sysfs->iopolicy; + *val = c->attrs->iopolicy; return 0; } diff --git a/libnvme/src/nvme/subsys-sysfs.h b/libnvme/src/nvme/generated/subsys-attrs.h similarity index 91% rename from libnvme/src/nvme/subsys-sysfs.h rename to libnvme/src/nvme/generated/subsys-attrs.h index 888c26af15..7c9114ad50 100644 --- a/libnvme/src/nvme/subsys-sysfs.h +++ b/libnvme/src/nvme/generated/subsys-attrs.h @@ -20,20 +20,20 @@ #pragma once -/* Opaque: defined only in the generated subsys-sysfs.c. No +/* Opaque: defined only in the generated subsys-attrs.c. No * other file may see its layout -- every field is reachable * only through the accessors below. */ -struct libnvme_subsystem_sysfs; +struct libnvme_subsystem_attrs; /* Internal: allocate/reset/free the opaque struct. Not part * of the public API, not listed in any .ld. */ -struct libnvme_subsystem_sysfs *libnvme_subsystem_sysfs_alloc(void); -void libnvme_subsystem_sysfs_reset( - struct libnvme_subsystem_sysfs *sysfs); -void libnvme_subsystem_sysfs_free( - struct libnvme_subsystem_sysfs *sysfs); +struct libnvme_subsystem_attrs *libnvme_subsystem_attrs_alloc(void); +void libnvme_subsystem_attrs_reset( + struct libnvme_subsystem_attrs *attrs); +void libnvme_subsystem_attrs_free( + struct libnvme_subsystem_attrs *attrs); /** * libnvme_subsystem_set_model() - Set model. diff --git a/libnvme/src/nvme/ns-sysfs-custom-linux.c b/libnvme/src/nvme/ns-attrs-custom-linux.c similarity index 69% rename from libnvme/src/nvme/ns-sysfs-custom-linux.c rename to libnvme/src/nvme/ns-attrs-custom-linux.c index 9c7b5c6b52..06b8bbd469 100644 --- a/libnvme/src/nvme/ns-sysfs-custom-linux.c +++ b/libnvme/src/nvme/ns-attrs-custom-linux.c @@ -12,12 +12,12 @@ #include "mem.h" #include "util.h" -#include "ns-sysfs.c" +#include "generated/ns-attrs.c" /* * No "csi" attribute: lba_count/lba_util/meta_size come from one * Identify Namespace command instead. Each field's own - * SYSFS_IS_LOADED() check keeps a caller that only reads one of these + * ATTR_IS_LOADED() check keeps a caller that only reads one of these * three from paying for more than one Identify command in the common * case, but a prior call can leave some fields loaded and others not * (e.g. -ENOMEM after lba_count's malloc but before lba_util's) -- @@ -40,25 +40,25 @@ static int ns_identify_geometry(struct libnvme_ns *n) nvme_id_ns_flbas_to_lbaf_inuse(id->flbas, &flbas); - if (!SYSFS_IS_LOADED(n->sysfs->lba_count)) { - n->sysfs->lba_count = malloc(sizeof(uint64_t)); - if (!n->sysfs->lba_count) + if (!ATTR_IS_LOADED(n->attrs->lba_count)) { + n->attrs->lba_count = malloc(sizeof(uint64_t)); + if (!n->attrs->lba_count) return -ENOMEM; - *n->sysfs->lba_count = le64_to_cpu(id->nsze); + *n->attrs->lba_count = le64_to_cpu(id->nsze); } - if (!SYSFS_IS_LOADED(n->sysfs->lba_util)) { - n->sysfs->lba_util = malloc(sizeof(uint64_t)); - if (!n->sysfs->lba_util) + if (!ATTR_IS_LOADED(n->attrs->lba_util)) { + n->attrs->lba_util = malloc(sizeof(uint64_t)); + if (!n->attrs->lba_util) return -ENOMEM; - *n->sysfs->lba_util = le64_to_cpu(id->nuse); + *n->attrs->lba_util = le64_to_cpu(id->nuse); } - if (!SYSFS_IS_LOADED(n->sysfs->meta_size)) { - n->sysfs->meta_size = malloc(sizeof(int)); - if (!n->sysfs->meta_size) + if (!ATTR_IS_LOADED(n->attrs->meta_size)) { + n->attrs->meta_size = malloc(sizeof(int)); + if (!n->attrs->meta_size) return -ENOMEM; - *n->sysfs->meta_size = le16_to_cpu(id->lbaf[flbas].ms); + *n->attrs->meta_size = le16_to_cpu(id->lbaf[flbas].ms); } return 0; @@ -92,11 +92,11 @@ static int ns_load_lba_count_from_size_attr(struct libnvme_ns *n) if (ret) return ret; - n->sysfs->lba_count = malloc(sizeof(uint64_t)); - if (!n->sysfs->lba_count) + n->attrs->lba_count = malloc(sizeof(uint64_t)); + if (!n->attrs->lba_count) return -ENOMEM; - *n->sysfs->lba_count = size >> (lba_shift - SECTOR_SHIFT); + *n->attrs->lba_count = size >> (lba_shift - SECTOR_SHIFT); return 0; } @@ -117,11 +117,11 @@ static int ns_load_lba_util_attr(struct libnvme_ns *n) if (endptr == str) return -EINVAL; - n->sysfs->lba_util = malloc(sizeof(uint64_t)); - if (!n->sysfs->lba_util) + n->attrs->lba_util = malloc(sizeof(uint64_t)); + if (!n->attrs->lba_util) return -ENOMEM; - *n->sysfs->lba_util = val; + *n->attrs->lba_util = val; return 0; } @@ -142,11 +142,11 @@ static int ns_load_meta_size_attr(struct libnvme_ns *n) if (endptr == str) return -EINVAL; - n->sysfs->meta_size = malloc(sizeof(int)); - if (!n->sysfs->meta_size) + n->attrs->meta_size = malloc(sizeof(int)); + if (!n->attrs->meta_size) return -ENOMEM; - *n->sysfs->meta_size = (int)val; + *n->attrs->meta_size = (int)val; return 0; } @@ -185,26 +185,26 @@ __shr_public int libnvme_ns_get_lba_size( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->lba_size))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->lba_size))) { str = libnvme_get_ns_attr(n, "queue/logical_block_size"); if (!str) - n->sysfs->lba_size = (int *)NO_SYSFS_ATTR; + n->attrs->lba_size = (int *)NO_ATTR; else { - n->sysfs->lba_size = malloc(sizeof(int)); - if (!n->sysfs->lba_size) + n->attrs->lba_size = malloc(sizeof(int)); + if (!n->attrs->lba_size) return -ENOMEM; - if (sscanf(str, "%d", n->sysfs->lba_size) != 1) { - free(n->sysfs->lba_size); - n->sysfs->lba_size = NULL; + if (sscanf(str, "%d", n->attrs->lba_size) != 1) { + free(n->attrs->lba_size); + n->attrs->lba_size = NULL; return -EINVAL; } } } - if (SYSFS_IS_ABSENT(n->sysfs->lba_size)) + if (ATTR_IS_ABSENT(n->attrs->lba_size)) return -ENOENT; - *val = *n->sysfs->lba_size; + *val = *n->attrs->lba_size; return 0; } @@ -243,7 +243,7 @@ __shr_public int libnvme_ns_get_lba_count( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->lba_count))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->lba_count))) { has_csi = ns_csi_attr_exists(n); if (has_csi < 0) return has_csi; @@ -254,14 +254,14 @@ __shr_public int libnvme_ns_get_lba_count( ret = ns_identify_geometry(n); if (ret) return ret; - if (!n->sysfs->lba_count) - n->sysfs->lba_count = (uint64_t *)NO_SYSFS_ATTR; + if (!n->attrs->lba_count) + n->attrs->lba_count = (uint64_t *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->lba_count)) + if (ATTR_IS_ABSENT(n->attrs->lba_count)) return -ENOENT; - *val = *n->sysfs->lba_count; + *val = *n->attrs->lba_count; return 0; } @@ -275,7 +275,7 @@ __shr_public int libnvme_ns_get_lba_util( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->lba_util))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->lba_util))) { has_csi = ns_csi_attr_exists(n); if (has_csi < 0) return has_csi; @@ -286,14 +286,14 @@ __shr_public int libnvme_ns_get_lba_util( ret = ns_identify_geometry(n); if (ret) return ret; - if (!n->sysfs->lba_util) - n->sysfs->lba_util = (uint64_t *)NO_SYSFS_ATTR; + if (!n->attrs->lba_util) + n->attrs->lba_util = (uint64_t *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->lba_util)) + if (ATTR_IS_ABSENT(n->attrs->lba_util)) return -ENOENT; - *val = *n->sysfs->lba_util; + *val = *n->attrs->lba_util; return 0; } @@ -307,7 +307,7 @@ __shr_public int libnvme_ns_get_meta_size( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->meta_size))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->meta_size))) { has_csi = ns_csi_attr_exists(n); if (has_csi < 0) return has_csi; @@ -318,14 +318,14 @@ __shr_public int libnvme_ns_get_meta_size( ret = ns_identify_geometry(n); if (ret) return ret; - if (!n->sysfs->meta_size) - n->sysfs->meta_size = (int *)NO_SYSFS_ATTR; + if (!n->attrs->meta_size) + n->attrs->meta_size = (int *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->meta_size)) + if (ATTR_IS_ABSENT(n->attrs->meta_size)) return -ENOENT; - *val = *n->sysfs->meta_size; + *val = *n->attrs->meta_size; return 0; } @@ -339,27 +339,27 @@ __shr_public int libnvme_ns_get_csi( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->csi))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->csi))) { str = libnvme_get_ns_attr(n, "csi"); if (!str) { - n->sysfs->csi = (enum nvme_csi *)NO_SYSFS_ATTR; + n->attrs->csi = (enum nvme_csi *)NO_ATTR; } else { - n->sysfs->csi = malloc(sizeof(enum nvme_csi)); - if (!n->sysfs->csi) + n->attrs->csi = malloc(sizeof(enum nvme_csi)); + if (!n->attrs->csi) return -ENOMEM; - if (sscanf(str, "%d", (int *)n->sysfs->csi) != 1) { - free(n->sysfs->csi); - n->sysfs->csi = NULL; + if (sscanf(str, "%d", (int *)n->attrs->csi) != 1) { + free(n->attrs->csi); + n->attrs->csi = NULL; return -EINVAL; } } } - if (SYSFS_IS_ABSENT(n->sysfs->csi)) + if (ATTR_IS_ABSENT(n->attrs->csi)) return -ENOENT; - *val = *n->sysfs->csi; + *val = *n->attrs->csi; return 0; } @@ -384,22 +384,22 @@ __shr_public int libnvme_ns_get_eui64( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->eui64))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->eui64))) { str = libnvme_get_ns_attr(n, "eui"); if (!str) { - n->sysfs->eui64 = (uint8_t *)NO_SYSFS_ATTR; + n->attrs->eui64 = (uint8_t *)NO_ATTR; } else { - n->sysfs->eui64 = malloc(8); - if (!n->sysfs->eui64) + n->attrs->eui64 = malloc(8); + if (!n->attrs->eui64) return -ENOMEM; - memcpy(n->sysfs->eui64, str, 8); + memcpy(n->attrs->eui64, str, 8); } } - if (SYSFS_IS_ABSENT(n->sysfs->eui64)) + if (ATTR_IS_ABSENT(n->attrs->eui64)) return -ENOENT; - *val = n->sysfs->eui64; + *val = n->attrs->eui64; return 0; } @@ -413,26 +413,26 @@ __shr_public int libnvme_ns_get_nguid( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->nguid))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->nguid))) { str = libnvme_get_ns_attr(n, "nguid"); if (!str) { - n->sysfs->nguid = (uint8_t *)NO_SYSFS_ATTR; + n->attrs->nguid = (uint8_t *)NO_ATTR; } else { - n->sysfs->nguid = malloc(16); - if (!n->sysfs->nguid) + n->attrs->nguid = malloc(16); + if (!n->attrs->nguid) return -ENOMEM; - if (libnvme_uuid_from_string(str, n->sysfs->nguid)) { - free(n->sysfs->nguid); - n->sysfs->nguid = NULL; + if (libnvme_uuid_from_string(str, n->attrs->nguid)) { + free(n->attrs->nguid); + n->attrs->nguid = NULL; return -EINVAL; } } } - if (SYSFS_IS_ABSENT(n->sysfs->nguid)) + if (ATTR_IS_ABSENT(n->attrs->nguid)) return -ENOENT; - *val = n->sysfs->nguid; + *val = n->attrs->nguid; return 0; } @@ -446,25 +446,25 @@ __shr_public int libnvme_ns_get_uuid( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->uuid))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->uuid))) { str = libnvme_get_ns_attr(n, "uuid"); if (!str) { - n->sysfs->uuid = (unsigned char *)NO_SYSFS_ATTR; + n->attrs->uuid = (unsigned char *)NO_ATTR; } else { - n->sysfs->uuid = malloc(NVME_UUID_LEN); - if (!n->sysfs->uuid) + n->attrs->uuid = malloc(NVME_UUID_LEN); + if (!n->attrs->uuid) return -ENOMEM; - if (libnvme_uuid_from_string(str, n->sysfs->uuid)) { - free(n->sysfs->uuid); - n->sysfs->uuid = NULL; + if (libnvme_uuid_from_string(str, n->attrs->uuid)) { + free(n->attrs->uuid); + n->attrs->uuid = NULL; return -EINVAL; } } } - if (SYSFS_IS_ABSENT(n->sysfs->uuid)) + if (ATTR_IS_ABSENT(n->attrs->uuid)) return -ENOENT; - *val = n->sysfs->uuid; + *val = n->attrs->uuid; return 0; } diff --git a/libnvme/src/nvme/ns-sysfs-custom-win.c b/libnvme/src/nvme/ns-attrs-custom-win.c similarity index 70% rename from libnvme/src/nvme/ns-sysfs-custom-win.c rename to libnvme/src/nvme/ns-attrs-custom-win.c index c98fdb9f94..6b425f50ec 100644 --- a/libnvme/src/nvme/ns-sysfs-custom-win.c +++ b/libnvme/src/nvme/ns-attrs-custom-win.c @@ -11,13 +11,13 @@ #include "mem.h" -#include "ns-sysfs.c" +#include "generated/ns-attrs.c" /* * Windows has no sysfs: lba_size/lba_count/lba_util/meta_size all come * from one Identify Namespace command, matching what libnvme_ns_init() * used to do eagerly before this conversion. Each field's own - * SYSFS_IS_LOADED() check keeps a caller that only reads one of these + * ATTR_IS_LOADED() check keeps a caller that only reads one of these * four from paying for more than one Identify command in the common * case, but a prior call can leave some fields loaded and others not * (e.g. -ENOMEM after lba_count's malloc but before lba_util's) -- @@ -40,32 +40,32 @@ static int ns_win_load_geometry(struct libnvme_ns *n) nvme_id_ns_flbas_to_lbaf_inuse(id->flbas, &flbas); - if (!SYSFS_IS_LOADED(n->sysfs->lba_size)) { - n->sysfs->lba_size = malloc(sizeof(int)); - if (!n->sysfs->lba_size) + if (!ATTR_IS_LOADED(n->attrs->lba_size)) { + n->attrs->lba_size = malloc(sizeof(int)); + if (!n->attrs->lba_size) return -ENOMEM; - *n->sysfs->lba_size = 1 << id->lbaf[flbas].ds; + *n->attrs->lba_size = 1 << id->lbaf[flbas].ds; } - if (!SYSFS_IS_LOADED(n->sysfs->lba_count)) { - n->sysfs->lba_count = malloc(sizeof(uint64_t)); - if (!n->sysfs->lba_count) + if (!ATTR_IS_LOADED(n->attrs->lba_count)) { + n->attrs->lba_count = malloc(sizeof(uint64_t)); + if (!n->attrs->lba_count) return -ENOMEM; - *n->sysfs->lba_count = le64_to_cpu(id->nsze); + *n->attrs->lba_count = le64_to_cpu(id->nsze); } - if (!SYSFS_IS_LOADED(n->sysfs->lba_util)) { - n->sysfs->lba_util = malloc(sizeof(uint64_t)); - if (!n->sysfs->lba_util) + if (!ATTR_IS_LOADED(n->attrs->lba_util)) { + n->attrs->lba_util = malloc(sizeof(uint64_t)); + if (!n->attrs->lba_util) return -ENOMEM; - *n->sysfs->lba_util = le64_to_cpu(id->nuse); + *n->attrs->lba_util = le64_to_cpu(id->nuse); } - if (!SYSFS_IS_LOADED(n->sysfs->meta_size)) { - n->sysfs->meta_size = malloc(sizeof(int)); - if (!n->sysfs->meta_size) + if (!ATTR_IS_LOADED(n->attrs->meta_size)) { + n->attrs->meta_size = malloc(sizeof(int)); + if (!n->attrs->meta_size) return -ENOMEM; - *n->sysfs->meta_size = le16_to_cpu(id->lbaf[flbas].ms); + *n->attrs->meta_size = le16_to_cpu(id->lbaf[flbas].ms); } return 0; @@ -81,18 +81,18 @@ __shr_public int libnvme_ns_get_lba_size( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->lba_size))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->lba_size))) { ret = ns_win_load_geometry(n); if (ret) return ret; - if (!n->sysfs->lba_size) - n->sysfs->lba_size = (int *)NO_SYSFS_ATTR; + if (!n->attrs->lba_size) + n->attrs->lba_size = (int *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->lba_size)) + if (ATTR_IS_ABSENT(n->attrs->lba_size)) return -ENOENT; - *val = *n->sysfs->lba_size; + *val = *n->attrs->lba_size; return 0; } @@ -132,18 +132,18 @@ __shr_public int libnvme_ns_get_lba_count( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->lba_count))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->lba_count))) { ret = ns_win_load_geometry(n); if (ret) return ret; - if (!n->sysfs->lba_count) - n->sysfs->lba_count = (uint64_t *)NO_SYSFS_ATTR; + if (!n->attrs->lba_count) + n->attrs->lba_count = (uint64_t *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->lba_count)) + if (ATTR_IS_ABSENT(n->attrs->lba_count)) return -ENOENT; - *val = *n->sysfs->lba_count; + *val = *n->attrs->lba_count; return 0; } @@ -157,18 +157,18 @@ __shr_public int libnvme_ns_get_lba_util( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->lba_util))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->lba_util))) { ret = ns_win_load_geometry(n); if (ret) return ret; - if (!n->sysfs->lba_util) - n->sysfs->lba_util = (uint64_t *)NO_SYSFS_ATTR; + if (!n->attrs->lba_util) + n->attrs->lba_util = (uint64_t *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->lba_util)) + if (ATTR_IS_ABSENT(n->attrs->lba_util)) return -ENOENT; - *val = *n->sysfs->lba_util; + *val = *n->attrs->lba_util; return 0; } @@ -182,18 +182,18 @@ __shr_public int libnvme_ns_get_meta_size( *val = dflt; - if (__shr_unlikely(!SYSFS_IS_LOADED(n->sysfs->meta_size))) { + if (__shr_unlikely(!ATTR_IS_LOADED(n->attrs->meta_size))) { ret = ns_win_load_geometry(n); if (ret) return ret; - if (!n->sysfs->meta_size) - n->sysfs->meta_size = (int *)NO_SYSFS_ATTR; + if (!n->attrs->meta_size) + n->attrs->meta_size = (int *)NO_ATTR; } - if (SYSFS_IS_ABSENT(n->sysfs->meta_size)) + if (ATTR_IS_ABSENT(n->attrs->meta_size)) return -ENOENT; - *val = *n->sysfs->meta_size; + *val = *n->attrs->meta_size; return 0; } diff --git a/libnvme/src/nvme/path-sysfs-custom-win.c b/libnvme/src/nvme/path-attrs-custom-linux.c similarity index 74% rename from libnvme/src/nvme/path-sysfs-custom-win.c rename to libnvme/src/nvme/path-attrs-custom-linux.c index 86e2b44613..657c819995 100644 --- a/libnvme/src/nvme/path-sysfs-custom-win.c +++ b/libnvme/src/nvme/path-attrs-custom-linux.c @@ -6,5 +6,5 @@ * Authors: Martin Belanger */ -#include "path-sysfs.c" -#include "path-sysfs-win.c" +#include "generated/path-attrs.c" +#include "generated/path-attrs-linux.c" diff --git a/libnvme/src/nvme/path-sysfs-custom-linux.c b/libnvme/src/nvme/path-attrs-custom-win.c similarity index 74% rename from libnvme/src/nvme/path-sysfs-custom-linux.c rename to libnvme/src/nvme/path-attrs-custom-win.c index 2eb68b79c4..4f7ad530f1 100644 --- a/libnvme/src/nvme/path-sysfs-custom-linux.c +++ b/libnvme/src/nvme/path-attrs-custom-win.c @@ -6,5 +6,5 @@ * Authors: Martin Belanger */ -#include "path-sysfs.c" -#include "path-sysfs-linux.c" +#include "generated/path-attrs.c" +#include "generated/path-attrs-win.c" diff --git a/libnvme/src/nvme/private-tree.h b/libnvme/src/nvme/private-tree.h index 104fa85b87..cb66974415 100644 --- a/libnvme/src/nvme/private-tree.h +++ b/libnvme/src/nvme/private-tree.h @@ -14,20 +14,20 @@ do { free(a); (a) = NULL; } while (0) /* - * NO_SYSFS_ATTR marks a lazy sysfs member as read, but the attribute - * does not exist -- different from NULL, which means the attribute has - * not been read yet. Used both directly (char * members) and boxed - * (a heap-allocated TYPE * for a cached non-string member, e.g. int *) -- + * NO_ATTR marks a lazily-loaded member as read, but the attribute does + * not exist -- different from NULL, which means the attribute has not + * been read yet. Used both directly (char * members) and boxed (a + * heap-allocated TYPE * for a cached non-string member, e.g. int *) -- * the (void *) casts below let the same sentinel serve any pointer type * without an incompatible-pointer-types diagnostic. */ -extern char NO_SYSFS_ATTR[]; +extern char NO_ATTR[]; -#define SYSFS_IS_LOADED(p) ((p) != NULL) -#define SYSFS_IS_ABSENT(p) ((void *)(p) == (void *)NO_SYSFS_ATTR) -#define SYSFS_FREE(p) \ +#define ATTR_IS_LOADED(p) ((p) != NULL) +#define ATTR_IS_ABSENT(p) ((void *)(p) == (void *)NO_ATTR) +#define ATTR_FREE(p) \ do { \ - if ((p) != NULL && !SYSFS_IS_ABSENT(p)) \ + if ((p) != NULL && !ATTR_IS_ABSENT(p)) \ free(p); \ (p) = NULL; \ } while (0) diff --git a/libnvme/src/nvme/private.h b/libnvme/src/nvme/private.h index 75212e4ace..eeedce9849 100644 --- a/libnvme/src/nvme/private.h +++ b/libnvme/src/nvme/private.h @@ -28,12 +28,12 @@ struct libnvme_passthru_completion; struct libnvme_async_req; /* Opaque: each is defined only in its own generated .c file -- see - * generate_sysfs_accessors.py. No other file may see their layout. + * generate_attr_accessors.py. No other file may see their layout. */ -struct libnvme_ctrl_sysfs; -struct libnvme_path_sysfs; -struct libnvme_ns_sysfs; -struct libnvme_subsystem_sysfs; +struct libnvme_ctrl_attrs; +struct libnvme_path_attrs; +struct libnvme_ns_attrs; +struct libnvme_subsystem_attrs; const char *libnvme_subsys_sysfs_dir(struct libnvme_global_ctx *ctx); const char *libnvme_ctrl_sysfs_dir(struct libnvme_global_ctx *ctx); @@ -274,8 +274,8 @@ struct libnvme_path { // !generate-accessors:read=generated,write=none !generat char *name; // !access:write=generated char *sysfs_dir; // !access:write=generated - /* Opaque: field list is PATH_SYSFS in sysfs_accessors_specs.py. */ - struct libnvme_path_sysfs *sysfs; // !access:read=none + /* Opaque: field list is PATH_ATTRS in attr_accessors_specs.py. */ + struct libnvme_path_attrs *attrs; // !access:read=none }; struct libnvme_ns_head { @@ -309,8 +309,8 @@ struct libnvme_ns { // !generate-accessors:read=generated,write=none !generate- char *generic_name; char *sysfs_dir; // !access:write=generated - /* Opaque: field list is NS_SYSFS in sysfs_accessors_specs.py. */ - struct libnvme_ns_sysfs *sysfs; // !access:read=none + /* Opaque: field list is NS_ATTRS in attr_accessors_specs.py. */ + struct libnvme_ns_attrs *attrs; // !access:read=none }; struct libnvme_ctrl { // !generate-accessors:read=generated,write=none !generate-python:alias=Ctrl @@ -339,8 +339,8 @@ struct libnvme_ctrl { // !generate-accessors:read=generated,write=none !generat bool persistent; // !access:write=generated struct libnvme_fabrics_config cfg; // !access:nested:write=none - /* Opaque: field list is CTRL_SYSFS in sysfs_accessors_specs.py. */ - struct libnvme_ctrl_sysfs *sysfs; // !access:read=none + /* Opaque: field list is CTRL_ATTRS in attr_accessors_specs.py. */ + struct libnvme_ctrl_attrs *attrs; // !access:read=none }; struct libnvme_subsystem { // !generate-accessors:read=generated,write=none !generate-python:alias=Subsystem @@ -353,7 +353,9 @@ struct libnvme_subsystem { // !generate-accessors:read=generated,write=none !ge char *sysfs_dir; char *subsysnqn; char *subsystype; - struct libnvme_subsystem_sysfs *sysfs; // !access:read=none + + /* Opaque: field list is SUBSYS_ATTRS in attr_accessors_specs.py. */ + struct libnvme_subsystem_attrs *attrs; // !access:read=none }; struct libnvme_host { // !generate-accessors:read=generated,write=none !generate-python:alias=Host diff --git a/libnvme/src/nvme/tree-fabrics.c b/libnvme/src/nvme/tree-fabrics.c index a2971e8187..7772b01256 100644 --- a/libnvme/src/nvme/tree-fabrics.c +++ b/libnvme/src/nvme/tree-fabrics.c @@ -311,9 +311,9 @@ static ctrl_match_t libnvmf_candidate_init(struct libnvme_global_ctx *ctx, /* * dhchap_host_key/dhchap_ctrl_key/keyring moved to the lazy - * libnvmf_ctrl_load_fabrics_attrs() (ctrl-sysfs-custom-fabrics.c) -- + * libnvmf_ctrl_load_fabrics_attrs() (ctrl-attrs-custom-fabrics.c) -- * this function keeps only the cfg.* fields, which stay eager since cfg - * is out of the lazy-sysfs struct entirely. tls_key's presence is + * is out of the lazy attrs struct entirely. tls_key's presence is * checked again by the lazy loader for keyring -- see the comment * there. */ diff --git a/libnvme/src/nvme/tree-linux.c b/libnvme/src/nvme/tree-linux.c index 61173155d9..5d92830fad 100644 --- a/libnvme/src/nvme/tree-linux.c +++ b/libnvme/src/nvme/tree-linux.c @@ -257,7 +257,7 @@ int libnvme_reconfigure_ctrl(struct libnvme_global_ctx *ctx, FREE_CTRL_ATTR(c->name); FREE_CTRL_ATTR(c->sysfs_dir); FREE_CTRL_ATTR(c->state); - libnvme_ctrl_sysfs_reset(c->sysfs); + libnvme_ctrl_attrs_reset(c->attrs); d = opendir(path); if (!d) { @@ -460,8 +460,8 @@ int libnvme_ns_init(const char *path, struct libnvme_ns *ns) if (ret) return ret; - ns->sysfs = libnvme_ns_sysfs_alloc(); - if (!ns->sysfs) + ns->attrs = libnvme_ns_attrs_alloc(); + if (!ns->attrs) return -ENOMEM; return 0; diff --git a/libnvme/src/nvme/tree-win.c b/libnvme/src/nvme/tree-win.c index 36aec99f90..756bfaf4c7 100644 --- a/libnvme/src/nvme/tree-win.c +++ b/libnvme/src/nvme/tree-win.c @@ -40,7 +40,7 @@ int libnvme_reconfigure_ctrl(__shr_unused struct libnvme_global_ctx *ctx, libnvme_ctrl_release_transport_handle(c); FREE_CTRL_ATTR(c->name); FREE_CTRL_ATTR(c->sysfs_dir); - libnvme_ctrl_sysfs_reset(c->sysfs); + libnvme_ctrl_attrs_reset(c->attrs); c->hdl = NULL; c->name = shr_xstrdup(name); @@ -265,8 +265,8 @@ const char *libnvme_ns_sysfs_dir( int libnvme_ns_init(__shr_unused const char *path, struct libnvme_ns *ns) { - ns->sysfs = libnvme_ns_sysfs_alloc(); - if (!ns->sysfs) + ns->attrs = libnvme_ns_attrs_alloc(); + if (!ns->attrs) return -ENOMEM; return 0; diff --git a/libnvme/src/nvme/tree.c b/libnvme/src/nvme/tree.c index 7f111130e0..21cb6359c5 100644 --- a/libnvme/src/nvme/tree.c +++ b/libnvme/src/nvme/tree.c @@ -42,7 +42,7 @@ static int libnvme_ctrl_scan_namespace(struct libnvme_global_ctx *ctx, static int libnvme_ctrl_scan_path(struct libnvme_global_ctx *ctx, struct libnvme_ctrl *c, char *name); -char NO_SYSFS_ATTR[] = ""; +char NO_ATTR[] = ""; char *libnvme_hostid_from_hostnqn(const char *hostnqn) { @@ -272,7 +272,7 @@ static void __nvme_free_ns(struct libnvme_ns *n) free(n->generic_name); free(n->name); free(n->sysfs_dir); - libnvme_ns_sysfs_free(n->sysfs); + libnvme_ns_attrs_free(n->attrs); libnvme_namespace_for_each_path_safe(n, p, _p) { list_del_init(&p->nentry); p->n = NULL; @@ -308,7 +308,7 @@ static void __nvme_free_subsystem(struct libnvme_subsystem *s) free(s->sysfs_dir); free(s->subsysnqn); free(s->subsystype); - libnvme_subsystem_sysfs_free(s->sysfs); + libnvme_subsystem_attrs_free(s->attrs); free(s); } @@ -352,8 +352,8 @@ int libnvme_create_subsystem(struct libnvme_host *h, return -ENOMEM; } - s->sysfs = libnvme_subsystem_sysfs_alloc(); - if (!s->sysfs) { + s->attrs = libnvme_subsystem_attrs_alloc(); + if (!s->attrs) { free(s->subsysnqn); free(s); return -ENOMEM; @@ -1060,7 +1060,7 @@ void nvme_free_path(struct libnvme_path *p) list_del_init(&p->nentry); free(p->name); free(p->sysfs_dir); - libnvme_path_sysfs_free(p->sysfs); + libnvme_path_attrs_free(p->attrs); free(p); } @@ -1084,8 +1084,8 @@ static int libnvme_ctrl_scan_path(struct libnvme_global_ctx *ctx, if (!p) return -ENOMEM; - p->sysfs = libnvme_path_sysfs_alloc(); - if (!p->sysfs) { + p->attrs = libnvme_path_attrs_alloc(); + if (!p->attrs) { free(p); return -ENOMEM; } @@ -1208,7 +1208,7 @@ void nvme_deconfigure_ctrl(libnvme_ctrl_t c) FREE_CTRL_ATTR(c->tls_key_identity); FREE_CTRL_ATTR(c->tls_key); FREE_CTRL_ATTR(c->address); - libnvme_ctrl_sysfs_reset(c->sysfs); + libnvme_ctrl_attrs_reset(c->attrs); } __shr_public void libnvme_unlink_ctrl(libnvme_ctrl_t c) @@ -1238,7 +1238,7 @@ static void __libnvme_free_ctrl(libnvme_ctrl_t c) FREE_CTRL_ATTR(c->host_traddr); FREE_CTRL_ATTR(c->host_iface); FREE_CTRL_ATTR(c->trsvcid); - libnvme_ctrl_sysfs_free(c->sysfs); + libnvme_ctrl_attrs_free(c->attrs); free(c); } @@ -1274,8 +1274,8 @@ int libnvme_create_ctrl(struct libnvme_global_ctx *ctx, if (!c) return -ENOMEM; - c->sysfs = libnvme_ctrl_sysfs_alloc(); - if (!c->sysfs) { + c->attrs = libnvme_ctrl_attrs_alloc(); + if (!c->attrs) { free(c); return -ENOMEM; } diff --git a/libnvme/src/path-sysfs.ld b/libnvme/src/path-attrs.ld similarity index 97% rename from libnvme/src/path-sysfs.ld rename to libnvme/src/path-attrs.ld index bb84d92f7c..802d54a035 100644 --- a/libnvme/src/path-sysfs.ld +++ b/libnvme/src/path-attrs.ld @@ -15,7 +15,7 @@ * Or: make update-accessors */ -LIBNVME_PATH_SYSFS_3 { +LIBNVME_PATH_ATTRS_3 { global: libnvme_path_get_ana_state; libnvme_path_get_numa_nodes; diff --git a/libnvme/src/subsys-sysfs.ld b/libnvme/src/subsys-attrs.ld similarity index 97% rename from libnvme/src/subsys-sysfs.ld rename to libnvme/src/subsys-attrs.ld index ac8ea8fb1c..25b871cd27 100644 --- a/libnvme/src/subsys-sysfs.ld +++ b/libnvme/src/subsys-attrs.ld @@ -15,7 +15,7 @@ * Or: make update-accessors */ -LIBNVME_SUBSYS_SYSFS_3 { +LIBNVME_SUBSYS_ATTRS_3 { global: libnvme_subsystem_get_model; libnvme_subsystem_set_model; diff --git a/libnvme/test/meson.build b/libnvme/test/meson.build index 17efcec937..d77c96aa66 100644 --- a/libnvme/test/meson.build +++ b/libnvme/test/meson.build @@ -15,12 +15,12 @@ if python3_prog.found() meson.project_source_root() / 'libnvme', ], ) - _ld_args = ['--ld', nvme_ld, '--ld', accessors_ld, '--ld', ctrl_sysfs_ld] + _ld_args = ['--ld', nvme_ld, '--ld', accessors_ld, '--ld', ctrl_attrs_ld] if want_fabrics _ld_args += ['--ld', nvmf_ld, '--ld', nvmf_accessors_ld] endif _hdr_args = [] - foreach hdr : headers + foreach hdr : headers + generated_headers _hdr_args += ['--header', meson.project_source_root() / 'libnvme' / 'src' / hdr] endforeach test( diff --git a/libnvme/tools/check-public-symbols.py b/libnvme/tools/check-public-symbols.py index 24e02ea69b..0083dcfcc9 100644 --- a/libnvme/tools/check-public-symbols.py +++ b/libnvme/tools/check-public-symbols.py @@ -40,10 +40,10 @@ ROOT / 'src' / 'libnvme-mi.ld', ROOT / 'src' / 'accessors.ld', ROOT / 'src' / 'accessors-fabrics.ld', - ROOT / 'src' / 'ctrl-sysfs.ld', - ROOT / 'src' / 'path-sysfs.ld', - ROOT / 'src' / 'ns-sysfs.ld', - ROOT / 'src' / 'subsys-sysfs.ld', + ROOT / 'src' / 'ctrl-attrs.ld', + ROOT / 'src' / 'path-attrs.ld', + ROOT / 'src' / 'ns-attrs.ld', + ROOT / 'src' / 'subsys-attrs.ld', ] # --------------------------------------------------------------------------- @@ -69,7 +69,7 @@ pub_syms = {} # symbol -> Path of the .c file that defines it -for c_path in sorted(SRC_DIR.glob('*.c')): +for c_path in sorted(SRC_DIR.rglob('*.c')): for m in PUB_RE.finditer(c_path.read_text(encoding='utf-8')): sym = m.group(1) pub_syms[sym] = c_path diff --git a/libnvme/tools/generator/generate_accessors.py b/libnvme/tools/generator/generate_accessors.py index 244ca20c67..9bf3ace9b5 100755 --- a/libnvme/tools/generator/generate_accessors.py +++ b/libnvme/tools/generator/generate_accessors.py @@ -351,35 +351,35 @@ class Member: py_alias: alternate Python attribute name from ``// !python:alias=NAME``, or None to use the C member name. - is_sysfs_lazy: True when this member's getter/setter use the - sentinel-cache shape instead of the plain generated - shape. Set directly by dict-driven generators (e.g. - generate_sysfs_accessors.py) — this generator's own - header-annotation parser never sets it. - sysfs_attr: sysfs attribute name to read on cache miss, or None. - sysfs_loader: loader function name that fills this member (and - possibly others in its group) on cache miss, or None. - Mutually meaningful only when sysfs_attr is None. - is_volatile: True when the member is always re-read from sysfs on - every call, never cached. - attr_reader: the C function name used to read a plain sysfs_attr + is_attr_lazy: True when this member's getter/setter use the + sentinel-cache shape instead of the plain generated + shape. Set directly by dict-driven generators (e.g. + generate_attr_accessors.py) — this generator's own + header-annotation parser never sets it. + attr_name: attribute name to read on cache miss, or None. + attr_loader: loader function name that fills this member (and + possibly others in its group) on cache miss, or None. + Mutually meaningful only when attr_name is None. + is_volatile: True when the member is always re-read on every call, + never cached. + attr_reader: the C function name used to read a plain attr_name (e.g. libnvme_get_ctrl_attr, libnvme_get_path_attr). - Meaningful only alongside sysfs_attr. + Meaningful only alongside attr_name. is_absent: True when this platform has no source for the member at - all -- the getter always returns -ENOENT, no sysfs_attr - or sysfs_loader call ever happens. + all -- the getter always returns -ENOENT, no attr_name + or attr_loader call ever happens. """ __slots__ = ('name', 'type', 'read_mode', 'write_mode', 'is_char_array', 'is_char_ptr_array', 'is_scalar_array', 'array_size', 'py_visible', 'py_alias', 'field_path', - 'is_sysfs_lazy', 'sysfs_attr', 'sysfs_loader', 'is_volatile', + 'is_attr_lazy', 'attr_name', 'attr_loader', 'is_volatile', 'attr_reader', 'is_absent') def __init__(self, name, type_str, read_mode, write_mode, is_char_array, is_char_ptr_array, is_scalar_array, array_size, py_visible=True, py_alias=None, field_path=None, - is_sysfs_lazy=False, sysfs_attr=None, sysfs_loader=None, + is_attr_lazy=False, attr_name=None, attr_loader=None, is_volatile=False, attr_reader=None, is_absent=False): self.name = name self.type = type_str # e.g. "const char *", "int", "__u32" @@ -392,9 +392,9 @@ def __init__(self, name, type_str, read_mode, write_mode, self.py_visible = py_visible # False → excluded from SWIG fragment self.py_alias = py_alias # str → rename Python attribute; None → use C name self.field_path = field_path if field_path is not None else name - self.is_sysfs_lazy = is_sysfs_lazy - self.sysfs_attr = sysfs_attr - self.sysfs_loader = sysfs_loader + self.is_attr_lazy = is_attr_lazy + self.attr_name = attr_name + self.attr_loader = attr_loader self.is_volatile = is_volatile self.attr_reader = attr_reader self.is_absent = is_absent @@ -1326,9 +1326,9 @@ def emit_hdr_getter(f, prefix, sname, type_name, mname, mtype, is_dyn_str): def emit_hdr_getter_lazy(f, prefix, sname, type_name, mname, mtype): - """Emit a header declaration for a lazy sysfs getter. + """Emit a header declaration for a lazy attribute getter. - Unlike a plain getter, a sysfs read (or the loader behind it) can + Unlike a plain getter, an attribute read (or the loader behind it) can fail, and a bare return value has no room to say so -- lazy getters return int and deliver the value through an out-param instead. A third argument, dflt, is what gets stored in that out-param when the @@ -1446,13 +1446,13 @@ def generate_hdr(f, prefix, sname, type_name, members): emit_hdr_setter_val(f, prefix, sname, type_name, member.name, member.type) if member.read_mode == 'generated': - if member.is_sysfs_lazy: + if member.is_attr_lazy: emit_hdr_getter_lazy(f, prefix, sname, type_name, member.name, member.type) else: emit_hdr_getter(f, prefix, sname, type_name, member.name, member.type, is_dyn_str) - elif member.read_mode == 'custom' and member.is_sysfs_lazy: + elif member.read_mode == 'custom' and member.is_attr_lazy: # The struct is opaque, so even a hand-written getter's # prototype must come from this generator -- no other file # may declare a function that reaches inside the struct. The @@ -1469,7 +1469,7 @@ def generate_hdr(f, prefix, sname, type_name, members): # scanf format for each numeric lazy-getter type this generator has ever # needed. Deliberately not a general type->format mapper -- add an entry -# only when a real member needs it (mirrors generate_sysfs_accessors.py's +# only when a real member needs it (mirrors generate_attr_accessors.py's # own restraint on its _PY_FROM dict). _SCANF_FMT = { 'long': '%ld', @@ -1639,14 +1639,14 @@ def emit_src_getter_scalar_array(f, prefix, sname, type_name, mname, elem_type, def emit_src_setter_lazy_dynstr(f, prefix, sname, type_name, mname, field_path): - """Emit a dynamic-string setter for a lazy sysfs member. + """Emit a dynamic-string setter for a lazy attribute member. - Frees the old value with SYSFS_FREE() instead of free(): the cached - value may be the NO_SYSFS_ATTR sentinel, and free()ing that address + Frees the old value with ATTR_FREE() instead of free(): the cached + value may be the NO_ATTR sentinel, and free()ing that address would crash. An explicit NULL argument stores the sentinel, not NULL -- otherwise setting NULL (e.g. clearing a key) would look identical to "never read," and the next getter call would silently re-fetch - from sysfs and undo the clear. + it and undo the clear. """ sig = (f'{PUB}void {_set_name(prefix, sname, mname)}' f'(struct {type_name} *p, const char *{mname})') @@ -1659,26 +1659,26 @@ def emit_src_setter_lazy_dynstr(f, prefix, sname, type_name, mname, field_path): f'\t\tconst char *{mname})\n' ) - f.write(f'{{\n\tSYSFS_FREE(p->{field_path});\n') - body = f'\tp->{field_path} = {mname} ? strdup({mname}) : NO_SYSFS_ATTR;' + f.write(f'{{\n\tATTR_FREE(p->{field_path});\n') + body = f'\tp->{field_path} = {mname} ? strdup({mname}) : NO_ATTR;' if fits_80_ntabs(1, body): f.write(body + '\n') else: f.write( f'\tp->{field_path} =\n' - f'\t\t{mname} ? strdup({mname}) : NO_SYSFS_ATTR;\n' + f'\t\t{mname} ? strdup({mname}) : NO_ATTR;\n' ) f.write('}\n\n') def emit_src_getter_lazy_attr(f, prefix, sname, type_name, mname, field_path, - sysfs_attr, attr_reader): - """Emit a lazy getter that caches one plain sysfs attribute. + attr_name, attr_reader): + """Emit a lazy getter that caches one plain attribute. First call reads the attribute and caches the result: a real pointer - if the attribute exists, or the NO_SYSFS_ATTR sentinel if it does not + if the attribute exists, or the NO_ATTR sentinel if it does not (a raw NULL there would look "not yet read" and re-fire every call). - Every later call returns the cached value without touching sysfs + Every later call returns the cached value without reading it again. Returns -ENOENT when the attribute does not exist, so the caller can tell "absent" from "not yet checked". *val is set to dflt unconditionally before anything else, so a failure path never leaves @@ -1695,23 +1695,23 @@ def emit_src_getter_lazy_attr(f, prefix, sname, type_name, mname, field_path, '{\n' f'\tstruct {type_name} *c = (struct {type_name} *)p;\n\n' '\t*val = dflt;\n\n' - f'\tif (__shr_unlikely(!SYSFS_IS_LOADED(c->{field_path}))) {{\n' + f'\tif (__shr_unlikely(!ATTR_IS_LOADED(c->{field_path}))) {{\n' ) - load = f'\t\tc->{field_path} = {attr_reader}(c, "{sysfs_attr}");' + load = f'\t\tc->{field_path} = {attr_reader}(c, "{attr_name}");' if fits_80_ntabs(2, load.lstrip()): f.write(load + '\n') else: f.write( f'\t\tc->{field_path} =\n' - f'\t\t\t{attr_reader}(c, "{sysfs_attr}");\n' + f'\t\t\t{attr_reader}(c, "{attr_name}");\n' ) f.write( f'\t\tif (!c->{field_path})\n' - f'\t\t\tc->{field_path} = NO_SYSFS_ATTR;\n' + f'\t\t\tc->{field_path} = NO_ATTR;\n' '\t}\n\n' ) f.write( - f'\tif (SYSFS_IS_ABSENT(c->{field_path}))\n' + f'\tif (ATTR_IS_ABSENT(c->{field_path}))\n' f'\t\treturn -ENOENT;\n\n' f'\t*val = c->{field_path};\n' f'\treturn 0;\n' @@ -1720,13 +1720,13 @@ def emit_src_getter_lazy_attr(f, prefix, sname, type_name, mname, field_path, def emit_src_getter_lazy_attr_num(f, prefix, sname, type_name, mname, mtype, - field_path, sysfs_attr, attr_reader): - """Emit a lazy getter that caches one plain sysfs attribute, boxed. + field_path, attr_name, attr_reader): + """Emit a lazy getter that caches one plain attribute, boxed. Same cache-once shape as emit_src_getter_lazy_attr(), but the cached field is a heap-allocated TYPE * rather than a plain value: mtype has no spare value to serve as "not loaded" (0 is a legitimate reading), - so the field reuses the string members' NULL/NO_SYSFS_ATTR/real-value + so the field reuses the string members' NULL/NO_ATTR/real-value tri-state instead of inventing a second mechanism. *val is set to dflt unconditionally before anything else -- see emit_src_getter_lazy_attr()'s docstring. @@ -1741,11 +1741,11 @@ def emit_src_getter_lazy_attr_num(f, prefix, sname, type_name, mname, mtype, '{\n' f'\tstruct {type_name} *c = (struct {type_name} *)p;\n\n' '\t*val = dflt;\n\n' - f'\tif (__shr_unlikely(!SYSFS_IS_LOADED(c->{field_path}))) {{\n' + f'\tif (__shr_unlikely(!ATTR_IS_LOADED(c->{field_path}))) {{\n' '\t\t__cleanup_free char *str = NULL;\n\n' - f'\t\tstr = {attr_reader}(c, "{sysfs_attr}");\n' + f'\t\tstr = {attr_reader}(c, "{attr_name}");\n' f'\t\tif (!str)\n' - f'\t\t\tc->{field_path} = ({mtype} *)NO_SYSFS_ATTR;\n' + f'\t\t\tc->{field_path} = ({mtype} *)NO_ATTR;\n' '\t\telse {\n' f'\t\t\tc->{field_path} = malloc(sizeof({mtype}));\n' f'\t\t\tif (!c->{field_path})\n' @@ -1761,7 +1761,7 @@ def emit_src_getter_lazy_attr_num(f, prefix, sname, type_name, mname, mtype, '\t\t\t}\n' '\t\t}\n' '\t}\n\n' - f'\tif (SYSFS_IS_ABSENT(c->{field_path}))\n' + f'\tif (ATTR_IS_ABSENT(c->{field_path}))\n' f'\t\treturn -ENOENT;\n\n' f'\t*val = *c->{field_path};\n' f'\treturn 0;\n' @@ -1770,14 +1770,14 @@ def emit_src_getter_lazy_attr_num(f, prefix, sname, type_name, mname, mtype, def emit_src_getter_lazy_loader(f, prefix, sname, type_name, mname, - field_path, sysfs_loader): + field_path, attr_loader): """Emit a lazy getter backed by a loader-function call. The loader may populate several members of the same group in one call (e.g. dhchap_host_key/dhchap_ctrl_key/keyring from one sysfs read pass), writing NULL to any it leaves absent. After it returns, a member still at NULL means no value exists for it -- stamp the - NO_SYSFS_ATTR sentinel so the guard doesn't re-fire the loader on + NO_ATTR sentinel so the guard doesn't re-fire the loader on every subsequent call. A negative loader return means the load itself failed (not just "attribute absent") and is propagated to the caller unchanged. *val is set to dflt unconditionally before @@ -1794,16 +1794,16 @@ def emit_src_getter_lazy_loader(f, prefix, sname, type_name, mname, f'\tstruct {type_name} *c = (struct {type_name} *)p;\n' '\tint ret;\n\n' '\t*val = dflt;\n\n' - f'\tif (__shr_unlikely(!SYSFS_IS_LOADED(c->{field_path}))) {{\n' - f'\t\tret = {sysfs_loader}(c);\n' + f'\tif (__shr_unlikely(!ATTR_IS_LOADED(c->{field_path}))) {{\n' + f'\t\tret = {attr_loader}(c);\n' '\t\tif (ret)\n' '\t\t\treturn ret;\n' f'\t\tif (!c->{field_path})\n' - f'\t\t\tc->{field_path} = NO_SYSFS_ATTR;\n' + f'\t\t\tc->{field_path} = NO_ATTR;\n' '\t}\n\n' ) f.write( - f'\tif (SYSFS_IS_ABSENT(c->{field_path}))\n' + f'\tif (ATTR_IS_ABSENT(c->{field_path}))\n' f'\t\treturn -ENOENT;\n\n' f'\t*val = c->{field_path};\n' f'\treturn 0;\n' @@ -1812,10 +1812,10 @@ def emit_src_getter_lazy_loader(f, prefix, sname, type_name, mname, def emit_src_getter_volatile_num(f, prefix, sname, type_name, mname, mtype, - field_path, sysfs_attr, attr_reader): + field_path, attr_name, attr_reader): """Emit an always-live numeric getter for a volatile lazy member. - No sentinel, no cache: every call re-reads the sysfs attribute and + No sentinel, no cache: every call re-reads the attribute and parses it into the member. Returns -ENOENT when the attribute cannot be read and -EINVAL when it can be read but not parsed, rather than the previous value -- the caller can tell a real absence, or bad @@ -1834,7 +1834,7 @@ def emit_src_getter_volatile_num(f, prefix, sname, type_name, mname, mtype, f'\tstruct {type_name} *c = (struct {type_name} *)p;\n' '\t__cleanup_free char *str = NULL;\n\n' '\t*val = dflt;\n\n' - f'\tstr = {attr_reader}(c, "{sysfs_attr}");\n' + f'\tstr = {attr_reader}(c, "{attr_name}");\n' '\tif (!str)\n' '\t\treturn -ENOENT;\n\n' f'\tif (sscanf(str, "{_SCANF_FMT[mtype]}", &c->{field_path}) != 1)\n' @@ -1846,7 +1846,7 @@ def emit_src_getter_volatile_num(f, prefix, sname, type_name, mname, mtype, def emit_src_getter_volatile_str(f, prefix, sname, type_name, mname, - field_path, sysfs_attr, attr_reader): + field_path, attr_name, attr_reader): """Emit an always-live string getter for a volatile lazy member. Re-reads the attribute on every call like emit_src_getter_volatile_num(), @@ -1870,7 +1870,7 @@ def emit_src_getter_volatile_str(f, prefix, sname, type_name, mname, f'\tstruct {type_name} *c = (struct {type_name} *)p;\n' '\t__cleanup_free char *str = NULL;\n\n' '\t*val = dflt;\n\n' - f'\tstr = {attr_reader}(c, "{sysfs_attr}");\n' + f'\tstr = {attr_reader}(c, "{attr_name}");\n' '\tif (!str)\n' '\t\treturn -ENOENT;\n\n' f'\tif (!c->{field_path} || strcmp(str, c->{field_path})) {{\n' @@ -1922,7 +1922,7 @@ def generate_src(f, prefix, sname, type_name, members): member.name, member.type, fp) continue - if member.is_sysfs_lazy: + if member.is_attr_lazy: if member.write_mode == 'generated': emit_src_setter_lazy_dynstr(f, prefix, sname, type_name, member.name, fp) @@ -1935,25 +1935,25 @@ def generate_src(f, prefix, sname, type_name, members): if is_str: emit_src_getter_volatile_str( f, prefix, sname, type_name, member.name, fp, - member.sysfs_attr, member.attr_reader) + member.attr_name, member.attr_reader) else: emit_src_getter_volatile_num( f, prefix, sname, type_name, member.name, - member.type, fp, member.sysfs_attr, + member.type, fp, member.attr_name, member.attr_reader) - elif member.sysfs_loader: + elif member.attr_loader: emit_src_getter_lazy_loader(f, prefix, sname, type_name, member.name, fp, - member.sysfs_loader) + member.attr_loader) elif is_str: emit_src_getter_lazy_attr(f, prefix, sname, type_name, member.name, fp, - member.sysfs_attr, + member.attr_name, member.attr_reader) else: emit_src_getter_lazy_attr_num( f, prefix, sname, type_name, member.name, - member.type, fp, member.sysfs_attr, + member.type, fp, member.attr_name, member.attr_reader) continue @@ -2168,7 +2168,7 @@ def generate_ld(f, prefix, sname, members, lc_members, default_members): if default_members: f.write(f'\t\t{_init_defaults_name(prefix, sname)};\n') for member in members: - custom_lazy = member.read_mode == 'custom' and member.is_sysfs_lazy + custom_lazy = member.read_mode == 'custom' and member.is_attr_lazy if member.read_mode == 'generated' or custom_lazy: f.write(f'\t\t{_get_name(prefix, sname, member.name)};\n') if member.write_mode == 'generated': diff --git a/libnvme/tools/generator/generate_sysfs_accessors.py b/libnvme/tools/generator/generate_attr_accessors.py old mode 100644 new mode 100755 similarity index 88% rename from libnvme/tools/generator/generate_sysfs_accessors.py rename to libnvme/tools/generator/generate_attr_accessors.py index 47a368a0a8..4964a6a761 --- a/libnvme/tools/generator/generate_sysfs_accessors.py +++ b/libnvme/tools/generator/generate_attr_accessors.py @@ -1,20 +1,24 @@ #!/usr/bin/env python3 # SPDX-License-Identifier: LGPL-2.1-or-later """ -generate_sysfs_accessors.py — Generate an opaque, sysfs-backed struct and its -accessors from a Python dict, instead of parsing an annotated header. +generate_attr_accessors.py — Generate an opaque, lazily-loaded struct and +its accessors from a Python dict, instead of parsing an annotated header. -Generates every struct spec dict in the SYSFS_SPECS list of the module -passed via --specs (e.g. sysfs_accessors_specs.py), in one run -- no +Generates every struct spec dict in the ATTR_SPECS list of the module +passed via --specs (e.g. attr_accessors_specs.py), in one run -- no per-struct invocation, no per-struct command-line selection. -See ../../design/tooling/generate_sysfs_accessors.md for the full design +See ../../design/tooling/generate_attr_accessors.md for the full design rationale (why this is a separate generator from generate_accessors.py, -the CTRL_SYSFS schema, and how to add a new member). +the CTRL_ATTRS schema, and how to add a new member). + +Generated .c/.h files are written to a 'generated' subdirectory of +--out-dir, keeping them visually separate from the hand-written +*-attrs-custom-*.c files that #include them -- see that same design doc. Example usage: - ./generate_sysfs_accessors.py --out-dir ../../src/nvme \ - --specs ../../src/nvme/sysfs_accessors_specs.py + ./generate_attr_accessors.py --out-dir ../../src/nvme \ + --specs ../../src/nvme/attr_accessors_specs.py """ import argparse @@ -40,12 +44,12 @@ def load_specs(path): - """Import the module at path and return its SYSFS_SPECS list.""" - spec = importlib.util.spec_from_file_location('sysfs_accessors_specs', + """Import the module at path and return its ATTR_SPECS list.""" + spec = importlib.util.spec_from_file_location('attr_accessors_specs', path) module = importlib.util.module_from_spec(spec) spec.loader.exec_module(module) - return module.SYSFS_SPECS + return module.ATTR_SPECS # --------------------------------------------------------------------------- @@ -120,8 +124,8 @@ def _make_member(spec, resolved, is_absent=False): is_scalar_array=False, array_size=None, field_path=field_path, - is_sysfs_lazy=True, - sysfs_attr=resolved.get('attr'), + is_attr_lazy=True, + attr_name=resolved.get('attr'), is_volatile=resolved.get('volatile', False), attr_reader=spec['attr_reader'], is_absent=is_absent, @@ -145,7 +149,7 @@ def build_members(spec): resolution differs, for the spec's Linux-only .c file. 'win' -- likewise, for the Windows-only .c file. - field_path uses '->' throughout (e.g. 'sysfs->model'): the owner + field_path uses '->' throughout (e.g. 'attrs->model'): the owner struct holds a pointer to this struct, not an embedded value. Groups are not yet OS-resolved (spec['groups'] is a single, @@ -186,8 +190,8 @@ def build_members(spec): is_scalar_array=False, array_size=None, field_path=field_path, - is_sysfs_lazy=True, - sysfs_loader=g['loader'], + is_attr_lazy=True, + attr_loader=g['loader'], ) all_members.append(member) shared_members.append(member) @@ -280,9 +284,9 @@ def emit_struct_def(f, spec): f.write(f"\t{m['type']} {m['name']};\n") else: # Cached numeric: boxed as TYPE * so the field can carry the - # same NULL/NO_SYSFS_ATTR/real-value tri-state a string - # member already uses -- the type itself has no spare value - # to mean "not loaded" (0 is a legitimate reading). + # same NULL/NO_ATTR/real-value tri-state a string member + # already uses -- the type itself has no spare value to + # mean "not loaded" (0 is a legitimate reading). f.write(f"\t{m['type']} *{m['name']};\n") for g in spec['groups']: for name in g['members']: @@ -311,7 +315,7 @@ def emit_alloc_free(f, spec): ) for path in reconfigure_reset_field_paths(spec): name = path.split('->', 1)[1] - f.write(f'\tSYSFS_FREE({owner_field}->{name});\n') + f.write(f'\tATTR_FREE({owner_field}->{name});\n') f.write('}\n\n') f.write( @@ -323,7 +327,7 @@ def emit_alloc_free(f, spec): ) for path in final_free_field_paths(spec): name = path.split('->', 1)[1] - f.write(f'\tSYSFS_FREE({owner_field}->{name});\n') + f.write(f'\tATTR_FREE({owner_field}->{name});\n') f.write(f'\tfree({owner_field});\n') f.write('}\n\n') @@ -365,8 +369,8 @@ def generate_header(spec, members): '/* Internal: loader callbacks, one per group above. Each\n' ' * fills every member of its group in a single call,\n' ' * returning 0 on success or a negative errno. Defined in\n' - ' * whichever hand-written *-custom-*.c matches the build\n' - ' * (see that file\'s own #ifdef/#include selection).\n' + ' * whichever hand-written *-attrs-custom-*.c matches the\n' + ' * build (see that file\'s own #ifdef/#include selection).\n' ' */\n' ) for fn in loaders: @@ -416,9 +420,9 @@ def generate_source_os(spec, os_members): No includes, no struct definition, no alloc/reset/free -- this file is never compiled on its own. It relies on being #include'd *after* - the shared .c in the hand-written ctrl-sysfs-custom-.c (or + the shared .c in the hand-written ctrl-attrs-custom-.c (or equivalent), which brings the struct definition and everything else - into scope first -- see generate_sysfs_accessors.md's "generated + into scope first -- see generate_attr_accessors.md's "generated file layout" section for the full #include chain. """ owner_type = spec['owner_type'] @@ -499,10 +503,10 @@ def emit_swig_getter_wrapper(owner_type, m): def generate_swig(spec, members): """SWIG fragment: extend the already-wrapped struct libnvme_ctrl - (declared in accessors.i) with these sysfs-backed properties. + (declared in accessors.i) with these lazily-loaded properties. Every member here goes through %extend, unconditionally -- SWIG's - generated glue can no more reach a field behind the opaque sysfs + generated glue can no more reach a field behind the opaque attrs pointer than any other C caller can, the same reason a hand-written 'custom' accessor in generate_accessors.py's own SWIG emitter needs %extend instead of a plain struct field. This is a bespoke, minimal @@ -539,7 +543,7 @@ def _py_representable(m): buf = io.StringIO() buf.write(f'{SPDX_C}\n\n{BANNER}\n\n') - buf.write(f'/* struct {owner_type} -- sysfs-backed properties */\n') + buf.write(f'/* struct {owner_type} -- lazily-loaded properties */\n') for m in writable: buf.write( @@ -609,13 +613,14 @@ def main(): parser.add_argument( '--specs', required=True, - help='Path to the Python module providing SYSFS_SPECS, a list of ' - 'struct spec dicts (e.g. sysfs_accessors_specs.py)', + help='Path to the Python module providing ATTR_SPECS, a list of ' + 'struct spec dicts (e.g. attr_accessors_specs.py)', ) parser.add_argument( '--out-dir', required=True, - help='Directory to write generated .c/.h files into', + help="Directory whose 'generated' subdirectory receives the " + 'generated .c/.h files', ) parser.add_argument( '--ld-out-dir', @@ -633,6 +638,11 @@ def main(): help='Read-only: exit non-zero if output is stale', ) args = parser.parse_args() + # .c/.h are the only fully generator-owned outputs (never hand- + # touched, unlike the hand-maintained .ld or the *-custom-*.c files + # that #include them) -- kept in their own subdirectory so they + # don't clutter src/nvme/ alongside hand-written files. + generated_dir = os.path.join(args.out_dir, 'generated') ld_out_dir = args.ld_out_dir or args.out_dir swig_out_dir = args.swig_out_dir or args.out_dir @@ -640,20 +650,23 @@ def main(): for spec in load_specs(args.specs): resolved = build_members(spec) outputs[spec['source']] = ( - args.out_dir, generate_source_shared(spec, resolved['shared'])) + generated_dir, generate_source_shared(spec, resolved['shared'])) if resolved['linux']: outputs[spec['source_linux']] = ( - args.out_dir, generate_source_os(spec, resolved['linux'])) + generated_dir, generate_source_os(spec, resolved['linux'])) if resolved['win']: outputs[spec['source_win']] = ( - args.out_dir, generate_source_os(spec, resolved['win'])) + generated_dir, generate_source_os(spec, resolved['win'])) outputs[spec['header']] = ( - args.out_dir, generate_header(spec, resolved['all'])) + generated_dir, generate_header(spec, resolved['all'])) outputs[spec['ld']] = ( ld_out_dir, generate_ld(spec, resolved['all'])) outputs[spec['swig']] = ( swig_out_dir, generate_swig(spec, resolved['all'])) + if not args.check: + os.makedirs(generated_dir, exist_ok=True) + stale = [] for name, (out_dir, content) in outputs.items(): path = os.path.join(out_dir, name) @@ -672,13 +685,13 @@ def main(): if stale: print('stale: ' + ', '.join(stale), file=sys.stderr) return 1 - print('all sysfs-accessor generated files up to date.') + print('all attr-accessor generated files up to date.') return 0 if stale: print('updated: ' + ', '.join(stale)) else: - print('all sysfs-accessor generated files unchanged.') + print('all attr-accessor generated files unchanged.') return 0 diff --git a/libnvme/tools/generator/meson.build b/libnvme/tools/generator/meson.build index a349f064af..0a869847fd 100644 --- a/libnvme/tools/generator/meson.build +++ b/libnvme/tools/generator/meson.build @@ -68,13 +68,13 @@ _tgt_fabrics = run_target( ], ) -_tgt_sysfs = run_target( - 'update-sysfs-accessors', +_tgt_attrs = run_target( + 'update-attr-accessors', command: [ - 'update-sysfs-accessors.sh', + 'update-attr-accessors.sh', _py3, - files('generate_sysfs_accessors.py'), - libnvme_src_nvme / 'sysfs_accessors_specs.py', + files('generate_attr_accessors.py'), + libnvme_src_nvme / 'attr_accessors_specs.py', libnvme_src_nvme, libnvme_src, libnvme_swig_dir, @@ -82,4 +82,4 @@ _tgt_sysfs = run_target( ) # This alias allows generating/checking all accessors in one shot. -alias_target('update-accessors', _tgt_common, _tgt_fabrics, _tgt_sysfs) +alias_target('update-accessors', _tgt_common, _tgt_fabrics, _tgt_attrs) diff --git a/libnvme/tools/generator/update-sysfs-accessors.sh b/libnvme/tools/generator/update-attr-accessors.sh similarity index 85% rename from libnvme/tools/generator/update-sysfs-accessors.sh rename to libnvme/tools/generator/update-attr-accessors.sh index 5c227df60d..d4c332fa28 100755 --- a/libnvme/tools/generator/update-sysfs-accessors.sh +++ b/libnvme/tools/generator/update-attr-accessors.sh @@ -1,8 +1,8 @@ #!/usr/bin/env bash # SPDX-License-Identifier: LGPL-2.1-or-later # -# update-sysfs-accessors.sh - Regenerate every spec in -# sysfs_accessors_specs.py's SYSFS_SPECS list (.h/.c/.i per spec, one, two, +# update-attr-accessors.sh - Regenerate every spec in +# attr_accessors_specs.py's ATTR_SPECS list (.h/.c/.i per spec, one, two, # or three .c files depending on whether it has per-OS-divergent members) # only when they change; report .ld symbol drift instead of rewriting it. # @@ -19,18 +19,19 @@ # It is NOT run during a normal build. # # This script does not know any spec's name or output filenames -- it -# just diffs whatever generate_sysfs_accessors.py actually wrote into a +# just diffs whatever generate_attr_accessors.py actually wrote into a # scratch directory against the same-named file in the source tree, by # extension: .h/.c auto-update, .i auto-updates, .ld is diffed and # reported but never rewritten (which version section a symbol belongs # to is a maintainer decision, same as accessors.ld/accessors-fabrics.ld). -# Adding a spec to SYSFS_SPECS therefore needs no change here. +# Adding a spec to ATTR_SPECS therefore needs no change here. # # Arguments (supplied by the Meson run_target): # $1 path to the python3 interpreter -# $2 path to generate_sysfs_accessors.py -# $3 path to sysfs_accessors_specs.py (SYSFS_SPECS input) -# $4 output directory for every spec's .h/.c files +# $2 path to generate_attr_accessors.py +# $3 path to attr_accessors_specs.py (ATTR_SPECS input) +# $4 output directory whose 'generated' subdirectory holds every +# spec's .h/.c files # $5 output directory for every spec's .ld file # $6 output directory for every spec's .i file # [--check] optional: CI mode; read-only, exit non-zero on drift @@ -39,7 +40,7 @@ set -euo pipefail PYTHON="${1:?missing python3 interpreter}" GENERATOR="${2:?missing generator script}" -SPECS="${3:?missing sysfs_accessors_specs.py path}" +SPECS="${3:?missing attr_accessors_specs.py path}" OUT_DIR="${4:?missing output directory}" LD_OUT_DIR="${5:?missing ld output directory}" SWIG_OUT_DIR="${6:?missing swig output directory}" @@ -54,16 +55,20 @@ fi TMPDIR_WORK=$(mktemp -d) trap 'rm -rf "$TMPDIR_WORK"' EXIT +GENERATED_OUT_DIR="$OUT_DIR/generated" +GENERATED_TMP_DIR="$TMPDIR_WORK/generated" + # --------------------------------------------------------------------------- # Helper: update a source file atomically when content changes. # --------------------------------------------------------------------------- update_if_changed() { - local src="$1" # generated file in TMPDIR_WORK + local src="$1" # generated file in the scratch tree local dest="$2" # target path in the source tree if [ -f "$dest" ] && cmp -s "$src" "$dest"; then printf " unchanged: %s\n" "$(basename "$dest")" else + mkdir -p "$(dirname "$dest")" local tmp_dest tmp_dest=$(mktemp "$(dirname "$dest")/.$(basename "$dest").XXXXXX") cp "$src" "$tmp_dest" @@ -148,10 +153,10 @@ check_ld_drift() { # --------------------------------------------------------------------------- # Run generator into the scratch directory -- one run generates every spec -# in SYSFS_SPECS. +# in ATTR_SPECS. # --------------------------------------------------------------------------- echo "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++" -echo "--- sysfs-accessors: begin generation ---" +echo "--- attr-accessors: begin generation ---" echo "" "$PYTHON" "$GENERATOR" --specs "$SPECS" --out-dir "$TMPDIR_WORK" \ @@ -163,9 +168,9 @@ if [ "$CHECK_MODE" -eq 1 ]; then # anything is out of sync. # ------------------------------------------------------------------ DRIFT=0 - for f in "$TMPDIR_WORK"/*.h "$TMPDIR_WORK"/*.c; do + for f in "$GENERATED_TMP_DIR"/*.h "$GENERATED_TMP_DIR"/*.c; do [ -e "$f" ] || continue - check_if_current "$f" "$OUT_DIR/$(basename "$f")" + check_if_current "$f" "$GENERATED_OUT_DIR/$(basename "$f")" done for f in "$TMPDIR_WORK"/*.i; do [ -e "$f" ] || continue @@ -184,7 +189,7 @@ if [ "$CHECK_MODE" -eq 1 ]; then echo "(.ld symbol changes require manual version-script edits;" \ "see WARNING above.)" echo "" - echo "--- sysfs-accessors: check FAILED ---" + echo "--- attr-accessors: check FAILED ---" echo "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++" echo "" exit 1 @@ -195,9 +200,9 @@ else # Update mode: auto-update .h/.c/.i; report .ld drift as advisory. # ------------------------------------------------------------------ CHANGED=0 - for f in "$TMPDIR_WORK"/*.h "$TMPDIR_WORK"/*.c; do + for f in "$GENERATED_TMP_DIR"/*.h "$GENERATED_TMP_DIR"/*.c; do [ -e "$f" ] || continue - update_if_changed "$f" "$OUT_DIR/$(basename "$f")" + update_if_changed "$f" "$GENERATED_OUT_DIR/$(basename "$f")" done for f in "$TMPDIR_WORK"/*.i; do [ -e "$f" ] || continue @@ -205,10 +210,10 @@ else done echo "" if [ "$CHANGED" -gt 0 ]; then - printf "%d file(s) updated in %s\n" "$CHANGED" "$OUT_DIR" + printf "%d file(s) updated in %s\n" "$CHANGED" "$GENERATED_OUT_DIR" echo "Don't forget to commit the updated files." else - echo "All sysfs-accessor source files are up to date." + echo "All attr-accessor source files are up to date." fi echo "" for f in "$TMPDIR_WORK"/*.ld; do @@ -218,6 +223,6 @@ else fi echo "" -echo "--- sysfs-accessors: generation complete ---" +echo "--- attr-accessors: generation complete ---" echo "++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++" echo "" From d9336c50215e9272d3920140a35f4ca9ed51ef52 Mon Sep 17 00:00:00 2001 From: Martin Belanger Date: Fri, 7 Aug 2026 16:43:20 -0400 Subject: [PATCH 2/2] libnvme: move accessors.[ch] and accessors-fabrics.[ch] to generated subdir keep generated files out of src/nvme/ so they're visually separate from the hand-written files around them. Also fixes stale-header fallback bugs this move would otherwise cause: tid.c/tid.h, exclusion.c, and discoverd/src/tid.h all reference these headers via the public "nvme/accessors-fabrics.h" path rather than a same-directory include, which was silently resolving to a stale copy in /usr/include from a previous install once the real file moved. Also fixes a -Werror build break introduced by the generated/ subdir move: nvme_incdir (added in the previous commit to let a quoted #include "private.h" resolve from nvme/generated/*.c) put -Ilibnvme/src/nvme on every compile command, which made libnvme/src/nvme/endian.h's own #include resolve back to itself instead of glibc's real header -- #pragma once silently no-ops the self-reference, dropping the declarations for htole64/htobe64/etc. Only visible as a warning locally; CI builds with --werror, where it's fatal. Removes nvme_incdir and instead makes both generators emit correct explicit relative includes (../private.h, ../private-fabrics.h) for the headers they parsed, now that their .c output lives one directory below. Verified with --werror (default and -Dfabrics=disabled), full test suite, and a live smoke test. Signed-off-by: Martin Belanger --- CONTRIBUTING.md | 4 ++-- discoverd/src/tid.h | 2 +- libnvme/design/tooling/generate_accessors.md | 4 ++-- libnvme/doc/meson.build | 4 ++-- libnvme/src/fabrics-includes.h.in | 2 +- libnvme/src/libnvme.h.in | 2 +- libnvme/src/meson.build | 18 ++++++------------ libnvme/src/nvme/exclusion.c | 2 +- .../nvme/{ => generated}/accessors-fabrics.c | 2 +- .../nvme/{ => generated}/accessors-fabrics.h | 0 libnvme/src/nvme/{ => generated}/accessors.c | 2 +- libnvme/src/nvme/{ => generated}/accessors.h | 0 libnvme/src/nvme/generated/ctrl-attrs.c | 4 ++-- libnvme/src/nvme/generated/ns-attrs.c | 4 ++-- libnvme/src/nvme/generated/path-attrs.c | 4 ++-- libnvme/src/nvme/generated/subsys-attrs.c | 4 ++-- libnvme/src/nvme/tid.c | 2 +- libnvme/src/nvme/tid.h | 2 +- libnvme/test/config-emit.c | 2 +- libnvme/tools/generator/generate_accessors.py | 13 +++++++++++-- .../tools/generator/generate_attr_accessors.py | 4 ++-- libnvme/tools/generator/meson.build | 11 ++++++----- 22 files changed, 48 insertions(+), 44 deletions(-) rename libnvme/src/nvme/{ => generated}/accessors-fabrics.c (99%) rename libnvme/src/nvme/{ => generated}/accessors-fabrics.h (100%) rename libnvme/src/nvme/{ => generated}/accessors.c (99%) rename libnvme/src/nvme/{ => generated}/accessors.h (100%) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index ba49ca61d1..15fea9a7f9 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -175,8 +175,8 @@ The script atomically updates the `.h` and `.c` files when their content changes. Commit the updated files afterward: ```shell -$ git add libnvme/src/nvme/accessors.h libnvme/src/nvme/accessors.c -$ git add libnvme/src/nvme/accessors-fabrics.h libnvme/src/nvme/accessors-fabrics.c +$ git add libnvme/src/nvme/generated/accessors.h libnvme/src/nvme/generated/accessors.c +$ git add libnvme/src/nvme/generated/accessors-fabrics.h libnvme/src/nvme/generated/accessors-fabrics.c $ git commit -m "libnvme: regenerate accessors following changes" ``` diff --git a/discoverd/src/tid.h b/discoverd/src/tid.h index 0f901456bd..324d772922 100644 --- a/discoverd/src/tid.h +++ b/discoverd/src/tid.h @@ -9,7 +9,7 @@ #include -#include +#include #include #include diff --git a/libnvme/design/tooling/generate_accessors.md b/libnvme/design/tooling/generate_accessors.md index c659c8ef60..045d918008 100644 --- a/libnvme/design/tooling/generate_accessors.md +++ b/libnvme/design/tooling/generate_accessors.md @@ -407,8 +407,8 @@ What each member demonstrates: ``` python3 generate_accessors.py \ - --h-out src/nvme/accessors-fabrics.h \ - --c-out src/nvme/accessors-fabrics.c \ + --h-out src/nvme/generated/accessors-fabrics.h \ + --c-out src/nvme/generated/accessors-fabrics.c \ --ld-out src/accessors-fabrics.ld \ src/nvme/private-fabrics.h ``` diff --git a/libnvme/doc/meson.build b/libnvme/doc/meson.build index 791246577c..0eba75ef09 100644 --- a/libnvme/doc/meson.build +++ b/libnvme/doc/meson.build @@ -9,8 +9,8 @@ # api_files = [ - 'accessors-fabrics.h', - 'accessors.h', + 'generated/accessors-fabrics.h', + 'generated/accessors.h', 'fabrics.h', 'ioctl.h', 'lib-types.h', diff --git a/libnvme/src/fabrics-includes.h.in b/libnvme/src/fabrics-includes.h.in index 0313268b4f..ea18203462 100644 --- a/libnvme/src/fabrics-includes.h.in +++ b/libnvme/src/fabrics-includes.h.in @@ -1,4 +1,4 @@ -#include +#include #include #include #include diff --git a/libnvme/src/libnvme.h.in b/libnvme/src/libnvme.h.in index 2cd2fc8207..398aae2129 100644 --- a/libnvme/src/libnvme.h.in +++ b/libnvme/src/libnvme.h.in @@ -12,7 +12,7 @@ extern "C" { #endif -#include +#include #include #include #include diff --git a/libnvme/src/meson.build b/libnvme/src/meson.build index 4bcfaa4a61..7f2a535826 100644 --- a/libnvme/src/meson.build +++ b/libnvme/src/meson.build @@ -6,7 +6,7 @@ # Authors: Martin Belanger # sources = [ - 'nvme/accessors.c', + 'nvme/generated/accessors.c', 'nvme/generated/subsys-attrs.c', 'nvme/ioctl.c', 'nvme/lib.c', @@ -40,7 +40,6 @@ elif host_system == 'windows' ] endif headers = [ - 'nvme/accessors.h', 'nvme/endian.h', 'nvme/ioctl.h', 'nvme/lib-types.h', @@ -68,6 +67,7 @@ headers = [ # headers above) -- kept in their own subdirectory and installed under # nvme/generated/ so libnvme.h.in can #include them by that same path. generated_headers = [ + 'nvme/generated/accessors.h', 'nvme/generated/ctrl-attrs.h', 'nvme/generated/path-attrs.h', 'nvme/generated/ns-attrs.h', @@ -76,7 +76,7 @@ generated_headers = [ if want_fabrics sources += [ - 'nvme/accessors-fabrics.c', + 'nvme/generated/accessors-fabrics.c', 'nvme/crypto.c', 'nvme/config.c', 'nvme/config-emit.c', @@ -90,8 +90,10 @@ if want_fabrics 'nvme/tree-fabrics.c', 'nvme/util-fabrics.c', ] + generated_headers += [ + 'nvme/generated/accessors-fabrics.h', + ] headers += [ - 'nvme/accessors-fabrics.h', 'nvme/config.h', 'nvme/crypto.h', 'nvme/exclusion.h', @@ -211,18 +213,11 @@ libnvme_header = configure_file( install_dir: prefixdir / get_option('includedir') / libnvme_api_name ) -# Needed so a quoted #include (e.g. "private.h") from nvme/generated/*.c -# still resolves against nvme/ -- the compiler's own current-file-directory -# rule only reaches siblings, not a parent, and generated/*.c sits one -# level deeper than the hand-written files it's #include'd from. -nvme_incdir = include_directories('nvme') - libnvme = library( libnvme_link_name, # produces libnvme.so sources, version: libnvme_so_version, c_args: ['-fvisibility=hidden'], - include_directories: nvme_incdir, link_args: link_args, dependencies: deps, install: true, @@ -249,7 +244,6 @@ libnvme_dep = declare_dependency( libnvme_test = library( libnvme_link_name + '-test', sources, - include_directories: nvme_incdir, dependencies: deps, install: false, ) diff --git a/libnvme/src/nvme/exclusion.c b/libnvme/src/nvme/exclusion.c index 7bb3b8fc16..f53834610b 100644 --- a/libnvme/src/nvme/exclusion.c +++ b/libnvme/src/nvme/exclusion.c @@ -38,7 +38,7 @@ #include "cleanup.h" #include "exclusion.h" #include "lib.h" -#include "nvme/accessors-fabrics.h" +#include "nvme/generated/accessors-fabrics.h" #include "nvme/tid.h" #include "private.h" #include "private-fabrics.h" diff --git a/libnvme/src/nvme/accessors-fabrics.c b/libnvme/src/nvme/generated/accessors-fabrics.c similarity index 99% rename from libnvme/src/nvme/accessors-fabrics.c rename to libnvme/src/nvme/generated/accessors-fabrics.c index d218719c58..36d8f16aca 100644 --- a/libnvme/src/nvme/accessors-fabrics.c +++ b/libnvme/src/nvme/generated/accessors-fabrics.c @@ -25,7 +25,7 @@ #include "accessors-fabrics.h" -#include "private-fabrics.h" +#include "../private-fabrics.h" /**************************************************************************** * Accessors for: struct libnvmf_context diff --git a/libnvme/src/nvme/accessors-fabrics.h b/libnvme/src/nvme/generated/accessors-fabrics.h similarity index 100% rename from libnvme/src/nvme/accessors-fabrics.h rename to libnvme/src/nvme/generated/accessors-fabrics.h diff --git a/libnvme/src/nvme/accessors.c b/libnvme/src/nvme/generated/accessors.c similarity index 99% rename from libnvme/src/nvme/accessors.c rename to libnvme/src/nvme/generated/accessors.c index 06cc06c4c2..1586a386d9 100644 --- a/libnvme/src/nvme/accessors.c +++ b/libnvme/src/nvme/generated/accessors.c @@ -25,7 +25,7 @@ #include "accessors.h" -#include "private.h" +#include "../private.h" /**************************************************************************** * Accessors for: struct libnvme_path diff --git a/libnvme/src/nvme/accessors.h b/libnvme/src/nvme/generated/accessors.h similarity index 100% rename from libnvme/src/nvme/accessors.h rename to libnvme/src/nvme/generated/accessors.h diff --git a/libnvme/src/nvme/generated/ctrl-attrs.c b/libnvme/src/nvme/generated/ctrl-attrs.c index 57303cc128..abb3c5f632 100644 --- a/libnvme/src/nvme/generated/ctrl-attrs.c +++ b/libnvme/src/nvme/generated/ctrl-attrs.c @@ -25,8 +25,8 @@ #include -#include "private.h" -#include "private-tree.h" +#include "../private.h" +#include "../private-tree.h" #include "ctrl-attrs.h" struct libnvme_ctrl_attrs { diff --git a/libnvme/src/nvme/generated/ns-attrs.c b/libnvme/src/nvme/generated/ns-attrs.c index 9cd414aac1..a448ce992d 100644 --- a/libnvme/src/nvme/generated/ns-attrs.c +++ b/libnvme/src/nvme/generated/ns-attrs.c @@ -25,8 +25,8 @@ #include -#include "private.h" -#include "private-tree.h" +#include "../private.h" +#include "../private-tree.h" #include "ns-attrs.h" struct libnvme_ns_attrs { diff --git a/libnvme/src/nvme/generated/path-attrs.c b/libnvme/src/nvme/generated/path-attrs.c index a9a2d8f2cd..39709e80d8 100644 --- a/libnvme/src/nvme/generated/path-attrs.c +++ b/libnvme/src/nvme/generated/path-attrs.c @@ -25,8 +25,8 @@ #include -#include "private.h" -#include "private-tree.h" +#include "../private.h" +#include "../private-tree.h" #include "path-attrs.h" struct libnvme_path_attrs { diff --git a/libnvme/src/nvme/generated/subsys-attrs.c b/libnvme/src/nvme/generated/subsys-attrs.c index 2db7eef1e1..7d2703e2bc 100644 --- a/libnvme/src/nvme/generated/subsys-attrs.c +++ b/libnvme/src/nvme/generated/subsys-attrs.c @@ -25,8 +25,8 @@ #include -#include "private.h" -#include "private-tree.h" +#include "../private.h" +#include "../private-tree.h" #include "subsys-attrs.h" struct libnvme_subsystem_attrs { diff --git a/libnvme/src/nvme/tid.c b/libnvme/src/nvme/tid.c index 23c1da109b..578ba69f96 100644 --- a/libnvme/src/nvme/tid.c +++ b/libnvme/src/nvme/tid.c @@ -15,7 +15,7 @@ #include #include -#include "nvme/accessors-fabrics.h" +#include "nvme/generated/accessors-fabrics.h" #include "nvme/lib.h" #include "nvme/tid.h" #include "private-fabrics.h" diff --git a/libnvme/src/nvme/tid.h b/libnvme/src/nvme/tid.h index be4c9727bb..15a6ab8faa 100644 --- a/libnvme/src/nvme/tid.h +++ b/libnvme/src/nvme/tid.h @@ -8,7 +8,7 @@ #pragma once #include -#include +#include struct libnvme_global_ctx; diff --git a/libnvme/test/config-emit.c b/libnvme/test/config-emit.c index aa3cdc74d1..2d41a6f1f0 100644 --- a/libnvme/test/config-emit.c +++ b/libnvme/test/config-emit.c @@ -24,7 +24,7 @@ #include #include #include -#include +#include static const char *g_hostid = "46ba5037-7ce5-41fa-9452-48477bf00080"; diff --git a/libnvme/tools/generator/generate_accessors.py b/libnvme/tools/generator/generate_accessors.py index 9bf3ace9b5..ea60f46b71 100755 --- a/libnvme/tools/generator/generate_accessors.py +++ b/libnvme/tools/generator/generate_accessors.py @@ -2528,7 +2528,16 @@ def main(): # ----------------------------------------------------------------------- # Pass 2 — parse all header files, accumulate generated fragments. # ----------------------------------------------------------------------- - files_to_include = [] # basenames of headers that contributed structs + files_to_include = [] # '../' + basename of headers that contributed + # structs -- '../' because the generated .c + # always lands one directory below the header + # it was parsed from (src/nvme/generated/ vs. + # src/nvme/). Not computed via os.path.relpath + # against args.c_fname: the update script stages + # output in a throwaway mktemp -d before copying + # it to its real destination, so args.c_fname's + # own directory does not reflect where the file + # actually ends up. forward_declares = [] # struct names needing forward declarations hdr_parts = [] # fragments for accessors.h src_parts = [] # fragments for accessors.c @@ -2581,7 +2590,7 @@ def main(): print(f"No annotated structs found in {in_hdr}.") continue - files_to_include.append(os.path.basename(in_hdr)) + files_to_include.append('../' + os.path.basename(in_hdr)) for (struct_name, members, lc_members, default_members, emit_py, struct_alias, name_prefix) in structs: diff --git a/libnvme/tools/generator/generate_attr_accessors.py b/libnvme/tools/generator/generate_attr_accessors.py index 4964a6a761..288cc94ba8 100755 --- a/libnvme/tools/generator/generate_attr_accessors.py +++ b/libnvme/tools/generator/generate_attr_accessors.py @@ -401,8 +401,8 @@ def generate_source_shared(spec, shared_members): '#include \n' '#include \n\n' '#include \n\n' - '#include "private.h"\n' - '#include "private-tree.h"\n' + '#include "../private.h"\n' + '#include "../private-tree.h"\n' f'#include "{spec["header"]}"\n\n' ) diff --git a/libnvme/tools/generator/meson.build b/libnvme/tools/generator/meson.build index 0a869847fd..44653f0fd5 100644 --- a/libnvme/tools/generator/meson.build +++ b/libnvme/tools/generator/meson.build @@ -20,7 +20,8 @@ # Usage: meson compile -C update-accessors # --------------------------------------------------------------------------- -# Generated source files go to src/nvme/ (alongside the library sources). +# Generated source files go to src/nvme/generated/ (kept separate from the +# hand-written library sources alongside it in src/nvme/). # The generated version script goes to src/ (alongside the other .ld files). # The generated SWIG includes and Python-only headers go to libnvme/ alongside # nvme.i. @@ -41,8 +42,8 @@ _tgt_common = run_target( 'update-accessors.sh', _py3, files('generate_accessors.py'), - libnvme_src_nvme / 'accessors.h', - libnvme_src_nvme / 'accessors.c', + libnvme_src_nvme / 'generated' / 'accessors.h', + libnvme_src_nvme / 'generated' / 'accessors.c', libnvme_src / 'accessors.ld', ] + _check_flag + [ '--swig-out', libnvme_swig_dir / 'accessors.i', @@ -58,8 +59,8 @@ _tgt_fabrics = run_target( 'update-accessors.sh', _py3, files('generate_accessors.py'), - libnvme_src_nvme / 'accessors-fabrics.h', - libnvme_src_nvme / 'accessors-fabrics.c', + libnvme_src_nvme / 'generated' / 'accessors-fabrics.h', + libnvme_src_nvme / 'generated' / 'accessors-fabrics.c', libnvme_src / 'accessors-fabrics.ld', ] + _check_flag + [ '--swig-out', libnvme_swig_dir / 'accessors-fabrics.i',