Date: Sun, 4 Aug 2002 14:34:29 -0700 (PDT) From: Antti Louko <alo@iki.fi> To: freebsd-gnats-submit@FreeBSD.org Subject: misc/41331: Pthread library open sets O_NONBLOCK flag and causes unnecessary EAGAIN errors especially with /dev/stdout. Message-ID: <200208042134.g74LYTM6074371@www.freebsd.org>
next in thread | raw e-mail | index | archive | help
>Number: 41331
>Category: misc
>Synopsis: Pthread library open sets O_NONBLOCK flag and causes unnecessary EAGAIN errors especially with /dev/stdout.
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: freebsd-bugs
>State: open
>Quarter:
>Keywords:
>Date-Required:
>Class: sw-bug
>Submitter-Id: current-users
>Arrival-Date: Sun Aug 04 14:40:01 PDT 2002
>Closed-Date:
>Last-Modified:
>Originator: Antti Louko
>Release: 4.5
>Organization:
>Environment:
FreeBSD xxx.louko.com 4.5-RELEASE FreeBSD 4.5-RELEASE #1: Tue Mar 5 23:48:33 EET 2002 root@xxx.louko.com:/xxx/src/sys/compile/ALO i386
>Description:
When using threads, the threads library
(/usr/src/lib/libc_r/uthread/uthread_fd.c) sets O_NONBLOCK for each
new opened file and fails to emulate the blocking write(2) correctly.
This affects eg. when a program opens /dev/stdout for writing and thje
reader process is slower than the writer. The writer gets EAGAIN
error which shouldn't happen when the open call didn't specify
O_NONBLOCK flag.
>How-To-Repeat:
Run the following program (compiled with gcc -pthread -o writer
writer.c) and feed its output to the shell script:
./writer | sh reader.sh
reader.sh:
----------------------------------------
#! /bin/sh
while :
do
dd of=/dev/null bs=1k count=1
sleep 1
done
----------------------------------------
writer.c
----------------------------------------
#include <stdio.h>
#include <errno.h>
#include <fcntl.h>
main(int argc, char **argv)
{
char buf[1024];
int fd;
int i;
int total = 0;
fd = open("/dev/stdout",O_WRONLY|O_CREAT|O_TRUNC,0666);
if (fd == -1) {
int e;
e = errno;
fprintf(stderr,"open, errno: %d\n",e);
exit(1);
}
for(i = 0; i < sizeof(buf); i++)
buf[i] = 'a' + (i % 26);
for(;;) {
int n;
n = write(fd,buf,sizeof(buf));
if (n > 0)
total += n;
if (n != sizeof(buf)) {
int e;
e = errno;
fprintf(stderr,"write, errno: %d\n",e);
fprintf(stderr,"Total bytes written %d\n",total);
exit(1);
}
}
}
----------------------------------------
Run the following program (compiled with gcc -pthread -o writer
writer.c) and feed its output to the shell script:
./writer | sh reader.sh
reader.sh:
----------------------------------------
#! /bin/sh
while :
do
dd of=/dev/null bs=1k count=1
sleep 1
done
----------------------------------------
writer.c
----------------------------------------
#include <stdio.h>
#include <errno.h>
#include <fcntl.h>
main(int argc, char **argv)
{
char buf[1024];
int fd;
int i;
int total = 0;
fd = open("/dev/stdout",O_WRONLY|O_CREAT|O_TRUNC,0666);
if (fd == -1) {
int e;
e = errno;
fprintf(stderr,"open, errno: %d\n",e);
exit(1);
}
for(i = 0; i < sizeof(buf); i++)
buf[i] = 'a' + (i % 26);
for(;;) {
int n;
n = write(fd,buf,sizeof(buf));
if (n > 0)
total += n;
if (n != sizeof(buf)) {
int e;
e = errno;
fprintf(stderr,"write, errno: %d\n",e);
fprintf(stderr,"Total bytes written %d\n",total);
exit(1);
}
}
}
----------------------------------------
Run the following program (compiled with gcc -pthread -o writer
writer.c) and feed its output to the shell script:
./writer | sh reader.sh
reader.sh:
----------------------------------------
#! /bin/sh
while :
do
dd of=/dev/null bs=1k count=1
sleep 1
done
----------------------------------------
writer.c
----------------------------------------
#include <stdio.h>
#include <errno.h>
#include <fcntl.h>
main(int argc, char **argv)
{
char buf[1024];
int fd;
int i;
int total = 0;
fd = open("/dev/stdout",O_WRONLY|O_CREAT|O_TRUNC,0666);
if (fd == -1) {
int e;
e = errno;
fprintf(stderr,"open, errno: %d\n",e);
exit(1);
}
for(i = 0; i < sizeof(buf); i++)
buf[i] = 'a' + (i % 26);
for(;;) {
int n;
n = write(fd,buf,sizeof(buf));
if (n > 0)
total += n;
if (n != sizeof(buf)) {
int e;
e = errno;
fprintf(stderr,"write, errno: %d\n",e);
fprintf(stderr,"Total bytes written %d\n",total);
exit(1);
}
}
}
----------------------------------------
>Fix:
>Release-Note:
>Audit-Trail:
>Unformatted:
To Unsubscribe: send mail to majordomo@FreeBSD.org
with "unsubscribe freebsd-bugs" in the body of the message
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200208042134.g74LYTM6074371>
