Antes da padronização havia ioctl(... FIONBIO... )e fcntl(... O_NDELAY... ), mas esses se comportavam de maneira inconsistente entre os sistemas e até mesmo dentro do mesmo sistema. Por exemplo, era comum FIONBIOtrabalhar em soquetes e O_NDELAYtrabalhar em ttys, com muita inconsistência para coisas como tubos, fifos e dispositivos. E se você não sabia que tipo de descritor de arquivo você tinha, você teria que definir ambos para ter certeza. Mas, além disso, uma leitura sem bloqueio e sem dados disponíveis também foi indicada de forma inconsistente; dependendo do sistema operacional e do tipo de descritor de arquivo, a leitura pode retornar 0, ou -1 com errno EAGAIN, ou -1 com errno EWOULDBLOCK. Ainda hoje, definindo FIONBIOouO_NDELAYno Solaris faz com que uma leitura sem dados retorne 0 em um tty ou pipe, ou -1 com errno EAGAIN em um soquete. No entanto, 0 é ambíguo, pois também é retornado para EOF.
POSIX abordou isso com a introdução de O_NONBLOCK, que padronizou o comportamento em diferentes sistemas e tipos de descritores de arquivo. Como os sistemas existentes geralmente desejam evitar quaisquer mudanças no comportamento que possam quebrar a compatibilidade com versões anteriores, POSIX definiu um novo sinalizador em vez de obrigar um comportamento específico para um dos outros. Alguns sistemas como Linux tratam todos os 3 da mesma maneira e também definem EAGAIN e EWOULDBLOCK com o mesmo valor, mas sistemas que desejam manter algum outro comportamento legado para compatibilidade com versões anteriores podem fazê-lo quando os mecanismos mais antigos são usados.
Novos programas devem usar fcntl(... O_NONBLOCK... ), conforme padronizado por POSIX.