簡體   English   中英

為什么在寫入python子進程stdin管道時丟失數據?

[英]Why is data missing when I write to a python subprocess stdin pipe?

我的python代碼如下所示:

def test():
    pipe = sp.Popen( ["test.sh"], stdin=sp.PIPE)
    data = "".join([chr((s)%17) for s in range(0,33)])
    os.write(pipe.stdin.fileno(), data)
    pipe.stdin.write("endoffile")

if __name__ == "__main__":
    test()

它調用以下簡單的bash shell腳本,該腳本僅將stdin寫入文件(腳本稱為test.sh)。

#!/bin/bash
VALUE=$(cat)

echo "$VALUE" >> /tmp/test.txt

當我運行python代碼時,我希望test.txt包含兩次0x01..0x10值,然后字符串“ endoffile”

但是,這是文件的十六進制轉儲:

0000000: 0102 0304 0506 0708 090a 0b0c 0d0e 0f10  ................
0000010: 0102 0304 0506 0708 090a 0b0c 0d0e 0f65  ...............e
0000020: 6e64 6f66 6669 6c65 0a                   ndoffile.

似乎缺少一個字節(0x10)。

我在這里想念什么?

-更新

將test()函數更改為:

def test():
    pipe = sp.Popen( ["test.sh"], stdin=sp.PIPE)
    data = "".join([chr((s)%16+1) for s in range(0,32)])
    os.write(pipe.stdin.fileno(), data)
    pipe.stdin.write("endoffile")

似乎解決了。 似乎與將chr(0)發送到管道有關。

range()在右側排他。

range(0, 33)[0, ..., 32] ,可能是因為這樣您就可以range(0, len(sequence))不會出現一對一的錯誤。

由於32 % 17 == 15 == 0x0f ,因此您期望的字節'\\x10'從來沒有成為列表的一部分。

編輯1:輸出中還缺少零字符'\\x00' 如果您使用VALUE=$(cat)的輸出cat是由外殼受到處理。

SingleUnix / POSIX似乎對此事保持沉默。 但是很明顯,您不能在shell變量的值(或名稱)中包含'\\0' ,因為Unix環境要求兩者都必須是C樣式的零終止字符串 我實際上希望VALUE的值是一個空字符串。

編輯2經過一番挖掘,我可以說至少ash實施忽略了'\\0'處理反引號提供的輸入。 讀取輸入,直到EOF和空字符被顯式跳過。

bash會執行相同的操作,甚至具有與該事件關聯的顯式(即使已注釋掉) 警告

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM