Почему блок именованного канала открывается только для чтения?

Я заметил несколько странностей при работе с именованными каналами (FIFO) в различных версиях UNIX (Linux, FreeBSD и MacOS X) с использованием Python. Первое и, возможно, наиболее неприятное, заключается в том, что попытки открыть пустой / неактивный FIFO только для чтения будут блокироваться (если я не использую os.O_NONBLOCK с нижним уровнем os.open () ) вызов). Однако, если я открою его для чтения / записи, то я не получу блокировки.

Примеры:

f = open('./myfifo', 'r')               # Blocks unless data is already in the pipe
f = os.open('./myfifo', os.O_RDONLY)    # ditto

# Contrast to:
f = open('./myfifo', 'w+')                           # does NOT block
f = os.open('./myfifo', os.O_RDWR)                   # ditto
f = os.open('./myfifo', os.O_RDONLY|os.O_NONBLOCK)   # ditto

Мне просто любопытно, почему. Почему блокируется открытый вызов, а не какая-то последующая операция чтения?

Также я заметил, что неблокирующий файловый дескриптор может проявлять различное поведение в Python. В случае, когда я использую os.open () с os.O_NONBLOCK для начальной операции открытия, тогда os.read () , похоже, возвращает пустая строка, если данные в файловом дескрипторе не готовы. Однако, если я использую fcntl.fcnt (f.fileno (), fcntl.F_SETFL, fcntl. GETFL | os.O_NONBLOCK) , тогда os.read вызывает исключение ( errno.EWOULDBLOCK )

Есть ли другой флаг, установленный обычным open ( ) , который не установлен в моем примере os.open () ? Чем они отличаются и почему?

57
задан tshepang 7 December 2013 в 19:56
поделиться