All checks were successful
Source release / source-package (push) Successful in 47s
Extend the conservative NCP 0x2222/35/16 AFP 2.0 Set File Information smoke path beyond FinderInfo-only writes by accepting the file Attributes bitmap for one deliberately narrow bit: Finder Invisible. WebSDK and Netatalk FPSetFileParams semantics carry file attributes as bitmap bit 0, with ATTRBIT_SETCLR selecting set-vs-clear behavior. Mirror that model only for ATTRBIT_INVISIBLE and reject all other AFP attribute bits so DOS/NetWare mode bits, timestamp writes, resource forks, and broader file protection semantics are not implied accidentally. Persist the mars_nwe-owned AFP attribute word in org.mars-nwe.afp.attributes via the local xattr abstraction. On Linux this maps to user.org.mars-nwe.afp.attributes, matching the org.mars-nwe.* source-level namespace while remaining portable on Linux xattr backends. Get File Information and Scan File Information now merge that stored Invisible bit into the existing 120-byte AFP file-info record. Update the Linux Set File Information smoke helper with --invisible, --clear-invisible, --attributes-only, and --finder-info-only so FinderInfo and the narrow AFP attribute path can be tested independently or together. Tests: git diff --check Tests: gcc -Iinclude -I/mnt/data/stubs -fsyntax-only tests/linux/afp_set_file_info_smoke.c TODO: keep all other AFP Set File Information bits rejected until their write-safe mapping to NetWare/DOS attributes, timestamps, CNID, and resource-fork metadata is designed.
477 lines
22 KiB
Markdown
477 lines
22 KiB
Markdown
# Linux NCP smoke tests
|
|
|
|
This directory contains optional Linux-side integration tests for endpoints that
|
|
are easier to exercise from a Unix host than from the DOS test utilities.
|
|
|
|
The tests use the ncpfs/libncp client library. They are not built by default
|
|
because they require the host ncpfs development headers/library and a running
|
|
NetWare-compatible server.
|
|
|
|
The AFP endpoints are intentionally conservative. mars_nwe-owned ids are read
|
|
from the versioned `org.mars-nwe.afp.entry-id` xattr before falling back to
|
|
Netatalk/libatalk AppleDouble/CNID metadata. When neither source has an id yet,
|
|
the existing stat-derived compatibility id is cached in that xattr so subsequent
|
|
AFP probes can reuse the same mars_nwe-owned id instead of re-entering the
|
|
temporary fallback path. The first AFP write smoke path is deliberately limited
|
|
to the FinderInfo bitmap of
|
|
AFP 2.0 Set File Information; CNID allocation, DOS attribute mapping, resource
|
|
fork writes, and data-fork writes remain separate write-safety work. mars_nwe
|
|
source uses Netatalk-style `org.mars-nwe.<domain>.*` xattr names; AFP
|
|
metadata stays under `org.mars-nwe.afp.*` while NetWare-core metadata uses
|
|
`org.mars-nwe.netware.*`. On Linux the local xattr helper stores those through
|
|
the portable `user.` namespace, matching Netatalk's `org.netatalk.*` EA
|
|
abstraction style.
|
|
|
|
Build with:
|
|
|
|
```sh
|
|
cmake -DMARS_NWE_BUILD_LINUX_TESTS=ON ...
|
|
cmake --build . --target afp_entry_id_smoke
|
|
cmake --build . --target afp_file_info_smoke
|
|
cmake --build . --target afp_scan_info_smoke
|
|
cmake --build . --target afp_temp_dir_handle_smoke
|
|
cmake --build . --target afp_set_file_info_smoke
|
|
```
|
|
|
|
## AFP Entry ID smoke test
|
|
|
|
`afp_entry_id_smoke` sends the WebSDK-documented NetWare AFP request:
|
|
|
|
```text
|
|
NCP 0x2222/35/12 AFP Get Entry ID From Path Name
|
|
```
|
|
|
|
It uses libncp's `NWRequestSimple()` path, so it goes through the same client
|
|
transport stack as other Linux ncpfs utilities.
|
|
|
|
Example:
|
|
|
|
```sh
|
|
./tests/linux/afp_entry_id_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
```
|
|
|
|
The test accepts NetWare-style `VOL:PATH` arguments. By default it sends the
|
|
supplied `SYS:`-style path directly with directory handle 0, matching the
|
|
verified mars_nwe smoke-test path. `--alloc-handle` is available only for
|
|
follow-up debugging of the separate directory-handle allocation path, and
|
|
`--dir-handle N` expects a handle that is valid in the current connection.
|
|
|
|
Useful smoke cases for a standard MARS-NWE `SYS` volume are:
|
|
|
|
```sh
|
|
./tests/linux/afp_entry_id_smoke -S MARS -U SUPERVISOR -P secret SYS:
|
|
./tests/linux/afp_entry_id_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_entry_id_smoke -S MARS -U SUPERVISOR -P secret SYS:SYSTEM
|
|
./tests/linux/afp_entry_id_smoke -S MARS -U SUPERVISOR -P secret SYS:BURST
|
|
```
|
|
|
|
A successful reply prints the request path, directory handle, and returned
|
|
32-bit AFP Entry ID. Server-side diagnostics currently mark stat-derived
|
|
temporary IDs with `fallback`; that means the endpoint is reachable, but
|
|
persistent CNID/AppleDouble entry-id storage is still future Mac-namespace
|
|
work.
|
|
|
|
If the server was built without the optional Netatalk/libatalk backend, the
|
|
endpoint is expected to return invalid namespace. To treat that as a successful
|
|
negative smoke test, use:
|
|
|
|
```sh
|
|
./tests/linux/afp_entry_id_smoke --allow-invalid-namespace -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
```
|
|
|
|
For path-resolution negative tests, use `--allow-invalid-path` to accept the
|
|
expected `0x9c` Invalid Path completion.
|
|
|
|
|
|
### AFP Get Entry ID From Name
|
|
|
|
`afp_entry_id_smoke` can also exercise the WebSDK-documented NetWare AFP
|
|
request:
|
|
|
|
```text
|
|
NCP 0x2222/35/04 AFP Get Entry ID From Name
|
|
```
|
|
|
|
Use `--from-name` to select this subfunction. The current mars_nwe
|
|
implementation supports the same verified path-backed smoke mode as
|
|
`AFP Get Entry ID From Path Name`: pass a raw `SYS:`-style path with directory
|
|
handle 0 and base Entry ID 0.
|
|
|
|
Useful smoke cases for a standard MARS-NWE `SYS` volume are:
|
|
|
|
```sh
|
|
./tests/linux/afp_entry_id_smoke --from-name -S MARS -U SUPERVISOR -P secret SYS:
|
|
./tests/linux/afp_entry_id_smoke --from-name -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_entry_id_smoke --from-name -S MARS -U SUPERVISOR -P secret SYS:SYSTEM
|
|
./tests/linux/afp_entry_id_smoke --from-name -S MARS -U SUPERVISOR -P secret SYS:BURST
|
|
```
|
|
|
|
A successful reply prints the same 32-bit AFP Entry ID format as the path-name
|
|
probe. Server-side diagnostics currently mark stat-derived temporary IDs with
|
|
`fallback`; real base-entry-id-relative lookup still depends on persistent
|
|
CNID/AppleDouble mapping.
|
|
|
|
### AFP Get Entry ID From NetWare Handle
|
|
|
|
`afp_entry_id_smoke` can also exercise the WebSDK-documented NetWare AFP
|
|
request:
|
|
|
|
```text
|
|
NCP 0x2222/35/06 AFP Get Entry ID From NetWare Handle
|
|
```
|
|
|
|
Use `--from-handle` to select this subfunction. The smoke test opens the
|
|
requested file through libncp in the same connection, passes the returned
|
|
6-byte NetWare file handle to the AFP request, and closes the file after the
|
|
AFP reply. This is important because NetWare file handles are connection-local:
|
|
`--dir-handle N` and file-handle values copied from server logs or unrelated
|
|
helper processes are not stable inputs for this request.
|
|
|
|
Useful smoke cases for a standard MARS-NWE `SYS:PUBLIC` directory are:
|
|
|
|
```sh
|
|
./tests/linux/afp_entry_id_smoke --from-handle -S MARS -U SUPERVISOR -P secret SYS:PUBLIC/pmdflts.ini
|
|
./tests/linux/afp_entry_id_smoke --from-handle -S MARS -U SUPERVISOR -P secret SYS:PUBLIC/ohlogscr.bat
|
|
```
|
|
|
|
Successful replies print the resolved volume number, 32-bit AFP Entry ID, and
|
|
fork indicator. The current implementation reports the data fork (`fork=0`)
|
|
and server diagnostics mark the returned Entry ID as `fallback` when it is
|
|
derived from Unix `stat(2)` data rather than persistent CNID, AppleDouble, or
|
|
libatalk metadata:
|
|
|
|
```text
|
|
AFP Entry ID From NetWare Handle path=SYS:PUBLIC/pmdflts.ini volume=0 entry_id=0x23c8787d (600340605) fork=0
|
|
AFP Entry ID From NetWare Handle path=SYS:PUBLIC/ohlogscr.bat volume=0 entry_id=0x260437f6 (637810678) fork=0
|
|
|
|
AFP Get Entry ID From NetWare Handle: handle=1 volume=0 unix='/var/mars_nwe/SYS/public/pmdflts.ini' entry=0x23c8787d fallback
|
|
AFP Get Entry ID From NetWare Handle: handle=1 volume=0 unix='/var/mars_nwe/SYS/public/ohlogscr.bat' entry=0x260437f6 fallback
|
|
```
|
|
|
|
The concrete fallback Entry IDs vary with filesystem metadata. Persistent
|
|
CNID/AppleDouble/libatalk-backed identity, parent Entry ID derivation, and AFP
|
|
resource-fork handle semantics remain future Mac-namespace work; the current
|
|
smoke coverage only verifies the conservative read-only data-fork mapping.
|
|
|
|
## AFP Alloc Temporary Directory Handle smoke test
|
|
|
|
`afp_temp_dir_handle_smoke` sends the WebSDK-documented NetWare AFP request:
|
|
|
|
```text
|
|
NCP 0x2222/35/11 AFP Alloc Temporary Directory Handle
|
|
```
|
|
|
|
The request layout is the AFP volume number, base AFP Entry ID, path length,
|
|
and AFP-style path. The current mars_nwe implementation supports the same
|
|
conservative path-backed subset as the Entry ID and File Information probes:
|
|
pass a raw `VOL:`-style path such as `SYS:` or `HOME:` and keep the
|
|
base Entry ID at zero. The compatibility server resolves the effective
|
|
NetWare volume from that path prefix instead of assuming volume 0; the request
|
|
volume byte is retained for WebSDK/header shape and for later Entry-ID-relative
|
|
lookup work. Pure Entry-ID-relative allocation is still rejected with Invalid
|
|
Path until persistent CNID/base-ID lookup exists.
|
|
|
|
Useful smoke cases for a standard MARS-NWE `SYS` volume are:
|
|
|
|
```sh
|
|
./tests/linux/afp_temp_dir_handle_smoke -S MARS -U SUPERVISOR -P secret SYS:
|
|
./tests/linux/afp_temp_dir_handle_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_temp_dir_handle_smoke -S MARS -U SUPERVISOR -P secret SYS:SYSTEM
|
|
./tests/linux/afp_temp_dir_handle_smoke -S MARS -U SUPERVISOR -P secret SYS:BURST
|
|
```
|
|
|
|
On installations with another exported volume, the same helper can be run
|
|
against that raw prefix, for example `HOME:`. The server log should then show
|
|
the resolved volume number for `HOME:` rather than hard-coded `vol=0`.
|
|
|
|
A successful reply prints the allocated temporary NetWare directory handle and
|
|
the effective-rights mask returned by the server. The smoke helper immediately
|
|
deallocates the handle with the normal NetWare Deallocate Directory Handle call
|
|
before closing the connection, so the handle value is only useful inside that
|
|
client connection and must not be copied into later tests or server logs.
|
|
|
|
Runtime-verified output and server diagnostic shape:
|
|
|
|
```text
|
|
AFP Alloc Temporary Dir Handle path=SYS: dir_handle=2 rights=0xff
|
|
AFP Alloc Temporary Dir Handle path=SYS:PUBLIC dir_handle=2 rights=0xff
|
|
AFP Alloc Temporary Dir Handle path=SYS:SYSTEM dir_handle=2 rights=0xff
|
|
AFP Alloc Temporary Dir Handle path=SYS:BURST dir_handle=2 rights=0xff
|
|
AFP Alloc Temporary Dir Handle: vol=0 request_vol=0 entry=0x00000000 path='SYS:' dir_handle=2 rights=0x1ff
|
|
AFP Alloc Temporary Dir Handle: vol=0 request_vol=0 entry=0x00000000 path='SYS:PUBLIC' dir_handle=2 rights=0x1ff
|
|
AFP Alloc Temporary Dir Handle: vol=0 request_vol=0 entry=0x00000000 path='SYS:SYSTEM' dir_handle=2 rights=0x1ff
|
|
AFP Alloc Temporary Dir Handle: vol=0 request_vol=0 entry=0x00000000 path='SYS:BURST' dir_handle=2 rights=0x1ff
|
|
```
|
|
|
|
The AFP reply carries the one-byte access-rights field consumed by the smoke
|
|
helper, so the client prints `0xff`. The server diagnostic logs the internal
|
|
NetWare effective-rights mask before that AFP reply narrowing, so a fully
|
|
privileged directory can appear as `0x1ff` in `mars_nwe.log`.
|
|
|
|
If the server was built without the optional Netatalk/libatalk backend, use
|
|
`--allow-invalid-namespace` for the expected negative test. Use
|
|
`--allow-invalid-path` for path-resolution negative tests.
|
|
|
|
|
|
## AFP Open File Fork smoke test
|
|
|
|
`afp_open_file_fork_smoke` sends the WebSDK-documented NetWare AFP open fork
|
|
request:
|
|
|
|
```text
|
|
NCP 0x2222/35/08 AFP Open File Fork
|
|
```
|
|
|
|
The first mars_nwe implementation is deliberately conservative. It supports
|
|
raw `VOL:`-style path requests such as `SYS:` or `HOME:` with base Entry ID
|
|
zero, opens only the AFP data fork, and only for read access. For path-backed
|
|
requests, mars_nwe resolves the effective NetWare volume from the raw path
|
|
prefix instead of assuming volume 0. On success the server returns the
|
|
normal six-byte NetWare file handle shape used by AFP handle APIs plus the
|
|
current data-fork length. The smoke helper immediately closes the returned
|
|
NetWare file handle in the same connection.
|
|
|
|
Useful smoke cases for a standard MARS-NWE `SYS` volume are:
|
|
|
|
```sh
|
|
./tests/linux/afp_open_file_fork_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC/pmdflts.ini
|
|
./tests/linux/afp_open_file_fork_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC/ohlogscr.bat
|
|
```
|
|
|
|
A file on another exported volume should be tested with its raw volume prefix
|
|
(for example `HOME:...`). The matching server log should report that resolved
|
|
volume number, while still showing the request volume byte separately.
|
|
|
|
A successful reply prints the returned NetWare handle, the requested fork, the
|
|
read access mode, and the data-fork length. A verified runtime smoke run
|
|
against the standard DOS utility files produced:
|
|
|
|
```text
|
|
AFP Open File Fork path=SYS:PUBLIC/pmdflts.ini handle=1 fork=0 access=0x01 fork_len=8161
|
|
AFP Open File Fork path=SYS:PUBLIC/ohlogscr.bat handle=1 fork=0 access=0x01 fork_len=1296
|
|
```
|
|
|
|
The matching server log records the path-backed open and the same data-fork
|
|
lengths:
|
|
|
|
```text
|
|
AFP Open File Fork: vol=0 request_vol=0 entry=0x00000000 fork=0 access=0x01 path='SYS:PUBLIC/pmdflts.ini' handle=1 fork_len=8161
|
|
AFP Open File Fork: vol=0 request_vol=0 entry=0x00000000 fork=0 access=0x01 path='SYS:PUBLIC/ohlogscr.bat' handle=1 fork_len=1296
|
|
```
|
|
|
|
The exact handle number is connection-local and must not be reused across
|
|
processes. The exact `fork_len` depends on the backing file contents. Resource fork
|
|
opens (`--fork 1`), write access (`--access 2`), and Entry-ID-only open remain
|
|
negative/TODO coverage until persistent CNID/base-ID lookup and AppleDouble
|
|
resource-fork semantics are available.
|
|
|
|
If the server was built without the optional Netatalk/libatalk backend, use
|
|
`--allow-invalid-namespace` for the expected negative test. Use
|
|
`--allow-invalid-path` for path-resolution, resource-fork, or Entry-ID-only
|
|
negative tests.
|
|
|
|
## AFP File Information smoke test
|
|
|
|
`afp_file_info_smoke` sends the WebSDK-documented NetWare AFP file
|
|
information requests:
|
|
|
|
```text
|
|
NCP 0x2222/35/05 AFP Get File Information
|
|
NCP 0x2222/35/15 AFP 2.0 Get File Information
|
|
```
|
|
|
|
It uses the same libncp `NWRequestSimple()` transport path as the Entry ID
|
|
smoke test and sends raw `SYS:`-style path requests with directory handle 0.
|
|
The server replies with the read-only AFP file information record currently
|
|
implemented by mars_nwe: Entry ID, Parent ID, attributes, data/resource fork
|
|
lengths, offspring count, fixed long/short names, and access rights.
|
|
|
|
Useful smoke cases for a standard MARS-NWE `SYS` volume are:
|
|
|
|
```sh
|
|
./tests/linux/afp_file_info_smoke -S MARS -U SUPERVISOR -P secret SYS:
|
|
./tests/linux/afp_file_info_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_file_info_smoke -S MARS -U SUPERVISOR -P secret SYS:SYSTEM
|
|
./tests/linux/afp_file_info_smoke -S MARS -U SUPERVISOR -P secret SYS:BURST
|
|
|
|
# AFP 2.0 variant using the same path-backed read-only reply
|
|
./tests/linux/afp_file_info_smoke --afp20 -S MARS -U SUPERVISOR -P secret SYS:
|
|
./tests/linux/afp_file_info_smoke --afp20 -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_file_info_smoke --afp20 -S MARS -U SUPERVISOR -P secret SYS:SYSTEM
|
|
./tests/linux/afp_file_info_smoke --afp20 -S MARS -U SUPERVISOR -P secret SYS:BURST
|
|
```
|
|
|
|
The AFP 2.0 mode is selected with `--afp20`. It has been verified against
|
|
the same `SYS:`, `SYS:PUBLIC`, `SYS:SYSTEM`, and `SYS:BURST` paths and
|
|
currently exercises the same path-backed read-only reply as the older call.
|
|
The current implementation fills fields that can be derived from Unix `stat(2)` and the optional libatalk
|
|
helper wrappers. Server-side diagnostics mark
|
|
stat-derived temporary Entry IDs with `fallback`; Parent ID, persistent
|
|
CNID/AppleDouble IDs, and fuller Finder Info/resource-fork semantics remain
|
|
future Mac-namespace work.
|
|
|
|
If the server was built without the optional Netatalk/libatalk backend, use
|
|
`--allow-invalid-namespace` for the expected negative test. Use
|
|
`--allow-invalid-path` for path-resolution negative tests.
|
|
|
|
## AFP Scan File Information smoke test
|
|
|
|
`afp_scan_info_smoke` sends the WebSDK-documented NetWare AFP scan requests:
|
|
|
|
```text
|
|
NCP 0x2222/35/10 AFP Scan File Information
|
|
NCP 0x2222/35/17 AFP 2.0 Scan File Information
|
|
```
|
|
|
|
The helper defaults to the AFP 2.0 subfunction (`0x11`) and uses `--afp10`
|
|
to exercise the older `0x0a` endpoint. Both variants include the documented
|
|
DesiredResponseCount word; mars_nwe currently returns one path-backed read-only
|
|
entry per request, using the same AFP file information record as
|
|
`afp_file_info_smoke`. The test sends raw `SYS:`-style path requests with
|
|
directory handle 0 and uses the returned `next_last_seen` AFP Entry ID as the
|
|
continuation token for the next call.
|
|
|
|
Useful smoke sequence for a standard MARS-NWE `SYS:PUBLIC` directory:
|
|
|
|
```sh
|
|
./tests/linux/afp_scan_info_smoke -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_scan_info_smoke --afp10 -S MARS -U SUPERVISOR -P secret SYS:PUBLIC
|
|
./tests/linux/afp_scan_info_smoke -S MARS -U SUPERVISOR -P secret --last-seen 0x260437f6 SYS:PUBLIC
|
|
./tests/linux/afp_scan_info_smoke -S MARS -U SUPERVISOR -P secret --last-seen 0x6686342b SYS:PUBLIC
|
|
```
|
|
|
|
Verified runtime output from the sample `SYS:PUBLIC` tree after mars_nwe had
|
|
cached persistent AFP entry ids in `org.mars-nwe.afp.entry-id` xattrs:
|
|
|
|
```text
|
|
AFP Scan File Info subfunction=0x11 path=SYS:PUBLIC last_seen=0x00000000 desired=1 next_last_seen=0x260437f6 entry_id=0x260437f6 parent_id=0x00000000 attrs=0x0000 data_len=1296 resource_len=0 offspring=0 long_name=ohlogscr.bat short_name=ohlogscr.bat rights=0x9700
|
|
AFP Scan File Info subfunction=0x0a path=SYS:PUBLIC last_seen=0x00000000 desired=1 next_last_seen=0x23c8787d entry_id=0x23c8787d parent_id=0x00000000 attrs=0x0000 data_len=8161 resource_len=0 offspring=0 long_name=pmdflts.ini short_name=pmdflts.ini rights=0x9700
|
|
AFP Scan File Info subfunction=0x11 path=SYS:PUBLIC last_seen=0x260437f6 desired=1 next_last_seen=0x6686342b entry_id=0x6686342b parent_id=0x00000000 attrs=0x0000 data_len=1024 resource_len=0 offspring=0 long_name=pmgate.sys short_name=pmgate.sys rights=0x9700
|
|
AFP Scan File Info subfunction=0x11 path=SYS:PUBLIC last_seen=0x6686342b desired=1 next_last_seen=0x2d12d99c entry_id=0x2d12d99c parent_id=0x00000000 attrs=0x0000 data_len=1954 resource_len=0 offspring=0 long_name=pmail.bat short_name=pmail.bat rights=0x9700
|
|
```
|
|
|
|
The concrete Entry IDs vary by filesystem metadata. On first contact mars_nwe
|
|
can derive a compatibility id from `stat(2)` and cache it in the versioned
|
|
`org.mars-nwe.afp.entry-id` xattr; later probes of that object return the
|
|
cached id. The verified xattr payloads are versioned as one version byte,
|
|
three reserved bytes, and a big-endian 32-bit AFP Entry ID:
|
|
|
|
```sh
|
|
getfattr -n user.org.mars-nwe.afp.entry-id -e hex /var/mars_nwe/SYS/public/pmdflts.ini
|
|
getfattr -n user.org.mars-nwe.afp.entry-id -e hex /var/mars_nwe/SYS/public/pmgate.sys
|
|
```
|
|
|
|
```text
|
|
user.org.mars-nwe.afp.entry-id=0x010000007b9c42e1
|
|
user.org.mars-nwe.afp.entry-id=0x010000006686342b
|
|
```
|
|
|
|
The scan continuation order is deliberately documented as server directory
|
|
iteration order, not numeric Entry-ID order. `last_seen` identifies the Entry
|
|
ID that was returned by the previous scan call so mars_nwe can skip entries
|
|
until that object is seen and then return the next directory entry. Therefore
|
|
the next returned Entry ID is not guaranteed to be numerically greater than the
|
|
`last_seen` value; in the verified run, `last_seen=0x6686342b` returns
|
|
`pmail.bat` with `entry_id=0x2d12d99c`. The older `0x0a` path intentionally
|
|
shares the same conservative scan implementation so older AFP callers can probe
|
|
the same read-only directory listing semantics before fuller multi-response and
|
|
CNID-backed scans are implemented.
|
|
|
|
If the server was built without the optional Netatalk/libatalk backend, use
|
|
`--allow-invalid-namespace` for the expected negative test. Use
|
|
`--allow-invalid-path` for path-resolution negative tests, and `--allow-empty`
|
|
when a scan continuation is expected to reach the end of the directory.
|
|
|
|
|
|
## AFP Set File Information metadata smoke test
|
|
|
|
`afp_set_file_info_smoke` sends the WebSDK-documented NetWare AFP 2.0 request:
|
|
|
|
```text
|
|
NCP 0x2222/35/16 AFP 2.0 Set File Information
|
|
```
|
|
|
|
The helper exercises two deliberately narrow write-safe AFP metadata subsets:
|
|
the file FinderInfo bitmap (`0x0020`) and the file Attributes bitmap (`0x0001`)
|
|
restricted to the Finder Invisible bit. It sends path-backed raw `VOL:`-style
|
|
requests, writes the 32-byte FinderInfo block to mars_nwe's private
|
|
`org.mars-nwe.afp.finder-info` metadata key, writes the narrow AFP attribute word
|
|
to `org.mars-nwe.afp.attributes`, and immediately verifies the updates through
|
|
AFP 2.0 Get File Information. On Linux the source-level `org.mars-nwe.afp.*` name is stored via the
|
|
portable `user.` xattr namespace by mars_nwe's local xattr wrapper, the same
|
|
pattern Netatalk uses for its `org.netatalk.*` metadata names.
|
|
|
|
Example:
|
|
|
|
```sh
|
|
./tests/linux/afp_set_file_info_smoke \
|
|
-S MARS -U SUPERVISOR -P secret \
|
|
--type TEXT --creator MARS \
|
|
SYS:PUBLIC/pmdflts.ini
|
|
```
|
|
|
|
Verified runtime output:
|
|
|
|
```text
|
|
AFP Set File Info path=SYS:PUBLIC/pmdflts.ini bitmap=0x0020 finder_type=TEXT finder_creator=MARS entry_id=0x23c8787d verified
|
|
```
|
|
|
|
Server diagnostics show the effective resolved volume, the request volume byte,
|
|
the FinderInfo bitmap, and the first eight FinderInfo bytes:
|
|
|
|
```text
|
|
AFP 2.0 Set File Information: vol=0 request_vol=0 entry=0x00000000 mask=0x0020 path='SYS:PUBLIC/pmdflts.ini' finder_type='TEXT' finder_creator='MARS'
|
|
AFP 2.0 Get File Information: vol=0 entry=0x00000000 mask=0xffff path='SYS:PUBLIC/pmdflts.ini' reply_entry=0x23c8787d fallback
|
|
```
|
|
|
|
The `fallback` marker on the first verification Get File Information diagnostic
|
|
still refers to the entry-id source: the returned entry id was derived from the
|
|
stat-backed compatibility path because no CNID or mars_nwe entry-id xattr existed
|
|
yet. The server now caches that derived id in `org.mars-nwe.afp.entry-id`, so a
|
|
second probe of the same file should reuse the xattr-backed id and normally omit
|
|
the `fallback` marker. It does not mean the FinderInfo write was ignored; the
|
|
helper verifies the written FinderInfo through the follow-up Get File Information
|
|
reply.
|
|
|
|
Linux xattr checks for the FinderInfo and cached Entry ID look like this:
|
|
|
|
```sh
|
|
getfattr -n user.org.mars-nwe.afp.finder-info -e hex /var/mars_nwe/SYS/public/pmdflts.ini
|
|
getfattr -n user.org.mars-nwe.afp.entry-id -e hex /var/mars_nwe/SYS/public/pmdflts.ini
|
|
```
|
|
|
|
For the verified FinderInfo smoke run, the FinderInfo xattr starts with
|
|
`TEXTMARS`:
|
|
|
|
```text
|
|
user.org.mars-nwe.afp.finder-info=0x544558544d415253000000000000000000000000000000000000000000000000
|
|
```
|
|
|
|
Finder Invisible can be tested without mutating DOS/NetWare mode bits:
|
|
|
|
```sh
|
|
./tests/linux/afp_set_file_info_smoke \
|
|
-S MARS -U SUPERVISOR -P secret \
|
|
--attributes-only --invisible \
|
|
SYS:PUBLIC/pmdflts.ini
|
|
|
|
getfattr -n user.org.mars-nwe.afp.attributes -e hex /var/mars_nwe/SYS/public/pmdflts.ini
|
|
```
|
|
|
|
The xattr payload is versioned. For an invisible file the expected Linux form
|
|
is:
|
|
|
|
```text
|
|
user.org.mars-nwe.afp.attributes=0x01000001
|
|
```
|
|
|
|
Use `--clear-invisible --attributes-only` to clear that bit; the same xattr then
|
|
stores `0x01000000`. All other Set File Information bitmap bits and all other
|
|
AFP attribute bits are intentionally rejected for now. That keeps timestamp,
|
|
DOS/NetWare mode-bit mapping, resource-fork, and Entry-ID-only write semantics
|
|
out of this metadata-only smoke path.
|
|
|
|
If the server was built without the optional Netatalk/libatalk backend, use
|
|
`--allow-invalid-namespace` for the expected negative test. Use
|
|
`--allow-invalid-path` for path-resolution negative tests.
|