Skip to content

Python <=3.9 segmentation fault in code snippet #117090

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
NullHypothesis opened this issue Mar 20, 2024 · 4 comments
Closed

Python <=3.9 segmentation fault in code snippet #117090

NullHypothesis opened this issue Mar 20, 2024 · 4 comments
Labels
type-bug An unexpected behavior, bug, or error

Comments

@NullHypothesis
Copy link

NullHypothesis commented Mar 20, 2024

Bug report

Bug description:

The following code snippet results in a segmentation fault in Python 3.8 and 3.9, but not 3.10 and newer:

#!/usr/bin/env python3.9

# pip install opentelemetry-sdk
from opentelemetry.sdk.trace import TracerProvider
from opentelemetry.sdk.trace.export import (
    BatchSpanProcessor,
    ConsoleSpanExporter,
)

fd = open("foo.txt", "w")
tracer_provider = TracerProvider()
processor = BatchSpanProcessor(ConsoleSpanExporter(out=fd))
tracer_provider.add_span_processor(processor)

The following conditions need to be met for the segmentation fault to happen:

  • Python 3.9.18 or older (does not happen with Python 3.10 or newer)
  • fd must not be closed (does not happen if fd.close() is run at the end)

I could reproduce this segfault on both macOS Sonoma 14.3.1 and Ubuntu Linux 23.10.

I realize that 3.8 and 3.9 are no longer in the "bugfix" phase but the segfault may have security implications, which is why I decided to open this issue. Please feel free to close if it's not helpful.

CPython versions tested on:

3.8, 3.9, 3.10, 3.13

Operating systems tested on:

Linux, macOS

@NullHypothesis NullHypothesis added the type-bug An unexpected behavior, bug, or error label Mar 20, 2024
@gaogaotiantian
Copy link
Member

Segfault is sometimes security issue, not always, but the more important thing is - can you repro this without opentelemetry? If it's a CPython issue then it should be reproducible without any 3rd party code.

@NullHypothesis
Copy link
Author

I'm unable to spend more cycles on this but I'll create an OpenTelemetry issue. If that results in something useful, I'll re-open.

@methane
Copy link
Member

methane commented Mar 21, 2024

I can reproduce it without otel. ref

import os, time

f = open("foo.txt", "w")

class C:
    def __init__(self):
        self.f = f
        os.register_at_fork(after_in_child=self.atfork)

    def atfork(self):
        print("atfork")
c=C()
del c, f

This issue caused by this code is called during late interpreter shutdown.

assert(globals != NULL);

This issue is fixed by this commit in Python 3.10. register_at_fork is cleared before sysdict.

#21605

But I am not sure about similar SEGV is not possible anymore.
ResourceWarning for unclosed files are happened during interpreter shutdown often.
So warning code would be more defensive. Instead of assert(global != NULL), it can be if (global == NULL) { goto handle_error; }

@methane
Copy link
Member

methane commented Mar 21, 2024

I checked finalization code and I can not find any way to emit ResourceWarning after Py_CLEAR(interp->sysdict); in interpreter_clean().
So I think this issue is really fixed in Python 3.10+ by #21605 .

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type-bug An unexpected behavior, bug, or error
Projects
None yet
Development

No branches or pull requests

4 participants