Python 我是在崩溃ctypes还是libFLAC?

Python 我是在崩溃ctypes还是libFLAC?,python,ctypes,Python,Ctypes,我已经找到了一种通过使用线程使libFLAC或ctypes崩溃的方法,但是这怎么可能呢?我不记得读过ctypes不是线程安全的,libflac1.2.1是显式线程安全的 无论如何,考虑下面的程序。最后是一个“for i in range()”循环。将范围设置为1可以正常工作,但增加范围会导致越来越多的SIGSEGV,直到程序永远不会产生任何输出。然后,如果您注释掉“从线程导入…”而启用“从多处理…”,则无论您同时启动多少实例,所有问题都将完全消失 有人能告诉我这里发生了什么事吗?我是不是用错了c

我已经找到了一种通过使用线程使libFLAC或ctypes崩溃的方法,但是这怎么可能呢?我不记得读过ctypes不是线程安全的,libflac1.2.1是显式线程安全的

无论如何,考虑下面的程序。最后是一个“for i in range()”循环。将范围设置为1可以正常工作,但增加范围会导致越来越多的SIGSEGV,直到程序永远不会产生任何输出。然后,如果您注释掉“从线程导入…”而启用“从多处理…”,则无论您同时启动多少实例,所有问题都将完全消失

有人能告诉我这里发生了什么事吗?我是不是用错了ctypes

问候/Klas

#! /usr/bin/python

import sys
import ctypes
import ctypes.util

# load the libFLAC .so
libflac = None
path = ctypes.util.find_library('FLAC')
if path:
    libflac = ctypes.CDLL(path)
if not libflac or not libflac._name:
    raise ImportError('failed to find libFLAC. Check your installation')

#### define cyptes prototypes for all library functions we need ####
SEARCH_FOR_METADATA   = 0x0
END_OF_STREAM         = 0x4
WRITE_STATUS_CONTINUE = 0x0

new = libflac.FLAC__stream_decoder_new
new.restype = ctypes.c_void_p
new.params = []

delete = libflac.FLAC__stream_decoder_delete
delete.restype = None
delete.params = [ctypes.c_void_p]

init_file = libflac.FLAC__stream_decoder_init_file
init_file.restype = ctypes.c_int
init_file.params = [
    ctypes.c_void_p, ctypes.c_char_p, ctypes.c_void_p,
    ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p
]

write_callback_type = ctypes.CFUNCTYPE(
    ctypes.c_int,
    ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p
)

error_callback_type = ctypes.CFUNCTYPE(
    None,
    ctypes.c_void_p, ctypes.c_int, ctypes.c_void_p
)

def write_callback(decoder, frame, buf, user):
    print 'write_callback()'
    return WRITE_STATUS_CONTINUE

def error_callback(decoder, status, user):
    print 'error_callback()'
#### end of ctypes prototypes ####

class FlacDecoder(object):
    decoder = None
    path    = None

    def __del__(self):
        delete(self.decoder)
        pass

    def __init__(self, path):
        self.decoder = new()
        self.path    = path

        # IMPORTANT: the callbacks must be saved somewhere to prevent the
        # garbage collector from smoking them (which leads to segfaults if
        # the calls are ever made)
        self.cb1 = write_callback_type(write_callback)
        self.cb3 = error_callback_type(error_callback)

        state = init_file(
            self.decoder, self.path, self.cb1, None, self.cb3, self.path
        )
        if state != SEARCH_FOR_METADATA:
            raise Exception('decoder_init_file() failed')

path = sys.argv[1].encode('utf-8')

def target(cursor):
    while True:
        dec = FlacDecoder(path)
        sys.stdout.write(cursor)

from threading import Thread
#from multiprocessing import Process as Thread

for i in range(2):
    t = Thread(target=target, args=(str(i),))
    t.daemon = True # so the program can quite without joining all the threads
    t.start()

while True:
    try:
        pass
    except KeyboardInterrupt:
        break
我在Debian挤压系统上运行此功能:

$ uname -a
Linux tor 2.6.32-trunk-amd64 #1 SMP Sun Jan 10 22:40:40 UTC 2010 x86_64 GNU/Linux
Python版本:

$ dpkg -s python2.6
Package: python2.6
Status: install ok installed
Priority: standard
Section: python
Installed-Size: 9240
Maintainer: Matthias Klose <doko@debian.org>
Architecture: amd64
Version: 2.6.6-10
Provides: python2.6-celementtree, python2.6-cjkcodecs, python2.6-ctypes, python2.6-elementtree, python2.6-wsgiref
Depends: python2.6-minimal (= 2.6.6-10), mime-support, libbz2-1.0, libc6 (>= 2.3), libdb4.8, libexpat1 (>= 1.95.8), libncursesw5 (>= 5.6+20070908), libreadline6 (>= 6.0), libsqlite3-0 (>= 3.5.9)
$dpkg-s python2.6
包装:python2.6
状态:安装正常已安装
优先权:标准
章节:python
安装尺寸:9240
维护者:Matthias Klose
架构:amd64
版本:2.6.6-10
提供:python2.6-celementtree、python2.6-cjkcodes、python2.6-ctypes、python2.6-elementtree、python2.6-wsgiref
取决于:python2.6-minimal(=2.6.6-10)、mime支持、libbz2-1.0、libc6(>=2.3)、libdb4.8、libexpat1(>=1.95.8)、libncursesw5(>=5.6+20070908)、libreadline6(>=6.0)、libsqlite3-0(>=3.5.9)
libFLAC版本:

$ dpkg -s libflac8
Package: libflac8
Status: install ok installed
Priority: optional
Section: libs
Installed-Size: 360
Maintainer: Debian Multimedia Maintainers <pkg-multimedia-maintainers@lists.alioth.debian.org>
Architecture: amd64
Source: flac
Version: 1.2.1-4
Depends: libc6 (>= 2.2.5), libogg0 (>= 1.0rc3)
$dpkg-s libflac8
包装:libflac8
状态:安装正常已安装
优先级:可选
章节:libs
安装尺寸:360
维护者:Debian多媒体维护者
架构:amd64
资料来源:flac
版本:1.2.1-4
取决于:libc6(>=2.2.5)、libogg0(>=1.0rc3)