directio

Igor Sysoev is at rambler-co.ru
Wed Jul 30 14:35:06 MSD 2008


On Tue, Jul 29, 2008 at 07:51:44PM +0200, Valery Kholodkov wrote:

> Прошу прощения, я был недостаточно многолословен: O_DIRECT требует ещё 
> чтобы размер буфера и указатель в файле были выравнены:
> 
> Breakpoint 1, ngx_read_file (file=0x80b9e90, buf=0xb7df9200 "", 
> size=131072, offset=44626744)
>     at src/os/unix/ngx_files.c:16
> 16          ngx_log_debug4(NGX_LOG_DEBUG_CORE, file->log, 0,
> (gdb) n
> 21          n = pread(file->fd, buf, size, offset);
> (gdb) n
> 23          if (n == -1) {
> (gdb) n
> 24              ngx_log_error(NGX_LOG_CRIT, file->log, ngx_errno,
> (gdb) n
> 26              return NGX_ERROR;
> 
> Соответственно, с этим патчем если я файл запрашиваю с начала, то всё 
> работает, за исключением последнего блока. А если я файл запрашиваю 
> частями с невыровненных смещений, то результат такой же как в предыдущем 
> письме.
> 
> Идея здесь, как я понимаю, в том, что ОС не занимается копированием, а 
> только трансляцией виртуальных адресов в физические. Данные 
> подкладываются в нужное место физической памяти DMA.

Да, при использовании O_DIRECT ОС может читать с диска прямо в
пользовательскую память. FreeBSD делает fallback к обычному чтению,
если параметры не удовлетворяют прямому чтению. В общем, я добавлю
в 0.7.7 directio, а там будем смотреть на каких Линуксах это работает.

Синтаксис немного изменился:

   directio [off|размер]

То есть, 0 теперь рассматривается как размер.

> Igor Sysoev wrote:
> >On Fri, Jul 25, 2008 at 09:11:41PM +0200, Valery Kholodkov wrote:
> >
> >>Скажите, патч предназначен исключительно для FreeBSD?
> >>
> >>Потому как на линуксе 2.6.10 я справедливо получаю:
> >>
> >>2008/07/25 20:58:08 [crit] 4600#0: *1 pread() failed, file 
> >>"/usr/local/nginx/html/Synovya.i.Lubovniki.1.of.2.avi" (22: Invalid 
> >>argument) while sending response to client, client: 192.168.1.13, 
> >>server: 192.168.1.1, request: "GET /Synovya.i.Lubovniki.1.of.2.avi 
> >>HTTP/1.1", host: "192.168.1.1"
> >>
> >>по очевидной причине -- приемный буфер не выровнен на границу дискового 
> >>блока:
> >>
> >>Breakpoint 1, ngx_read_file (file=0x80b9ec4, buf=0x80f3970 "", 
> >>size=32768, offset=0)
> >>    at src/os/unix/ngx_files.c:16
> >>16          ngx_log_debug4(NGX_LOG_DEBUG_CORE, file->log, 0,
> >>(gdb) n
> >>21          n = pread(file->fd, buf, size, offset);
> >>(gdb) n
> >>23          if (n == -1) {
> >>(gdb) n
> >>24              ngx_log_error(NGX_LOG_CRIT, file->log, ngx_errno,
> >>(gdb) n
> >>26              return NGX_ERROR;
> >>(gdb) n
> >>54      }
> >
> >Новый патч, в котором буфера выровнены по размеру сектора.
> >
> >
> >
> 
> 
> -- 
> Regards,
> Valery Kholodkov

-- 
Игорь Сысоев
http://sysoev.ru





More information about the nginx-ru mailing list