質問

I have a python loop that reads from multiple child processes (without blocking). Sometimes I have to write to that child process. The first write goes through but if I perform a non-blocking read then write to the child process again, the second write never seems to go through to the child process.

I believe if I perform a regular blocking read (process.stderr.readline()), the second read will go through. Any help?

Python loop

# create mock process
childprocesses = []
p = subprocess.Popen(['./cprogram'], 
    stdin=subprocess.PIPE, 
    stdout=subprocess.PIPE, 
    stderr=subprocess.PIPE)
childprocesses.append(p)
loop_4eva()

# the loop
def loop_4eva():
    for process in childprocesses:
        if(process.poll() is None):
            process.stdin.write("first write\n")
            output = non_block_read(process.stderr).strip()
            print output
            process.stdin.write("second write\n")
            output = non_block_read(process.stderr).strip()
            print output


def non_block_read(output):
    fd = output.fileno()
    fl = fcntl.fcntl(fd, fcntl.F_GETFL)
    fcntl.fcntl(fd, fcntl.F_SETFL, fl | os.O_NONBLOCK)
    try:
            return output.readline()
    except:
            return ''

A child process (c program)

void main(){
    char buffer[256];
    while(1){
        fgets(buffer, 256, stdin);//read/buffer one line from stdin
        fprintf(stderr, "read: %s", buffer);//buffer includes '\n'
    }
}

Output (python prints...)

read: first write
//nothing else

役に立ちましたか?

解決

stdin is line buffered in C. You will probably need to disable buffering in the child process to make this work. You'll also want to add a process.stdin.flush() to ensure you aren't getting buffered on the writer side.

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top