Skip to content

Latest commit

 

History

History
255 lines (218 loc) · 25.9 KB

File metadata and controls

255 lines (218 loc) · 25.9 KB

Here is the combined list of vulnerabilities, formatted as markdown with main paragraphs and subparagraphs for each vulnerability, removing duplicates (in this case, there were no duplicates):

Combined Vulnerability List

1. Potential Context Manipulation Vulnerability in OpenTracing Bridge

  • Vulnerability Name: OpenTracing Bridge Context Manipulation

  • Description:

    1. An attacker crafts a malicious OpenTracing SpanContext, potentially containing forged or manipulated trace and baggage data.
    2. This malicious SpanContext is injected into an application instrumented with the OpenTelemetry/OpenTracing bridge.
    3. The application uses the bridgeTracer.ContextWithSpanHook to propagate this potentially malicious OpenTracing SpanContext to the OpenTelemetry context.
    4. Due to insufficient validation or sanitization within the bridge during the conversion from OpenTracing to OpenTelemetry context, the malicious data from the OpenTracing SpanContext is carried over into the OpenTelemetry context.
    5. Subsequently, OpenTelemetry instrumentation within the application, relying on the integrity of the context, might be misled or act based on the attacker-controlled data, potentially leading to information disclosure or other unintended consequences.
  • Impact:

    • High: Allows an attacker to inject potentially malicious data into the OpenTelemetry context of an application via the OpenTracing bridge. This could lead to misrepresentation of tracing data, potentially hiding malicious activities or misleading observability platforms. In a worst-case scenario, if application logic relies on data propagated through the context without proper validation, it could lead to security breaches such as information disclosure or authorization bypass, although this is less likely in the core library itself and more dependent on application-level usage of context data.
  • Vulnerability Rank: High

  • Currently Implemented Mitigations:

    • The provided code snippets in bridge/opentracing/README.md do not explicitly show any sanitization or validation of SpanContext data during the bridging process. The documentation focuses on functionality rather than security considerations.
    • The code snippet bridgeTracer.ContextWithSpanHook suggests a hook mechanism, but its implementation details and security measures are not provided in the README files or the current PROJECT FILES.
    • Based on the source code analysis of the current PROJECT FILES, no new mitigations are implemented.
  • Missing Mitigations:

    • Input validation and sanitization for OpenTracing SpanContext data before it is propagated to the OpenTelemetry context within the bridgeTracer.ContextWithSpanHook function or similar bridging mechanisms.
    • Clear documentation and guidelines for developers using the OpenTelemetry/OpenTracing bridge on potential security implications and recommended practices for handling context data from external tracing systems.
  • Preconditions:

    • Application must be using the go.opentelemetry.io/otel/bridge/opentracing bridge.
    • Application must be processing or propagating OpenTracing SpanContexts from potentially untrusted external sources.
    • The application must be using bridgeTracer.ContextWithSpanHook as described in the documentation.
  • Source Code Analysis:

    • The provided PROJECT FILES (/code/exporters/zipkin/model_test.go, /code/exporters/zipkin/zipkin_test.go, /code/exporters/zipkin/model.go, /code/exporters/zipkin/env_test.go, /code/exporters/zipkin/zipkin.go, /code/exporters/zipkin/doc.go, /code/exporters/zipkin/internal/gen.go, /code/exporters/zipkin/internal/matchers/expecter.go, /code/exporters/zipkin/internal/matchers/temporal_matcher.go, /code/exporters/zipkin/internal/matchers/expectation.go, /code/exporters/zipkin/internal/internaltest/env.go, /code/exporters/zipkin/internal/internaltest/alignment.go, /code/exporters/zipkin/internal/internaltest/text_map_carrier.go, /code/exporters/zipkin/internal/internaltest/text_map_carrier_test.go, /code/exporters/zipkin/internal/internaltest/text_map_propagator.go, /code/exporters/zipkin/internal/internaltest/env_test.go, /code/exporters/zipkin/internal/internaltest/errors.go, /code/exporters/zipkin/internal/internaltest/text_map_propagator_test.go, /code/exporters/zipkin/internal/internaltest/harness.go, /code/exporters/prometheus/config_test.go, /code/exporters/prometheus/benchmark_test.go, /code/exporters/prometheus/config.go, /code/exporters/prometheus/exporter_test.go, /code/exporters/prometheus/exporter.go, /code/exporters/prometheus/doc.go, /code/exporters/stdout/stdouttrace/config.go, /code/exporters/stdout/stdouttrace/trace.go, /code/exporters/stdout/stdouttrace/doc.go, /code/exporters/stdout/stdouttrace/trace_test.go, /code/exporters/stdout/stdouttrace/example_test.go, /code/exporters/stdout/stdoutmetric/config.go, /code/exporters/stdout/stdoutmetric/exporter_test.go, /code/exporters/stdout/stdoutmetric/encoder.go, /code/exporters/stdout/stdoutmetric/exporter.go, /code/exporters/stdout/stdoutmetric/doc.go, /code/exporters/stdout/stdoutmetric/example_test.go, /code/exporters/stdout/stdoutlog/config_test.go, /code/exporters/stdout/stdoutlog/config.go, /code/exporters/stdout/stdoutlog/exporter_test.go, /code/exporters/stdout/stdoutlog/record.go, /code/exporters/stdout/stdoutlog/exporter.go, /code/exporters/stdout/stdoutlog/doc.go, /code/exporters/stdout/stdoutlog/example_test.go, /code/go.mod, /code/log/go.mod, /code/metric/go.mod, /code/bridge/opencensus/go.mod, /code/bridge/opencensus/test/go.mod, /code/bridge/opentracing/go.mod, /code/bridge/opentracing/test/go.mod, /code/trace/go.mod, /code/trace/internal/telemetry/test/go.mod, /code/internal/tools/go.mod, /code/schema/go.mod, /code/sdk/go.mod, /code/sdk/log/go.mod, /code/sdk/metric/go.mod, /code/exporters/otlp/otlpmetric/otlpmetrichttp/go.mod, /code/exporters/otlp/otlpmetric/otlpmetricgrpc/go.mod, /code/exporters/otlp/otlptrace/go.mod, /code/exporters/otlp/otlptrace/otlptracegrpc/go.mod, /code/exporters/otlp/otlptrace/otlptracehttp/go.mod, /code/exporters/otlp/otlplog/otlploggrpc/go.mod, /code/exporters/otlp/otlplog/otlploghttp/go.mod, /code/exporters/zipkin/go.mod, /code/exporters/prometheus/go.mod, /code/exporters/stdout/stdouttrace/go.mod, /code/exporters/stdout/stdoutmetric/go.mod, /code/exporters/stdout/stdoutlog/go.mod, /code/Makefile) are related to various exporters and not the OpenTracing bridge implementation. Therefore, no source code analysis could be performed on the bridge itself using these files. Please refer to the description and missing mitigations for details.
  • Security Test Case:

    1. Setup a simple application that uses the go.opentelemetry.io/otel/bridge/opentracing bridge.
    2. Create a malicious OpenTracing SpanContext. This malicious context could include:
      • Forged TraceID or SpanID values that might conflict with internal OpenTelemetry IDs or cause parsing errors.
      • Malicious or excessively large baggage items designed to cause processing issues or information leakage if logged or exported.
      • TraceState with invalid characters or exceeding length limits to test handling of malformed TraceState.
    3. Inject this malicious OpenTracing SpanContext into an incoming request or operation that is instrumented with the application. This injection would typically happen through OpenTracing's context propagation mechanisms (e.g., HTTP headers).
    4. Within the application, use the bridgeTracer.ContextWithSpanHook to bridge the context.
    5. Observe the behavior of the application and the exported OpenTelemetry telemetry data. Specifically:
      • Check if the malicious data from the OpenTracing SpanContext is present in the OpenTelemetry Spans and context.
      • Monitor for any errors, panics, or unexpected behavior in the application or telemetry pipeline.
      • Examine exported telemetry data for any signs of data corruption or injection.
    6. A successful exploit would demonstrate that malicious data from the OpenTracing SpanContext is successfully propagated into the OpenTelemetry context without proper validation or sanitization, potentially causing issues in observability or downstream systems.

2. Information Disclosure via Process Command Arguments

  • Vulnerability Name: Process Command Arguments Information Disclosure

  • Description:

    1. The OpenTelemetry Go SDK's resource detection feature, when configured with WithProcessCommandArgs(), collects and exposes process command-line arguments as resource attributes.
    2. If an application is launched with sensitive information (e.g., passwords, API keys, access tokens) directly in the command-line arguments, this information will be captured by the resource detector.
    3. This sensitive information, now included as resource attributes, can be exported along with telemetry data (traces, metrics, logs) to observability backends.
    4. An attacker gaining access to these exported telemetry data (e.g., by compromising an observability platform, intercepting network traffic if telemetry is not securely transmitted) can potentially retrieve the sensitive command-line arguments, leading to information disclosure.
  • Impact:

    • High: Exposure of sensitive information passed as command-line arguments. This could include credentials, API keys, or other secrets, potentially leading to unauthorized access to systems or data.
  • Vulnerability Rank: High

  • Currently Implemented Mitigations:

    • The documentation for WithProcessCommandArgs() includes a warning: "Warning! This option will include process command line arguments. If these contain sensitive information it will be included in the exported resource." This warning is a form of documentation-based mitigation, but not a code-level mitigation.
    • No code-level sanitization or filtering of command-line arguments is implemented in the provided PROJECT FILES.
  • Missing Mitigations:

    • Implement a mechanism to filter or redact sensitive information from process command-line arguments before they are included as resource attributes. This could involve:
      • Providing options to selectively include/exclude specific command-line arguments based on keywords or patterns.
      • Offering a way to redact or mask sensitive parts of command-line arguments.
    • Enhance documentation to strongly recommend against passing sensitive information via command-line arguments when using WithProcessCommandArgs().
  • Preconditions:

    • Application must be using the OpenTelemetry Go SDK's resource detection feature.
    • Application must be configured to use WithProcessCommandArgs() option when creating a Resource.
    • Application must be launched with sensitive information passed as command-line arguments.
    • Telemetry data including resource attributes must be exported to an observability backend accessible to attackers.
  • Source Code Analysis:

    • In /code/sdk/resource/config.go:
      // WithProcessCommandArgs adds an attribute with all the command arguments (including
      // the command/executable itself) as received by the process to the configured
      // Resource.
      //
      // Warning! This option will include process command line arguments. If these
      // contain sensitive information it will be included in the exported resource.
      func WithProcessCommandArgs() Option {
          return WithDetectors(processCommandArgsDetector{})
      }
    • In /code/sdk/resource/process.go:
      var (
          defaultCommandArgsProvider    commandArgsProvider    = func() []string { return os.Args }
          commandArgs    = defaultCommandArgsProvider
      )
      
      // Detect returns a *Resource that describes all the command arguments as received
      // by the process.
      func (processCommandArgsDetector) Detect(ctx context.Context) (*Resource, error) {
          return NewWithAttributes(semconv.SchemaURL, semconv.ProcessCommandArgs(commandArgs()...)), nil
      }
    • The code directly uses os.Args to retrieve command-line arguments without any filtering or sanitization. When WithProcessCommandArgs() is enabled, these arguments are directly added as resource attributes using semconv.ProcessCommandArgs.
    • There is no mechanism in the provided code to prevent sensitive data in command-line arguments from being captured and exported as telemetry.
    • The provided PROJECT FILES (/code/exporters/zipkin/model_test.go, /code/exporters/zipkin/zipkin_test.go, /code/exporters/zipkin/model.go, /code/exporters/zipkin/env_test.go, /code/exporters/zipkin/zipkin.go, /code/exporters/zipkin/doc.go, /code/exporters/zipkin/internal/gen.go, /code/exporters/zipkin/internal/matchers/expecter.go, /code/exporters/zipkin/internal/matchers/temporal_matcher.go, /code/exporters/zipkin/internal/matchers/expectation.go, /code/exporters/zipkin/internal/internaltest/env.go, /code/exporters/zipkin/internal/internaltest/alignment.go, /code/exporters/zipkin/internal/internaltest/text_map_carrier.go, /code/exporters/zipkin/internal/internaltest/text_map_carrier_test.go, /code/exporters/zipkin/internal/internaltest/text_map_propagator.go, /code/exporters/zipkin/internal/internaltest/env_test.go, /code/exporters/zipkin/internal/internaltest/errors.go, /code/exporters/zipkin/internal/internaltest/text_map_propagator_test.go, /code/exporters/zipkin/internal/internaltest/harness.go, /code/exporters/prometheus/config_test.go, /code/exporters/prometheus/benchmark_test.go, /code/exporters/prometheus/config.go, /code/exporters/prometheus/exporter_test.go, /code/exporters/prometheus/exporter.go, /code/exporters/prometheus/doc.go, /code/exporters/stdout/stdouttrace/config.go, /code/exporters/stdout/stdouttrace/trace.go, /code/exporters/stdout/stdouttrace/doc.go, /code/exporters/stdout/stdouttrace/trace_test.go, /code/exporters/stdout/stdouttrace/example_test.go, /code/exporters/stdout/stdoutmetric/config.go, /code/exporters/stdout/stdoutmetric/exporter_test.go, /code/exporters/stdout/stdoutmetric/encoder.go, /code/exporters/stdout/stdoutmetric/exporter.go, /code/exporters/stdout/stdoutmetric/doc.go, /code/exporters/stdout/stdoutmetric/example_test.go, /code/exporters/stdout/stdoutlog/config_test.go, /code/exporters/stdout/stdoutlog/config.go, /code/exporters/stdout/stdoutlog/exporter_test.go, /code/exporters/stdout/stdoutlog/record.go, /code/exporters/stdout/stdoutlog/exporter.go, /code/exporters/stdout/stdoutlog/doc.go, /code/exporters/stdout/stdoutlog/example_test.go, /code/go.mod, /code/log/go.mod, /code/metric/go.mod, /code/bridge/opencensus/go.mod, /code/bridge/opencensus/test/go.mod, /code/bridge/opentracing/go.mod, /code/bridge/opentracing/test/go.mod, /code/trace/go.mod, /code/trace/internal/telemetry/test/go.mod, /code/internal/tools/go.mod, /code/schema/go.mod, /code/sdk/go.mod, /code/sdk/log/go.mod, /code/sdk/metric/go.mod, /code/exporters/otlp/otlpmetric/otlpmetrichttp/go.mod, /code/exporters/otlp/otlpmetric/otlpmetricgrpc/go.mod, /code/exporters/otlp/otlptrace/go.mod, /code/exporters/otlp/otlptrace/otlptracegrpc/go.mod, /code/exporters/otlp/otlptrace/otlptracehttp/go.mod, /code/exporters/otlp/otlplog/otlploggrpc/go.mod, /code/exporters/otlp/otlplog/otlploghttp/go.mod, /code/exporters/zipkin/go.mod, /code/exporters/prometheus/go.mod, /code/exporters/stdout/stdouttrace/go.mod, /code/exporters/stdout/stdoutmetric/go.mod, /code/exporters/stdout/stdoutlog/go.mod, /code/Makefile) do not include any mitigations for this vulnerability.
  • Security Test Case:

    1. Create a simple Go application that uses the OpenTelemetry Go SDK's resource detection and is configured with resource.WithProcessCommandArgs().
    2. In this application, initialize a TracerProvider and a simple exporter (e.g., tracetest.NewInMemoryExporter).
    3. Start a span in the application.
    4. End the span and force flush the exporter.
    5. Launch the application from the command line, passing a sensitive value as a command-line argument (e.g., ./myapp --api-key=sensitive_api_key).
    6. After running the application, retrieve the exported spans from the in-memory exporter.
    7. Assert that the exported resource attributes for the span include process.command_args and that this attribute's value contains the sensitive command-line argument (--api-key=sensitive_api_key).
    8. This test case demonstrates that sensitive command-line arguments are indeed captured as resource attributes and could be exported.

3. HTTP Header Injection via Environment Variables

  • Vulnerability Name: HTTP Header Injection via Environment Variables

  • Description: The stringToHeader function in /code/exporters/otlp/otlptrace/otlptracegrpc/internal/envconfig/envconfig.go and /code/exporters/otlp/otlptrace/otlptracehttp/internal/envconfig/envconfig.go parses header key-value pairs from environment variables like OTEL_EXPORTER_OTLP_HEADERS. While the function validates header keys to contain only "token" characters as per RFC7230, it does not prevent header injection attacks. An attacker could potentially inject arbitrary HTTP headers by crafting a malicious header string in the environment variable.

    Step-by-step trigger:

    1. An application using OpenTelemetry OTLP exporter for gRPC or HTTP reads exporter configurations from environment variables.
    2. An attacker sets a malicious environment variable, for example OTEL_EXPORTER_OTLP_HEADERS="X-Malicious-Header: injected-value,Valid-Header: valid-value".
    3. The stringToHeader function parses this environment variable.
    4. The function incorrectly splits the header string by comma and processes each part. It validates keys to be token chars, but it doesn't prevent injection of new headers via crafted keys or values.
    5. The OTLP exporter uses these parsed headers in subsequent HTTP or gRPC requests to the OTLP collector.
    6. The injected header X-Malicious-Header: injected-value is now included in the outgoing requests.
  • Impact: The impact of this vulnerability is high. HTTP header injection can have various security implications. Depending on the collector and intermediary systems, an attacker might be able to:

    • Bypass security controls.
    • Modify or manipulate requests.
    • Potentially gain unauthorized access or control over the collector or downstream systems if they rely on HTTP headers for authentication or authorization.
    • Cause unexpected behavior in the collector or downstream applications.
    • In some scenarios, it might be possible to leverage header injection for cross-site scripting (XSS) or other web-based attacks if the collector or monitoring dashboards expose these headers.
  • Vulnerability Rank: High

  • Currently Implemented Mitigations:

    • Header Key Validation: The isValidHeaderKey function in envconfig.go checks if the header key contains only token characters, preventing some invalid characters in header keys.
    • Error Logging: The stringToHeader function logs errors if header parsing fails, which can help in detecting potentially malicious header formats.

    Mitigation Location: /code/exporters/otlp/otlptrace/otlptracegrpc/internal/envconfig/envconfig.go:141-151 and /code/exporters/otlp/otlptrace/otlptracehttp/internal/envconfig/envconfig.go:141-151

  • Missing Mitigations:

    • Header Value Sanitization: The code does not sanitize or validate header values, allowing arbitrary values to be injected.
    • Prevention of Header Injection: The current validation is insufficient to prevent header injection. The code should be modified to strictly parse headers and disallow injection attempts. Consider using a more robust header parsing library or implementing stricter checks to ensure that only intended headers are processed.
    • Limit Header Keys: Restrict the allowed header keys to a predefined safe list. If any header key outside of this list is provided via environment variables, it should be rejected.
    • Input Sanitization and Validation: Implement more rigorous input validation and sanitization for environment variables that are used to configure HTTP headers.
  • Preconditions:

    • The application must be using OpenTelemetry OTLP exporter for gRPC or HTTP.
    • The application must be configured to read exporter configurations from environment variables (which is the default behavior).
    • An attacker must be able to control the environment variables of the application. In containerized environments or shared hosting, this might be possible through various means like manipulating container configurations or exploiting other vulnerabilities to set environment variables.
  • Source Code Analysis:

    // code/exporters/otlp/otlptrace/otlptracegrpc/internal/envconfig/envconfig.go (and otlptracehttp version)
    
    func stringToHeader(value string) map[string]string {
        headersPairs := strings.Split(value, ",")
        headers := make(map[string]string)
    
        for _, header := range headersPairs {
            n, v, found := strings.Cut(header, "=")
            if !found {
                global.Error(errors.New("missing '="), "parse headers", "input", header)
                continue
            }
    
            trimmedName := strings.TrimSpace(n)
    
            // Validate the key.
            if !isValidHeaderKey(trimmedName) {
                global.Error(errors.New("invalid header key"), "parse headers", "key", trimmedName)
                continue
            }
    
            // Only decode the value.
            value, err := url.PathUnescape(v) // Value is unescaped, but not sanitized
            if err != nil {
                global.Error(err, "escape header value", "value", v)
                continue
            }
            trimmedValue := strings.TrimSpace(value)
    
            headers[trimmedName] = trimmedValue // Header map is populated without injection prevention
        }
    
        return headers
    }
    
    func isValidHeaderKey(key string) bool {
        if key == "" {
            return false
        }
        for _, c := range key {
            if !isTokenChar(c) { // Only token chars are validated for key
                return false
            }
        }
        return true
    }

    Visualization:

    graph LR
        A[Start stringToHeader] --> B[Split value by comma]
        B --> C{Iterate through header pairs}
        C --> D{Cut header pair by "="}
        D -- No "=" --> E[Log Error: missing "="]
        D -- Found "=" --> F[Trim whitespace from key]
        F --> G{isValidHeaderKey(trimmedName)?}
        G -- No --> H[Log Error: invalid header key]
        G -- Yes --> I[URL PathUnescape value]
        I --> J{Error during unescape?}
        J -- Yes --> K[Log Error: escape header value]
        J -- No --> L[Trim whitespace from value]
        L --> M[headers[trimmedName] = trimmedValue]
        M --> C
        C -- No more pairs --> N[Return headers]
    
    Loading

    Source Code Walkthrough:

    1. The stringToHeader function takes a string value representing headers, expected to be comma-separated key-value pairs.
    2. It splits the value string by commas into headerPairs.
    3. It iterates through each header in headerPairs.
    4. For each header, it attempts to split it into a key-value pair using strings.Cut(header, "=").
    5. If the split by "=" fails (no "=" found), it logs an error and continues to the next header.
    6. It trims whitespace from the extracted key (trimmedName).
    7. It validates the trimmedName using isValidHeaderKey to ensure it contains only token characters.
    8. If the key is invalid, it logs an error and continues.
    9. It URL-path-unescapes the value part. Note: While the value is unescaped, it's not sanitized for header injection vulnerabilities.
    10. If unescaping fails, it logs an error and continues.
    11. It trims whitespace from the unescaped value (trimmedValue).
    12. It adds the trimmedName and trimmedValue to the headers map. Crucially, no check is performed here to prevent header injection. The code directly populates the header map.
    13. After processing all header pairs, it returns the headers map.
  • Security Test Case:

    Test Case Title: HTTP Header Injection via Environment Variables Test

    Description: This test case verifies that the stringToHeader function is vulnerable to HTTP header injection when parsing environment variables for OTLP exporter configuration. It checks if an attacker can inject arbitrary headers into outgoing HTTP requests by crafting a malicious header string in the environment variable.

    Preconditions:

    • Set up a test environment with an OTLP HTTP exporter configured to send traces to a mock collector.
    • The mock collector should be capable of capturing and inspecting HTTP headers of incoming requests.

    Test Steps:

    1. Set the environment variable OTEL_EXPORTER_OTLP_HEADERS to a malicious string containing a header injection payload, for example: OTEL_EXPORTER_OTLP_HEADERS="Valid-Header: valid-value,X-Injected-Header: injected-value".
    2. Initialize the OTLP HTTP exporter, ensuring it reads configurations from environment variables.
    3. Create and export a simple trace span using the initialized exporter.
    4. Inspect the HTTP headers received by the mock collector for the exported trace data.
    5. Verify that the injected header X-Injected-Header: injected-value is present in the HTTP headers captured by the mock collector, along with the Valid-Header.

    Expected Result:

    • The test should pass if the mock collector receives the HTTP request containing the injected header X-Injected-Header: injected-value. This confirms that the stringToHeader function is vulnerable to header injection and allows arbitrary headers to be added to outgoing HTTP requests via environment variables.