|
ProtoCore v1.0.16
Deterministic, zero-heap network stack for embedded targets
|
WebDAV wire format (RFC 4918): method classification, header parsing, and the 207 Multi-Status XML builder. More...
#include "protocore_config.h"Go to the source code of this file.
Classes | |
| struct | DavLock |
| One active lock (RFC 4918 §6.4). More... | |
| struct | DavLockTable |
| The server-global lock table (one instance, not per-connection). More... | |
| struct | WebdavNs |
| Dispatch table. Addressed by offset, so the layout is asserted below. More... | |
Macros | |
| #define | PROTOCORE_DAV_DEPTH_INFINITY 0x7fffffff |
| Depth: infinity sentinel (a lone constant). | |
| #define | PROTOCORE_DAV_LOCK_MAX 8 |
| Maximum concurrent locks (fixed - a small structural bound, not a per-board tunable). | |
| #define | PROTOCORE_DAV_LOCK_PATH_MAX 128 |
| Maximum locked-path length, including the NUL. | |
| #define | PROTOCORE_DAV_LOCK_TOKEN_MAX 48 |
| Maximum lock-token length, including the NUL (e.g. "opaquelocktoken:xxxxxxxx-pc"). | |
Typedefs | |
| typedef enum PROTO_ENUM_PACKED | WebDavMethod |
| WebDAV request methods recognized by the server. | |
Enumerations | |
| enum | PROTO_ENUM_PACKED { DAV_M_OPTIONS , DAV_M_GET , DAV_M_HEAD , DAV_M_PUT , DAV_M_DELETE , DAV_M_PROPFIND , DAV_M_PROPPATCH , DAV_M_MKCOL , DAV_M_COPY , DAV_M_MOVE , DAV_M_LOCK , DAV_M_UNLOCK , DAV_M_UNSUPPORTED } |
| WebDAV request methods recognized by the server. More... | |
Functions | |
| PROTOCORE_NS_LAYOUT (WebdavNs, method, depth, xml_escape, dest_path, ms_begin, ms_entry, ms_end, proppatch_ms, lock_init, lock_acquire, lock_sweep, lock_refresh, lock_find, lock_release, lock_can_write, if_token) | |
| WebDavMethod | protocore_webdav_method (uint8_t *work, const char *m) |
| Classify an HTTP method token (e.g. "PROPFIND") into a WebDavMethod. | |
| int | protocore_webdav_depth (uint8_t *work, const char *depth_hdr, int dflt) |
| Parse a Depth header value ("0", "1", or "infinity"). | |
| size_t | protocore_webdav_xml_escape (uint8_t *work, char *dst, size_t cap, const char *src) |
XML-escape src into dst (&, <, >, ", ‘’`). | |
| proto_bool | protocore_webdav_dest_path (uint8_t *work, const char *destination, char *out, size_t cap) |
| Extract and percent-decode the path of a Destination header. . | |
| size_t | protocore_webdav_ms_begin (uint8_t *work, char *buf, size_t cap, size_t len) |
| Write the XML prolog and the open <multistatus> element. | |
| size_t | protocore_webdav_ms_entry (uint8_t *work, char *buf, size_t cap, size_t len, const char *href, proto_bool is_collection, uint32_t size, const char *rfc1123_mtime, const char *content_type) |
| Append one <response> describing a resource. | |
| size_t | protocore_webdav_ms_end (uint8_t *work, char *buf, size_t cap, size_t len) |
| Close the <multistatus> element. | |
| size_t | protocore_webdav_proppatch_ms (uint8_t *work, char *buf, size_t cap, const char *href, const char *body, size_t body_len) |
| Build a complete 207 Multi-Status body answering a PROPPATCH. The . | |
| void | protocore_webdav_lock_init (uint8_t *work, DavLockTable *t) |
| Reset a lock table (no locks held). | |
| const DavLock * | protocore_webdav_lock_acquire (uint8_t *work, DavLockTable *t, const char *path, const char *token, proto_bool exclusive, proto_bool depth_infinity, uint32_t expiry_s) |
| Acquire a lock on path with the caller-supplied token (RFC 4918 . | |
| size_t | protocore_webdav_lock_sweep (uint8_t *work, DavLockTable *t, uint32_t now_s) |
| Expire and drop every lock whose timeout has passed (RFC 4918 . | |
| const DavLock * | protocore_webdav_lock_refresh (uint8_t *work, DavLockTable *t, const char *token, uint32_t new_expiry_s) |
| Refresh a held lock's timeout to new_expiry_s, keyed by token (a . | |
| const DavLock * | protocore_webdav_lock_find (uint8_t *work, const DavLockTable *t, const char *path) |
| Find a lock covering path: one on path itself, or a Depth-infinity . | |
| proto_bool | protocore_webdav_lock_release (uint8_t *work, DavLockTable *t, const char *token) |
| Release the lock whose token equals token (UNLOCK). true if one was . | |
| proto_bool | protocore_webdav_lock_can_write (uint8_t *work, const DavLockTable *t, const char *path, const char *presented_token) |
| May a write to path proceed given the token the request presented . | |
| proto_bool | protocore_webdav_if_token (uint8_t *work, const char *if_header, char *out, size_t cap) |
| Extract the first lock token from an If header value (RFC 4918 . | |
Variables | |
| PROTOCORE_NS WebdavNs Webdav | PROTOCORE_UNUSED |
| Module namespace. | |
WebDAV wire format (RFC 4918): method classification, header parsing, and the 207 Multi-Status XML builder.
Mirrors the CoAP/SNMP split: this header declares the pure, host-testable core (no sockets, no filesystem - unit-tested in env:native_webdav). The filesystem-backed request handling (PROPFIND directory walk, PUT/MKCOL/DELETE/ COPY/MOVE, GET via the file-serving path) lives in server/io/webdav_handler.h and runs only on a build with a real filesystem.
Scope: class 1 (PROPFIND Depth 0/1, PROPPATCH, PUT, DELETE, MKCOL, COPY, MOVE) plus OPTIONS and class 2 LOCK/UNLOCK, now enforced by a small lock table (see the lock manager below): a locked resource rejects a write that does not present the matching token in its If header (423 Locked). PROPPATCH is answered 207 with every requested property refused 403 (read-only live properties, no dead-property store). The filesystem-backed handler streams a PUT body straight to the file (PC's stream-body hook), so uploads are not bounded by BODY_BUF_SIZE.
work is bytes the CALLER holds. This module reads none of them: it carries nothing between calls, so there is no state to keep and nothing to wipe. The parameter is there so a caller drives every namespace the same way.
Definition in file webdav.h.
| #define PROTOCORE_DAV_DEPTH_INFINITY 0x7fffffff |
| #define PROTOCORE_DAV_LOCK_MAX 8 |
| #define PROTOCORE_DAV_LOCK_PATH_MAX 128 |
| #define PROTOCORE_DAV_LOCK_TOKEN_MAX 48 |
| typedef enum PROTO_ENUM_PACKED WebDavMethod |
WebDAV request methods recognized by the server.
| enum PROTO_ENUM_PACKED |
| PROTOCORE_NS_LAYOUT | ( | WebdavNs | , |
| method | , | ||
| depth | , | ||
| xml_escape | , | ||
| dest_path | , | ||
| ms_begin | , | ||
| ms_entry | , | ||
| ms_end | , | ||
| proppatch_ms | , | ||
| lock_init | , | ||
| lock_acquire | , | ||
| lock_sweep | , | ||
| lock_refresh | , | ||
| lock_find | , | ||
| lock_release | , | ||
| lock_can_write | , | ||
| if_token | |||
| ) |
| WebDavMethod protocore_webdav_method | ( | uint8_t * | work, |
| const char * | m | ||
| ) |
Classify an HTTP method token (e.g. "PROPFIND") into a WebDavMethod.
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| m | M |
| int protocore_webdav_depth | ( | uint8_t * | work, |
| const char * | depth_hdr, | ||
| int | dflt | ||
| ) |
Parse a Depth header value ("0", "1", or "infinity").
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| depth_hdr | Depth hdr |
| dflt | Dflt |
| size_t protocore_webdav_xml_escape | ( | uint8_t * | work, |
| char * | dst, | ||
| size_t | cap, | ||
| const char * | src | ||
| ) |
XML-escape src into dst (&, <, >, ", ‘’`).
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| dst | Dst |
| cap | Cap |
| src | Src |
| proto_bool protocore_webdav_dest_path | ( | uint8_t * | work, |
| const char * | destination, | ||
| char * | out, | ||
| size_t | cap | ||
| ) |
Extract and percent-decode the path of a Destination header. .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| destination | Destination |
| out | Out |
| cap | Cap |
| size_t protocore_webdav_ms_begin | ( | uint8_t * | work, |
| char * | buf, | ||
| size_t | cap, | ||
| size_t | len | ||
| ) |
Write the XML prolog and the open <multistatus> element.
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| buf | Buf |
| cap | Cap |
| len | Len |
| size_t protocore_webdav_ms_entry | ( | uint8_t * | work, |
| char * | buf, | ||
| size_t | cap, | ||
| size_t | len, | ||
| const char * | href, | ||
| proto_bool | is_collection, | ||
| uint32_t | size, | ||
| const char * | rfc1123_mtime, | ||
| const char * | content_type | ||
| ) |
Append one <response> describing a resource.
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| buf | Buf |
| cap | Cap |
| len | Len |
| href | the resource's URL path (XML-escaped here) |
| is_collection | true for a directory (emits <collection>) |
| size | content length (files only) |
| rfc1123_mtime | Last-Modified string, or "" to omit |
| content_type | MIME type (files only), or "" to omit |
| size_t protocore_webdav_ms_end | ( | uint8_t * | work, |
| char * | buf, | ||
| size_t | cap, | ||
| size_t | len | ||
| ) |
Close the <multistatus> element.
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| buf | Buf |
| cap | Cap |
| len | Len |
| size_t protocore_webdav_proppatch_ms | ( | uint8_t * | work, |
| char * | buf, | ||
| size_t | cap, | ||
| const char * | href, | ||
| const char * | body, | ||
| size_t | body_len | ||
| ) |
Build a complete 207 Multi-Status body answering a PROPPATCH. The .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| buf | destination buffer (whole document, NUL-terminated) |
| cap | buffer capacity |
| href | the resource path (XML-escaped here) |
| body | the PROPPATCH request body (not required to be NUL-terminated) |
| body_len | length of body |
| void protocore_webdav_lock_init | ( | uint8_t * | work, |
| DavLockTable * | t | ||
| ) |
Reset a lock table (no locks held).
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| const DavLock * protocore_webdav_lock_acquire | ( | uint8_t * | work, |
| DavLockTable * | t, | ||
| const char * | path, | ||
| const char * | token, | ||
| proto_bool | exclusive, | ||
| proto_bool | depth_infinity, | ||
| uint32_t | expiry_s | ||
| ) |
Acquire a lock on path with the caller-supplied token (RFC 4918 .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| path | Path |
| token | Token |
| exclusive | Exclusive |
| depth_infinity | Depth infinity |
| expiry_s | the monotonic second the lock expires (0 = no timeout); protocore_dav_lock_sweep drops a |
| size_t protocore_webdav_lock_sweep | ( | uint8_t * | work, |
| DavLockTable * | t, | ||
| uint32_t | now_s | ||
| ) |
Expire and drop every lock whose timeout has passed (RFC 4918 .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| now_s | the caller's current monotonic second |
| const DavLock * protocore_webdav_lock_refresh | ( | uint8_t * | work, |
| DavLockTable * | t, | ||
| const char * | token, | ||
| uint32_t | new_expiry_s | ||
| ) |
Refresh a held lock's timeout to new_expiry_s, keyed by token (a .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| token | Token |
| new_expiry_s | New expiry s |
| const DavLock * protocore_webdav_lock_find | ( | uint8_t * | work, |
| const DavLockTable * | t, | ||
| const char * | path | ||
| ) |
Find a lock covering path: one on path itself, or a Depth-infinity .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| path | Path |
| proto_bool protocore_webdav_lock_release | ( | uint8_t * | work, |
| DavLockTable * | t, | ||
| const char * | token | ||
| ) |
Release the lock whose token equals token (UNLOCK). true if one was .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| token | Token |
| proto_bool protocore_webdav_lock_can_write | ( | uint8_t * | work, |
| const DavLockTable * | t, | ||
| const char * | path, | ||
| const char * | presented_token | ||
| ) |
May a write to path proceed given the token the request presented .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| t | T |
| path | Path |
| presented_token | Presented token |
| proto_bool protocore_webdav_if_token | ( | uint8_t * | work, |
| const char * | if_header, | ||
| char * | out, | ||
| size_t | cap | ||
| ) |
Extract the first lock token from an If header value (RFC 4918 .
| work | PROTOCORE_WEBDAV_BORROW bytes the caller took. Not held past the call. |
| if_header | If header |
| out | Out |
| cap | Cap |
| PROTOCORE_NS WebdavNs Webdav PROTOCORE_UNUSED |
Module namespace.