Skip to main content

DiagnosticsLayer

Struct DiagnosticsLayer 

Source
pub struct DiagnosticsLayer { /* private fields */ }
Expand description

Subsystem-wide diagnostics state.

Reads are wait-free. Self::diagnostics_for, Self::line_severity, Self::diagnostics_on_line, and the count helpers all go through one ArcSwap::load. The renderer’s per-line line_severity(uri, line) call (50 lines × 60 Hz = 3000/s on the render thread per the audit) no longer takes a mutex.

Writes serialise on a brief mutex. Self::apply and the clear_* methods take a small write-side lock just long enough to clone the current snapshot, mutate it, recompute the affected URI’s by_uri entry, and ArcSwap::store it. Writers don’t block readers (ArcSwap is RCU-flavoured); two concurrent writers serialise via the write lock.

Cloneable; every clone shares the same ArcSwap cell + the same write lock (so the layer behaves as one logical state across actor pumps).

Implementations§

Source§

impl DiagnosticsLayer

Source

pub fn new(logger: LspLogger) -> Self

Build an empty layer. The logger is used for “dropped stale” telemetry.

Source

pub fn set_wake(&self, wake: Arc<Notify>)

Install the render-wake Notify (the editor’s async_landed). Boot calls this once after the layer is built; every subsequent apply fires it so a pushed diagnostic change repaints off-keystroke. Idempotent (last wins); shared across all clones.

Source

pub fn snapshot_revision(&self) -> usize

§12 paint gate: a cheap change-token for the current snapshot.

Every Self::apply swaps a fresh Arc<DiagnosticsSnapshot> into the cell, so the snapshot’s pointer address is a precise, allocation-free “did the diagnostics change” signal — stable while unchanged, distinct after any push (including the CLEAR when an error is fixed). build_render_state folds this into RenderState::paint_revision so a pushed diagnostics change (which is an overlay, deliberately excluded from the cells MatrixVersion — see lattice-cells/src/version.rs) still requests an off-keystroke paint. Without it, the gutter / underline / inline-summary would update in the snapshot but not repaint until the next keypress (the “undo → diagnostic disappears” report).

Source

pub fn apply(&self, event: DiagnosticEvent)

Apply one DiagnosticEvent. Drops stale events; clears state on empty diagnostics; otherwise replaces the (uri, server_id) entry. Single-snapshot publish at the end: readers either see the prior state or the post-write state, never a torn intermediate.

Source

pub fn diagnostics_for(&self, uri: &Uri) -> Vec<Diagnostic>

All diagnostics for a URI, merged across every server that’s attached to it. Returns an empty Vec when there are none.

Source

pub fn diagnostics_arc(&self, uri: &Uri) -> Option<Arc<[Diagnostic]>>

Wait-free Arc<[Diagnostic]> borrow of the merged diagnostics for uri. Preferred on the hot path (renderer / picker fan-out) – avoids the per-call Vec allocation that diagnostics_for does.

Source

pub fn diagnostics_on_line(&self, uri: &Uri, line: u32) -> Vec<Diagnostic>

Diagnostics that overlap line. Half-open at the end: a range ending on line N column 0 covers lines start.line ..= end.line - 1 (LSP convention). To match the gutter glyph behaviour we still surface diagnostics whose end is exactly at line N column 0 if N is the current line – callers prefer “show, don’t hide” for edge cases.

Source

pub fn line_severity(&self, uri: &Uri, line: u32) -> Option<DiagnosticSeverity>

Most severe severity present on line, or None if no diagnostic touches it. “Most severe” = lowest enum tag (Error == 1 < Warning == 2 < Information == 3 < Hint == 4). Used by the gutter glyph provider; runs once per visible line per frame, so this path stays allocation-free (filters the borrowed slice in place).

Source

pub fn inline_line_summary( &self, uri: &Uri, line: u32, min_rank: u8, ) -> Option<InlineDiagnosticSummary>

L4a (lsp-architecture.md §15): a one-line end-of-line summary of the qualifying diagnostics on line of uri, for the inline cursor-line presentation. A diagnostic qualifies when its severity rank is <= min_rank (as severe or more severe than the configured floor); unknown-severity diagnostics map to rank 4 and so only qualify when min_rank is itself 4. Returns None when nothing on the line qualifies.

The text is the most-severe qualifying diagnostic’s message (first line only, truncated to [INLINE_SUMMARY_MAX_CHARS] with an ellipsis) plus +N when N further qualifying diagnostics share the line. Most-severe = lowest rank; ties resolve to the earliest by (line, character) (the merged list is already so ordered). Wait-free: one snapshot load + a single pass over the URI’s diagnostics, so it stays on the cheap side of the actor thread’s publish path.

Source

pub fn iter_uris(&self) -> Vec<Uri>

Every URI with at least one stored diagnostic. Sorted alphabetically (stable for the :diagnostics buffer view).

Source

pub fn snapshot(&self) -> Vec<(Uri, Vec<Diagnostic>)>

Snapshot of every (uri, merged-list) pair. Backs the :diagnostics buffer’s body. URIs sorted; diagnostics within a URI ordered by (line, column).

Source

pub fn count(&self) -> usize

Total diagnostic count across every URI / server. Used by the modeline summary (“rust: 3 errors, 2 warnings”).

Source

pub fn severity_counts(&self) -> SeverityCounts

Severity tally across every URI: (errors, warnings, info, hints). Modeline / status segment consumer.

Source

pub fn clear(&self)

Drop everything. Used by :diag-clear and tests.

Source

pub fn clear_uri(&self, uri: &Uri)

Drop every entry for a URI (across all servers). Used when a buffer closes – the diagnostics are no longer relevant since we won’t render them.

Source

pub fn clear_server(&self, server_id: &Arc<str>)

Drop every entry for one server – used when a server dies / is detached.

Trait Implementations§

Source§

impl Clone for DiagnosticsLayer

Source§

fn clone(&self) -> DiagnosticsLayer

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for DiagnosticsLayer

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl Default for DiagnosticsLayer

Source§

fn default() -> DiagnosticsLayer

Returns the “default value” for a type. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

§

impl<T> Instrument for T

§

fn instrument(self, span: Span) -> Instrumented<Self> ⓘ

Instruments this type with the provided [Span], returning an Instrumented wrapper. Read more
§

fn in_current_span(self) -> Instrumented<Self> ⓘ

Instruments this type with the current Span, returning an Instrumented wrapper. Read more
Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
§

impl<T> Pointable for T

§

const ALIGN: usize

The alignment of pointer.
§

type Init = T

The type for initializers.
§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
§

impl<T> WithSubscriber for T

§

fn with_subscriber<S>(self, subscriber: S) -> WithDispatch<Self> ⓘ
where S: Into<Dispatch>,

Attaches the provided Subscriber to this type, returning a [WithDispatch] wrapper. Read more
§

fn with_current_subscriber(self) -> WithDispatch<Self> ⓘ

Attaches the current default Subscriber to this type, returning a [WithDispatch] wrapper. Read more