🌐 IIS

IIS Logging, Performance & Troubleshooting Common Errors

📅 July 21, 202611 min readITVedas

Diagnose production IIS issues: W3C log fields that matter, Failed Request Tracing, key perf counters, and root causes for 500.19, 502.3, and 503 errors.

ADVANCED
⏱ 11 min read
Prerequisites:
Key Facts
  • sc-status paired with sc-substatus and sc-win32-status pinpoints the exact failure category, not just the HTTP code
  • Failed Request Tracing only writes an XML trace when a request actually matches a configured failure-definition rule, so it produces no overhead on requests that don't match
  • HTTP 502.3 originates from Application Request Routing or another reverse proxy, not from the IIS worker process itself
  • HTTP 503 with a Service Unavailable page almost always means the application pool is stopped, not that the site is misconfigured

Why Logging and Performance Diagnostics Matter

Most IIS problems that reach an administrator's desk are reported vaguely: "the site is slow," "we got an error page," "it works sometimes." None of that is actionable on its own. IIS ships with three independent diagnostic systems that, used together, turn a vague complaint into a root cause: W3C logs for historical request-level data, Failed Request Tracing for deep per-request traces on demand, and Performance Monitor counters for real-time resource pressure. Each answers a different question. Logs tell you what happened and when. FREB tells you why a specific request failed, step by step through the pipeline. Counters tell you whether the server is currently under stress. Reaching for the wrong one wastes time — pulling FREB traces to answer a capacity question, or staring at Task Manager to explain a single failed request, are both dead ends. The rest of this article treats them as a toolkit, then applies that toolkit to the three status codes IIS administrators see most often in production: 500.19, 502.3, and 503.

W3C Logging Format and the Fields Worth Watching

IIS supports several log formats, but W3C Extended Log File Format is the one worth standardizing on: it's a plain-text, space-delimited format with a self-describing header and a customizable field list, and it's what every log analysis tool expects. Logs live under %SystemDrive%\inetpub\logs\LogFiles by default, one subfolder per site, with a new file created daily unless you change the rollover policy.

The default field set is thin. In IIS Manager, under a site's Logging feature, click Select Fields and add these if they aren't already present:

A practical habit: filter a day's log for sc-status values of 4xx and 5xx, then sort by time-taken descending within that filtered set. Slow errors and fast errors usually have different causes — a slow 500 often points to a downstream dependency timing out before the app fails, while a fast 500 usually points to something failing immediately, like a null reference or a missing config section.

Failed Request Tracing (FREB) for Hard-to-Reproduce Issues

W3C logs tell you a request failed; they don't tell you where in the pipeline it failed or what each module did along the way. Failed Request Tracing (branded FREB, for Failed Request Event Buffering) closes that gap by capturing a detailed, step-by-step XML trace of individual requests as they move through IIS — module by module, with timings and outcomes for each stage.

FREB requires the Tracing role service (Web Server > Health and Diagnostics > Tracing) to be installed, and it must be enabled per site under Configure Failed Request Tracing, where you set a log directory and a maximum trace file count. The critical piece is the failure definition: a rule specifying which requests get traced, based on status code ranges, time-taken thresholds, or specific event severities. This is what makes FREB practical for production — you don't trace every request, only ones matching the rule, so there's no meaningful performance cost on the requests you don't care about.

This targeting is exactly what makes FREB the right tool for issues you can't reproduce on demand: an error that shows up once a day under real traffic, or a request that occasionally takes 30 seconds instead of 300ms. Set a rule to catch status-codes(500-599) or time-taken(30000), let it run, and the next occurrence produces a full trace automatically — no need to be watching when it happens. Each trace is written as an .xml file readable directly in a browser (with the accompanying freb.xsl stylesheet in the same folder) or in IIS Manager's trace log viewer. The trace shows every module invoked, in order, with the elapsed time each one took and the exact point of failure — which is precisely the detail a W3C log entry with a single time-taken value cannot provide.

Key Performance Counters to Watch

Logs and traces are retrospective — they explain what already happened. Performance counters, monitored through Performance Monitor (perfmon) or collected into a monitoring system, tell you what's happening right now and give early warning before users notice.

The practical workflow is to baseline these counters during normal operation, then alert on deviation rather than on fixed thresholds — "requests queued sustained above baseline for five minutes" is a far more reliable signal than an arbitrary fixed number, since normal queue depth varies enormously by application and hardware.

Troubleshooting 500.19 — Configuration Error

500.19 means IIS could not process the request because of an invalid or inaccessible configuration, and it happens before any application code runs. The sc-win32-status field and the detailed error page both surface a Config Error and a Config File path — always start there rather than guessing.

The most common causes, in order of frequency:

Because this fails before the application layer, application-side logging (including most APM tools) never sees the request — W3C logs and the IIS error page are the only sources of truth here.

Troubleshooting 502.3 — Bad Gateway

502.3 is specific to servers running as a reverse proxy — typically via Application Request Routing (ARR) or URL Rewrite configured with a reverse-proxy rule — and it means the request reached IIS successfully but the upstream server IIS was proxying to did not respond correctly, or at all. This is fundamentally different from 500.19: the local IIS configuration is fine, the problem is downstream.

Sub-status variants clarify the specific failure: a common one is 502.3 Bad Gateway (ARR) shown with a Win32 error like connection refused or timeout. Work through these causes:

Because the failure is on the network hop between proxy and backend, the proxy server's own W3C log will show the 502 with essentially no useful detail beyond the sub-status — the real diagnostic data lives on or near the backend.

Troubleshooting 503 — Service Unavailable

503 means IIS itself is up and listening, but the application pool serving the request is not — most commonly because it has stopped. Unlike 500.19 and 502.3, this is rarely a configuration content problem; it's a process-state problem, and the investigation starts in the Application pools view in IIS Manager and the event logs, not in web.config.

Work the causes in this order:

Once the pool is confirmed running again, correlate its start time against the W3C logs and, if the crash was intermittent, retroactively enable a FREB rule on time-taken or status code so the next crash produces a full request trace instead of just an event log entry.

Key Takeaways

  • Enable W3C logging with the full field set before an incident happens — you cannot retroactively log a request that already occurred
  • Use FREB, not the browser or Fiddler, when an error is intermittent or only happens under load
  • Watch Requests Queued and Current Connections as leading indicators of saturation before users start reporting timeouts
  • Distinguish 500.19 (bad config, XML-level) from 502.3 (bad upstream, proxy-level) from 503 (dead app pool, process-level) — the fix lives in a different layer for each
  • Check the rapid-fail protection settings and the Application/System event logs before touching any config file when a pool won't stay running