Keldrin Remote Portal V1.0.34
Derived from upstream DSM Remote Portal V1.0.7

This is a program-only deployment ZIP. It contains no store.php, users, API
keys, passwords, command history, runtime files, or real external target.

DEPLOYMENT
1. Deploy to a fresh /keldrin directory. Do not copy data from an existing
   production portal deployment. Complete setup over HTTPS and keep the
   generated API key private.
2. Ensure the web server denies all direct access to data/. The supplied
   data/.htaccess does this for Apache; configure the equivalent on other
   servers.
3. External socket tests fail closed until the operator creates:

       data/keldrin-external-targets.php

   Copy data/keldrin-external-targets.example.php to that exact filename and
   preserve its first PHP guard line. Map the exact Site ID created during
   setup to the router's current real public IPv4. The example documentation
   address is intentionally not a usable public target. Keep the policy file
   private. If the public IPv4 changes, update this policy before testing.
4. When Cloudflare is used, bypass interactive challenge/caching only for the
   exact /keldrin/api/bridge.php path and prevent direct access to the origin.
5. Future program updates are accepted only as exact schema-2 Keldrin Portal
   packages signed by the configured offline ECDSA P-256 key. Browser admins
   use Portal Update over trusted HTTPS; native Keldrin uses the explicit
   authenticated maintenance endpoint. Neither path accepts arbitrary files,
   PHP, URLs, unsigned ZIPs, downgrades, or packages that contain private state.
6. Keep the offline signing private key outside the deployment and repository.
   The embedded trust root is public-key material only. Configure
   data/keldrin-trusted-proxies.php with exact proxy IPs only when trusted
   reverse-proxy HTTPS termination is required; forwarded headers otherwise
   fail closed.

COMPATIBILITY
- HMAC header names (X-DSM-*), payload/response JSON names, command actions,
  package type, and endpoint paths remain Portal 1.0.7 wire-compatible. The
  Keldrin Portal release version is independently tracked as 1.0.34.
- DSM internal PHP constant and HTML meta names are intentionally unchanged.
- The portal's service-worker cache is isolated by deployment scope and only
  removes obsolete caches bearing its own Keldrin scope prefix.
- Protocol-v1 public PHP front controllers and recovery/bootstrap files are
  immutable during online updates. Mutable libraries and assets activate only
  while the exclusive update lock is held, with journalled rollback.

KELDRIN SCHEDULE SEMANTICS
Schedule Override controls only Keldrin's daily host-sleep request at the
configured local time reported by Keldrin. Administrators choose 1, 2, 4, 24,
or 48 hours. Timed overrides expire automatically. It does not stop or start game servers, change Windows
inactivity sleep, change wake-on-LAN, or skip updates. Disabling or expiry
never applies a missed sleep request retroactively.

EXTERNAL TEST BOUNDARY
Every PHP socket test is restricted to the exact public IPv4 mapped to the
authenticated Site ID in the server-side policy, and Keldrin's submitted
PublicIPv4 must match it. The client may choose a reviewed port/protocol check,
but it cannot turn this portal into a scanner for arbitrary Internet hosts.