JanDeDobbeleer/oh-my-posh · warning

async timed out

Error message

async timed out

What it means

awaitAsync polls the WinRT async operation status on a fixed interval until a deadline (smtcAsyncTimeout) expires. If the operation neither completes, nor is cancelled, nor errors before the deadline, the library stops waiting and returns this timeout error rather than blocking prompt rendering indefinitely.

Source

Thrown at src/runtime/smtc_windows.go:213

	if hr != 0 {
		return fmt.Errorf("QueryInterface IAsyncInfo: 0x%08x", hr)
	}
	defer comRelease(asyncInfo)

	deadline := time.Now().Add(smtcAsyncTimeout)
	for {
		var status uint32
		comCall(asyncInfo, asyncInfoGetStatus, uintptr(unsafe.Pointer(&status)))
		switch status {
		case asyncStatusCompleted:
			return nil
		case asyncStatusCanceled:
			return errors.New("async cancelled")
		case asyncStatusError:
			return errors.New("async failed")
		}
		if time.Now().After(deadline) {
			return errors.New("async timed out")
		}
		time.Sleep(smtcAsyncPollInterval)
	}
}

func queryMediaPlayer(player string) (*MediaInfo, error) {
	// RoInitialize / RoUninitialize update thread-local state, so we have to
	// pin the goroutine to one OS thread for the duration of this call.
	goruntime.LockOSThread()
	defer goruntime.UnlockOSThread()

	// RO_INIT_MULTITHREADED = 1. S_FALSE (1) means already initialised on
	// this thread, which is fine — we still pair with RoUninitialize.
	hr, _, _ := procRoInitialize.Call(1)
	if hr != 0 && hr != 1 {
		return nil, fmt.Errorf("RoInitialize: 0x%08x", hr)
	}
	defer func() { _, _, _ = procRoUninitialize.Call() }()

View on GitHub (pinned to 0976794618)

Solutions

  1. Retry on the next prompt render — usually a transient delay.
  2. Disable the media/spotify segment if timeouts happen frequently on your machine.
  3. Close unresponsive media apps or restart Windows Audio/SMTC-related services.
  4. Update oh-my-posh in case the timeout budget or polling strategy was adjusted.
Defensive patterns

Strategy: retry

Try / catch

info, err := queryMediaPlayer(player)
if errors.Is(err, errTimeoutLike) || err != nil {
    // skip this render; the next prompt retries the query
    return nil, nil
}

Prevention

When it happens

Trigger: queryMediaPlayer or readMediaProperties awaited an async WinRT operation that stayed in a non-terminal state (e.g. Started) longer than smtcAsyncTimeout, causing the polling loop to pass its deadline.

Common situations: Slow or heavily loaded system delaying COM callbacks; Windows media service unresponsive; system resuming from sleep with media stack still initializing; antivirus or COM contention slowing the call.

Understand the failure class

Related errors


AI-assisted analysis of JanDeDobbeleer/oh-my-posh@0976794618 (2026-08-31). Data as JSON: /api/errors/ffdd70213a4b2560. Report an issue: GitHub.