/* * _file_sync — нейтрализовать буфер потока (см. _file.h и * docs/file-buffering-design.md, «семантика инвалидации»). * * Направление «запись»: сбросить несброшенный хвост одним write(); * короткая запись = ошибка потока. Направление «чтение»: откатить * позицию fd назад на непрочитанный readahead (+1 за hold-байт * ungetc) — после этого реальная позиция fd совпадает с логической * позицией потока, буфер объявляется пустым. */ #include #include "_file.h" int _file_sync(FILE *fp) { if (fp->flags & _F_DIROUT) { uint16_t n = fp->level; fp->flags &= (uint8_t)~_F_DIROUT; fp->level = 0; fp->curp = fp->buf; if (n) { int w = write(fp->fd, fp->buf, n); if (w < 0 || (uint16_t)w != n) { fp->flags |= _F_ERROR; return EOF; } } } else { long back = fp->level; if (fp->hold != EOF) { back++; fp->hold = EOF; } fp->level = 0; fp->curp = fp->buf; if (back) { if (lseek(fp->fd, -back, SEEK_CUR) < 0) { fp->flags |= _F_ERROR; return EOF; } } } return 0; }