# Gateway Licensing

## Overview

LMC Exporter 0.18.x supports two licensing modes:

<table><caption class="sr-only">Overview</caption><thead><tr><th scope="col">Mode</th><th scope="col">Configuration</th><th scope="col">Behavior</th></tr></thead><tbody><tr><td>Local file</td><td><code>license_mode = "local_file"</code></td><td>Validates the configured <code>license_file</code>. This is the default.</td></tr><tr><td>Gateway</td><td><code>license_mode = "gateway"</code></td><td>Acquires and renews a Gateway lease for the complete configured workload.</td></tr></tbody></table>

In Gateway mode, the exporter must receive the full requested entitlement before it creates the LMC shared-memory pool, starts workers, or opens the HTTP listener. `license_file` is not used in this mode.

NotePlatform support

Gateway mode is qualified for Enterprise Linux 8 and 9 on x86\_64. Local-file licensing retains the wider exporter platform support.

## Basic Configuration

This example uses one HTTPS Gateway with mutual TLS and two exporter targets:

```
license_mode = "gateway"
gateway_endpoints = ["https://gateway.example:8443"]
gateway_auth_mode = "mtls"
gateway_tls_ca_file = "/etc/lmc-exporter/gateway-ca.pem"
gateway_tls_cert_file = "/etc/lmc-exporter/client.pem"
gateway_tls_key_file = "/etc/lmc-exporter/client-key.pem"
gateway_state_directory = "/var/lib/lmc-exporter"

[[targets]]
app = "ads"
server_key = "82"
component_instance_id = "ads-primary"

[[targets]]
app = "adh"
server_key = "999"
component_instance_id = "adh-primary"
```

Gateway settings can appear at the TOML root or in `[settings]`. CLI options override TOML values. CLI names replace underscores with hyphens; for example, `gateway_request_timeout_ms` becomes `--gateway-request-timeout-ms`.

## Gateway Settings

<table><caption class="sr-only">Gateway Settings</caption><thead><tr><th scope="col">Key</th><th scope="col">Default</th><th scope="col">Description</th></tr></thead><tbody><tr><td><code>license_mode</code></td><td><code>"local_file"</code></td><td>Use <code>local_file</code> or <code>gateway</code>.</td></tr><tr><td><code>gateway_endpoints</code></td><td><code>[]</code></td><td>One or two distinct Gateway URLs with the same <code>http</code> or <code>https</code> scheme. Repeat <code>--gateway-endpoint</code> on the CLI.</td></tr><tr><td><code>gateway_auth_mode</code></td><td><code>"none"</code></td><td>Authentication profile: <code>none</code>, <code>bearer</code>, or <code>mtls</code>.</td></tr><tr><td><code>gateway_bearer_token_file</code></td><td><code>""</code></td><td>Bearer token file, required only for bearer authentication.</td></tr><tr><td><code>gateway_tls_ca_file</code></td><td><code>""</code></td><td>Optional CA bundle for HTTPS. System trust is used when omitted.</td></tr><tr><td><code>gateway_tls_cert_file</code></td><td><code>""</code></td><td>Client certificate and intermediate chain, required for mTLS.</td></tr><tr><td><code>gateway_tls_key_file</code></td><td><code>""</code></td><td>Matching unencrypted private key, required for mTLS.</td></tr><tr><td><code>gateway_state_directory</code></td><td><code>""</code></td><td>Required absolute path for the persisted installation identity.</td></tr><tr><td><code>gateway_connect_timeout_ms</code></td><td><code>2000</code></td><td>Connection timeout from <code>1</code> to <code>60000</code>; cannot exceed the request timeout.</td></tr><tr><td><code>gateway_request_timeout_ms</code></td><td><code>5000</code></td><td>Per-endpoint request timeout from <code>1</code> to <code>60000</code>.</td></tr><tr><td><code>gateway_startup_timeout_ms</code></td><td><code>30000</code></td><td>Total acquisition budget from <code>1</code> to <code>300000</code>.</td></tr><tr><td><code>gateway_retry_max_attempts</code></td><td><code>3</code></td><td>Retry rounds from <code>1</code> to <code>10</code>; each round can try both endpoints.</td></tr><tr><td><code>gateway_retry_base_delay_ms</code></td><td><code>100</code></td><td>Initial retry delay from <code>1</code> to <code>60000</code>.</td></tr><tr><td><code>gateway_retry_max_delay_ms</code></td><td><code>2000</code></td><td>Maximum retry delay from <code>1</code> to <code>60000</code>.</td></tr><tr><td><code>gateway_renew_base_delay_ms</code></td><td><code>1000</code></td><td>Initial renewal retry delay from <code>1</code> to <code>60000</code>.</td></tr><tr><td><code>gateway_renew_max_delay_ms</code></td><td><code>30000</code></td><td>Maximum renewal retry delay from <code>1</code> to <code>60000</code>.</td></tr><tr><td><code>gateway_release_timeout_ms</code></td><td><code>5000</code></td><td>Total shutdown and release budget from <code>1</code> to <code>30000</code>.</td></tr><tr><td><code>gateway_requested_ttl_seconds</code></td><td><code>0</code></td><td>Requested lease lifetime; <code>0</code> uses the Gateway default. The returned expiry remains authoritative.</td></tr></tbody></table>

Supported authentication profiles are HTTP with `none` or `bearer`, and HTTPS with `none` or `mtls`. A bearer token must not be placed directly on the command line; configure the token file instead. Credential files are loaded at startup, so rotation requires a restart.

## Component Identities and Entitlement Counts

Every selected target needs a `component_instance_id` in Gateway mode. This value identifies the licensed component and is separate from the target’s discovery `instance` selector.

Component IDs are case-sensitive, contain 1–128 ASCII characters, and must match `[A-Za-z0-9][A-Za-z0-9._:-]{0,127}`. Supported application names are `adh`, `ads`, `ats`, and `rtc`.

The exporter requests one unit for each distinct `(app, component_instance_id)` pair:

-   Aliases that represent the same component can share an ID and count as one unit.
-   Different component instances must use different IDs.
-   Configured targets count even when their source is temporarily unavailable.
-   The same ID used by different application types counts once for each application.

For a single global `server_key`, set `component_instance_id`. For multiple global keys, provide IDs in the same order:

```
app = "ads"
server_keys = ["82", "456"]
component_instance_ids = ["ads-primary", "ads-secondary"]
```

On the CLI, repeat `--server-key` and `--component-instance-id` in corresponding order. Embedded `[[targets]]` entries require their own `component_instance_id`; do not combine target-level IDs with the global ID settings.

## Persisted Installation Identity

`gateway_state_directory` stores a generated installation UUID in `installation-id`. The exporter reuses this identity after restarts so Gateway can reconcile the installation and its workload.

Prepare the directory as follows:

-   Use an absolute path owned by the exporter service account.
-   Set directory permissions to `0700`.
-   Place it on a local persistent filesystem that supports file locking, atomic publication, and `fsync`.
-   Give each installation its own directory. Do not copy or share an installation identity between hosts.

The exporter creates `installation-id` with mode `0600` and holds `installation-id.lock` for its lifetime. A second process using the same state directory fails to start. Unsafe permissions, symlinks, malformed identity data, or storage and lock failures also block startup; the exporter does not replace an invalid identity automatically.

## Lease and Shutdown Behavior

After acquisition, the exporter renews the lease in the background. Temporary renewal failures do not interrupt collection while the existing lease remains valid.

If the lease expires or Gateway establishes entitlement loss, the exporter permanently closes collection and output admission and exits with status `1`. A later response cannot reopen the process. On a normal `SIGINT` or `SIGTERM`, the exporter stops output and attempts to release a valid lease within `gateway_release_timeout_ms`.

NoteExpired or lost leases are not released

The exporter does not send a release after entitlement loss or lease expiry, including when the lease expires while shutdown threads are joining. A valid release is bounded by both the configured cleanup budget and the lease’s remaining lifetime.

Gateway failover and retries preserve the logical request across configured endpoints. All endpoint URLs must use the same scheme. Gateway access remains an online requirement; the persisted installation ID is not an offline lease.

## Security Guidance

-   Bearer token and private-key files must be regular files owned by the service user or root, with no group or other permissions. Modes `0400` and `0600` are suitable.
-   Use TLS 1.2 or later for HTTPS deployments.
-   Configure `gateway_tls_ca_file` when the system trust store does not contain the deployment CA.
-   Do not include credentials, query strings, or fragments in Gateway endpoint URLs.
-   Restart the exporter after changing credentials, endpoints, targets, or entitlement quantities.
