Table of Contents

Class LeaseSource

Namespace
Hi.Licenses
Assembly
HiDisp.dll

Internal Use Only. The cloud lease as the licence source of this process. The source is decided once per process: Sentinel mode, the default, is today's behaviour line for line, with hasp behind every gate; lease mode, entered by Use(), answers every gate (Login(AuthFeature), IsLoggedIn(AuthFeature), the native cache checks, the composition and feature queries) from the grants of the last VERIFIED Install(string, int, string) and never calls hasp. The native provider does no file I/O and verifies once per install: the token, its file and the server protocol belong to the cloud lease client in HiNc, which also writes StopReason and CloudStepHint and raises LeaseRestored and TierChanged. Every P/Invoke here is declared on the CoreDll constant: touching this class does not run License's static constructor, so a login host that only installs a lease never starts the licence watchdog. A process without the lease exports in its core (an older core.dll) reads as Sentinel mode from IsActive, State and SecondsLeft, while Use() and Install(string, int, string) throw EntryPointNotFoundException as any P/Invoke would.

public static class LeaseSource
Inheritance
LeaseSource
Inherited Members

Properties

CloudStepHint

Internal Use Only. The account's step quota as the licence server last described it – the verified and stepQuota of the last lease answer that was not a replay (as the lease state file cached them, for a secondary process and at a start), with the installed token's tier – for the wording of a refused machining step: whether the account is verified (the per-play cap of an unverified one), which quota is used up, when it refills and what a verified account would get. Written by the cloud lease client: the holder from the answer, a secondary process and a start from the files; null = unknown (nothing answered yet, or the files of an older client). A plan without a quota (a paid plan) is a hint whose QuotaKind is null. The field is volatile: the writer is the sync loop or a secondary's poll, the reader the machining thread, which reads it once per refusal and keeps what it read, since the client replaces it meanwhile.

public static CloudStepHint CloudStepHint { get; set; }

Property Value

CloudStepHint

IsActive

Internal Use Only. Whether the licence source of this process is the cloud lease: true from a successful Use() on (State is not SentinelMode), false in Sentinel mode.

public static bool IsActive { get; }

Property Value

bool

SecondsLeft

Internal Use Only. The seconds until the installed lease expires, the earlier of its two deadlines: 0 when it is expired or nothing is installed, -1 in Sentinel mode (and in a process whose core has no lease exports).

public static int SecondsLeft { get; }

Property Value

int

State

Internal Use Only. The provider's state: SentinelMode until Use() (and in a process whose core has no lease exports), then None, Valid or Expired from the installs.

public static LeaseState State { get; }

Property Value

LeaseState

Exceptions

InvalidOperationException

The core answered a code this build does not know.

StopReason

Internal Use Only. Why the lease stopped granting, for the pause message of a refused machining step: null (no stop, or the lease ran out while the licence server could not be reached), “offline”, “sign-in-required”, “in-use-elsewhere”, “license-expired” or “consent-required” – the licence server's error code (the last: the server serves the lease again only after the account agreed to the current terms, which the sign-in page asks at the next start). Written by the cloud lease client (HiNc), which clears it on an Install(string, int, string) that returns Valid; read by the machining runner (HiMech) when the native step consume answers that the lease is expired. The field is volatile: the writer is the sync loop, the reader the machining thread.

public static string StopReason { get; set; }

Property Value

string

Methods

Install(string, int, string)

Internal Use Only. Verifies a lease token (an ES256 JWS under a key pinned in the core) and installs it: its grants and caps are in force from a Valid or Expired result on, and its step grant (sgrant; none = no grant limit) replaces the previous lease's in LeaseStepsLeft, so the cloud lease client tightens it to the chain's arithmetic after every install (TightenLeaseSteps(long)); a negative result leaves the previous lease, if any, in force. The grace is min(remainingSeconds, exp - iat, 3600) seconds from now on both the monotonic and the wall clock, the earlier deadline counting.

public static LeaseInstallResult Install(string jws, int remainingSeconds, string midB64u)

Parameters

jws string

The lease token as the licence server sent it (three base64url parts).

remainingSeconds int

What the server's clock says is left of the token: exp minus the server's date; 0 or less installs it expired.

midB64u string

This device's machine id, base64url (32 bytes decoded); the token's mid must equal it.

Returns

LeaseInstallResult

The native code as a LeaseInstallResult.

Exceptions

ArgumentNullException

jws or midB64u is null.

InvalidOperationException

The core answered a code this build does not know.

Message(LeaseInstallResult)

Internal Use Only. One sentence per LeaseInstallResult, for logs and the licence dialog's last error.

public static string Message(LeaseInstallResult result)

Parameters

result LeaseInstallResult

The result to describe.

Returns

string

The sentence, without a full stop.

RaiseLeaseRestored()

Internal Use Only. Raises LeaseRestored: the cloud lease client calls it once per install that moved the state from expired to valid, or brought steps to a used-up step grant. Every subscriber runs, each on its own: a subscriber that throws skips none of the others, and its exception never reaches the raiser – the sync loop that raises keeps renewing – but comes back as the return value for the caller to log.

public static AggregateException RaiseLeaseRestored()

Returns

AggregateException

The subscribers' exceptions, one inner exception per subscriber that threw, in subscription order; null when none threw or none is subscribed.

RaiseTierChanged(LeaseTierChange)

Internal Use Only. Raises TierChanged: the cloud lease client calls it once per install whose tier differs from the previous install's. Every subscriber runs, each on its own: a subscriber that throws skips none of the others, and its exception never reaches the raiser – the sync loop keeps renewing – but comes back as the return value for the caller to log.

public static AggregateException RaiseTierChanged(LeaseTierChange change)

Parameters

change LeaseTierChange

The old and the new tier with the new lease's caps and quota.

Returns

AggregateException

The subscribers' exceptions, one inner exception per subscriber that threw, in subscription order; null when none threw or none is subscribed.

Exceptions

ArgumentNullException

change is null.

Use()

Internal Use Only. Switches the licence source of this process to the cloud lease. Idempotent once switched. Nothing is granted until an Install(string, int, string) verifies a token; a machining call in between would meet the native no-licence abort, so the caller installs (or refuses to start) before any licence gate is read.

public static void Use()

Exceptions

InvalidOperationException

A Sentinel login already happened in this process: the source was decided as Sentinel.

PlatformNotSupportedException

This build of the core has no lease verifier (the Linux core).

Events

LeaseRestored

Internal Use Only. Raised through RaiseLeaseRestored() by the cloud lease client – the holder or a secondary process of the same PC – after an Install(string, int, string) that moved State from Expired to Valid, and after a valid install that brought steps to a step grant that was used up (LeaseStepsLeft 0 before the install, not 0 after it and the client's tighten): a run the lease paused resumes on it (HiNc's project service), a user's own pause never. The event is static and lives as long as the process: a subscriber that gets disposed unsubscribes in its Dispose, or the event keeps the instance alive and calls it, disposed, at the next restore. Subscribers run on the raiser's thread – the client's sync loop or a secondary's poll, a background task – never on a UI thread.

public static event Action LeaseRestored

Event Type

Action

TierChanged

Internal Use Only. Raised through RaiseTierChanged(LeaseTierChange) by the cloud lease client after an Install(string, int, string) whose token carries another plan tier than the token installed before it in this process – the plan changed on the server: an upgrade, a trial that became a paid licence, a licence that ended and the account's next one took over – with the old and the new tier and the new lease's caps and quota (LeaseTierChange): HiNc's project service says CloudLease–TierChanged on it. The same rules as LeaseRestored: static and process-long, so a subscriber that gets disposed unsubscribes in its Dispose; raised on the client's thread – the sync loop or a secondary's poll – never on a UI thread.

public static event Action<LeaseTierChange> TierChanged

Event Type

Action<LeaseTierChange>