На какие API влияют {$IOCHECKS OFF}?

У нас есть некоторый древний код Delphi (возможно, даже возникший как код Turbo Pascal), который использует {$I-} ака {$IOCHECKS OFF}, что заставляет код использовать IOResult вместо исключений для ошибок дискового ввода-вывода.

Я хочу избавиться от {$I-} и перенести этот код в 1990-е годы, но для этого я хотел бы знать, на что все это влияет {$IOCHECKS OFF}, Влияет ли это только на грубые старые встроенные функции ввода-вывода, такие как AssignFile / Reset / Rewrite / Append / CloseFile? Или это влияет на более современные вещи, такие как TFileStream? Что еще более важно, что еще может быть затронуто, о чем я не думаю? ( Основы Delphi предполагают, что он также влияет на MkDir и RmDir. Если он влияет на них, их должно быть больше.)

Раздел справки Delphi 2007 "Проверка ввода-вывода (Delphi)" (ms-help://borland.bds5/devcommon/compdirsinput_outputchecking_xml.html) говорит, что это влияет на "процедуры ввода-вывода [s]" и что "процедуры ввода-вывода описаны в руководстве по языку Delphi". Это не очень помогает, так как CodeGear никогда не выпускал Language Guide, а последний раз Borland выпускал Delphi 5.

Какие функции и классы ведут себя по-разному под {$I-}?


РЕДАКТИРОВАТЬ: принятый ответ дает некоторое хорошее представление, но вот краткое резюме в форме списка в алфавитном порядке: {$IOCHECKS OFF} влияет только на следующие подпрограммы из системного блока.

  • присоединять
  • BlockRead
  • BlockWrite
  • ChDir
  • CloseFile
  • Eof
  • Eoln
  • стирать
  • FilePos
  • Размер файла
  • Промывать
  • MkDir
  • Читать
  • ReadLn
  • переименовывать
  • Сброс
  • перезапись
  • RmDir
  • Искать
  • SeekEof
  • SeekEoln
  • SetLineBreakStyle
  • усекать
  • Написать
  • Writeln

1 ответ

Решение

Поскольку $I является директивой компилятора, она может влиять только на код, сгенерированный компилятором, и она может влиять только на код, который фактически компилируется.

По этим двум причинам это не может повлиять на такие вещи, как TFileStream, Это класс в Classes.pas, который вы не компилируете. На любой код в нем не влияет $I директивы. Кроме того, компилятор не обрабатывает этот класс специально каким-либо образом. Это просто еще один обычный класс.

$I Директива влияет на встроенные функции языка, которые вы упомянули. Компилятор генерирует вызовы этих функций специально. Это также влияет на звонки write, writeln, а также readln, Это также должно повлиять BlockRead а также BlockWrite,

Вы можете проверить исходный код. Все, что звонит SetInOutRes подвержен $I, Это включает в себя функции, которые открывают файлы (Append, Reset, а также Rewrite), а также все остальное, что принимает параметр типа file или же TextFile (Flush, BlockRead, BlockWrite, Erase, FilePos, Seek, FileSize, Read, Readln, Write, Writeln, Rename, Eof, SeekEof, Eoln, SeekEol, Truncate, SetLineBreakStyle, а также CloseFile). Кроме того, все, что вызывает InOutError (ChDir, MkDir, драм RmDir).

Заметно отсутствует в списке AssignFile, Эта функция на самом деле не выполняет никаких операций ввода-вывода. Он просто устанавливает запись файла так, чтобы Append, Reset, а также Rewrite будет знать, что делать.


Я должен отметить, что смотреть на исходный код - это просто вывод. $I директива контролирует, будет ли компилятор вставлять вызовы в __IOTest Функция в вашем собственном коде после вызова некоторых других функций. Эта функция проверяет значение InOutResи, если он не равен нулю, возникает ошибка времени выполнения (что может привести к исключению, если SysUtils включен в вашу программу). Мы не можем проверить исходный код, чтобы напрямую узнать, на какие функции влияют $I (так как он вызывается только в сгенерированном компилятором коде), поэтому мы действительно просто ищем, какие функции установлены InOutResс предположением, что они не будут делать это, если не будут знать, что компилятор проверит это позже.

Другие вопросы по тегам