Skip to content

C#: Recognize safe output encoding in cs/log-forging - #22737

Open
Bubby4j wants to merge 1 commit into
github:mainfrom
Bubby4j:fix/cs-json-safe-log-encoding
Open

Bubby4j wants to merge 1 commit into
github:mainfrom
Bubby4j:fix/cs-json-safe-log-encoding

Conversation

@Bubby4j

@Bubby4j Bubby4j commented Oct 2, 2026

Copy link
Copy Markdown
Contributor

Summary

Log injection / log forging is one of the biggest sources of false positive flaws from CodeQL according to this analysis and my own personal experience.

This change prevents false positives from cs/log-forging when all present logging configuration uses a safe JSON format, either from .NET or Serilog.

The query suppresses alerts for standard Microsoft.Extensions.Logging and Serilog logging calls only when a conservative, database-wide configuration check succeeds. It recognizes supported code-configured JSON logging setups and deliberately retains alerts whenever it finds a potentially incompatible, unresolved, or unsupported logging configuration.

Over time this could be extended to support additional popular logging frameworks or safe output formats. In particular .NET 11 may soon have a safe console logger.

Risks

This is intentionally a database-wide heuristic: if it incorrectly classifies an application as JSON-only, it can suppress genuine cs/log-forging results throughout that database.

The false-negative risk is primarily configuration that is not visible or not recognized by the extractor/model—for example, logging changes in external dependencies, reflection, runtime-loaded configuration, or an external extension method that mutates logging without exposing a logging-related signature. The implementation partially mitigates this by requiring narrow recognized patterns and by vetoing on visible ambiguity or unsupported configuration, at the cost of retaining some false positives.

Suppression criteria

Suppression requires both positive evidence of a supported JSON-only configuration and no vetoing configuration anywhere visible in the database.

Recognized configurations are:

  • LoggerFactory.Create callbacks that configure AddJsonConsole().
  • Host or service-registration setup which:
    • unconditionally clears existing providers with ClearProviders();
    • then unconditionally adds AddJsonConsole();
    • is associated with the same host instance; and
    • occurs before Build().
  • Serilog AddSerilog configuration callbacks that unconditionally configure supported JSON-formatted console, audit-console, or file sinks, including supported WriteTo.Async wrappers.
    • Supported formatters are JsonFormatter with an omitted or null closingDelimiter, and CompactJsonFormatter / RenderedCompactJsonFormatter with their default formatter or a built-in JsonValueFormatter.
    • writeToProviders and preserveStaticLogger must be omitted or false.
  • Recognized static/bootstrap Serilog loggers configured with a supported JSON sink.

Suppression applies only to calls to supported framework logger APIs whose receiver is a library-provided Microsoft.Extensions.Logging or Serilog logger type. It does not suppress non-logger sinks such as tracing APIs or source-defined logger implementations.

Conservative vetoes

The suppression is disabled if the database contains, among other things:

  • an unconfigured host, ambiguous host/logging alias, conditional setup, or setup after Build();
  • unsupported or unresolved Microsoft logging or Serilog configuration;
  • configuration loaded from external sources;
  • alternative providers such as NLog or log4net;
  • direct registration or replacement of logging services/providers;
  • logging-options configuration or console formatter overrides;
  • logging configuration that escapes into a field or property;
  • unresolved new LoggerFactory() construction;
  • source-defined ILogger implementations; or
  • an unsupported static Serilog logger assignment.

Tests

Added coverage for:

  • safe and mixed built-in .NET logging configurations;
  • direct host, HostApplicationBuilder, and service-registration setup;
  • safe and unsafe Serilog sinks, formatters, forwarding, bootstrap loggers, and external configuration;
  • unconfigured hosts, conditional/aliased setup, setup after build, provider overrides, configuration escapes, and custom loggers;
  • veto classification, so the conditions preventing suppression are independently regression-tested.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants