Электронная библиотека книг Александра Фролова и Григория Фролова.
Shop2You.ru Создайте свой интернет-магазин
Библиотека
Братьев
Фроловых

Операционная система Microsoft Windows 3.1 для программиста

© Александр Фролов, Григорий Фролов
Том 13, М.: Диалог-МИФИ, 1993, 284 стр.

[Назад] [Содеожание] [Дальше]

4.1. Особенности работы с файлами в мультизадачной среде

В этом разделе мы расскажем о тех ограничениях, которые накладываются на методы работы с файлами в мультизадачной среде операционной системы Windows версии 3.1.

Файлы и обработка сообщений

Так как работа приложений Windows (и самой операционной системы Windows) основана на передаче и обработке сообщений, вся файловая активность приложения также начинается во время обработки какого-либо сообщения. Например, редактор текста загружает редактируемый файл, когда приходит сообщение от строки "Open..." меню "File".

С файлами можно работать по-разному.

Первый способ (используемый программами MS-DOS) заключается в том, чтобы открыть все нужные им файлы в начале работы программы и закрыть их перед завершением работы программы. Если, однако, программа работает с большим количеством файлов, ей может не хватить управляющих блоков DFCB, используемых MS-DOS для каждого открытого файла (см. 1 том "Библиотеки системного программиста", раздел 2.4 "Таблица файлов MS-DOS"). Количество таких блоков определяется оператором "FILES=" в файле config.sys.

Для более экономного использования управляющих блоков DFCB программы могут открывать и закрывать файлы по мере необходимости, сокращая таким образом количество файлов, открытых одновременно. Это второй способ.

Приложения Windows не должны держать файлы открытыми на протяжении всего времени своей работы. Более того, вся обработка файла должна выполнятся во время обработки одного сообщения. То есть обработчик сообщения должен открыть файл, выполнить над ним все нужные операции ввода/вывода, а затем закрыть файл. Есть и еще одно ограничение - необходимо закрыть все файлы перед выводом на экран немодальной или модальной диалоговой панели (в том числе и перед вызовом функции MessageBox).

Смысл этих ограничений заключается в том, что они не позволяют пользователю переключиться на другое приложение, если текущее приложение не закрыло все свои файлы.

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

Представьте себе, что ваше приложение открыло файл, расположенный на дискете. После этого пользователь переключился на другое приложение, которое также работает с дискетами. Для него потребовалось установить другую дискету и пользователь это сделал. Затем он снова переключился на первое приложение, которое продолжило, например, прерванную операцию записи. Но теперь эта операция будет выполняться с другой дискетой, в результате чего обе дискеты скорее всего придется форматировать.

Поэтому приложения Windows должны придерживаться следующего правила:

Все операции с файлом, такие как открытие файла, чтение/запись и закрытие, должны выполнятся во время обработки одного сообщения. Нельзя открывать файл в обработчике одного сообщения и закрывать его в обработчике другого сообщения.

Временные файлы

Программы MS-DOS иногда создают на диске временные файлы , задавая для них либо фиксированное имя, которое зависит от программы, либо имя, созданное на основе текущей даты и времени.

Первый способ непригоден для приложений Windows, так как в системе могут работать несколько копий одного приложения. Поэтому, если, например, две копии приложения SUPERCAD попытаются создать два временных файла с именем !suprcad.tmp, такая операция получится только у той копии приложения, которая попытается сделать это первой.

В составе программного интерфейса Windows имеется функция GetTempFileName , предназначенная для получения имени временного файла:

int WINAPI GetTempFileName(
  BYTE   bDriveLetter,
  LPCSTR lpszPrefixString,
  UINT   uUnique,
  LPSTR  lpszTempFileName);

Параметр bDriveLetter задает диск, на котором будет расположен временный файл. Если значение этого параметра равно нулю, временный файл будет создан на текущем диске.

Параметр lpszPrefixString должен содержать указатель на текстовую строку, содержащую префикс, который будет добавлен к имени временного файла. В префиксе необходимо использовать кодировку OEM.

Параметр uUnique должен содержать целое число, которое будет добавлено к префиксу для формирование имени временного файла. Если значение этого параметра равно нулю, Windows будет использовать число, полученное из текущего системного времени.

Подготовленный полный путь для временного файла будет записан в буфер размером не менее 144 байт, адрес которого передается функции через параметр lpszTempFileName. При этом будет использована кодировка OEM.

Функция GetTempFileName возвращает значение, переданное ей через параметр uUnique, или значение, вычисленное исходя из текущего системного времени, если значение параметра uUnique равно нулю.

Учтите, что функция GetTempFileName не создает временные файлы. За создание и удаление временных файлов отвечает само приложение.

Остановимся подробнее на выборе диска для создания временных файлов.

Приложение Windows должно разрешать пользователю назначить каталог, в котором будут расположены временный файлы. В этом случае пользователь может отвести для всех временных файлов отдельный логический или даже физический диск, что благоприятно скажется на производительности файловой системы.

Для назначения каталога в простейшем случае можно использовать переменную среды TEMP, устанавливаемую в файле autoexec.bat.

Если передать функции GetTempFileName в качестве параметра bDriveLetter нулевое значение, для определения диска, на котором будет расположен временный файл, используется следующий алгоритм.

Если определена переменная среды TEMP, для размещения временного файла используется диск, указанный в этой переменной.

Если переменная TEMP не определена, для размещения временного файла используется первый жесткий диск, обычно C:.

Вы можете в параметре bDriveLetter указать дополнительно константу TF_FORCEDRIVE, определенную в файле windows.h как 0x80. В этом случае для размещения файлов используется указанный в этом параметре диск без учета переменной среды TEMP или буквы, которой обозначается первый установленный в системе жесткий диск.

В программном интерфейсе Windows есть еще одна функция, которая может быть использована для создания временных файлов. Это функция GetTempDrive :

BYTE WINAPI GetTempDrive(char unused);

Параметр функции не используется.

Функция GetTempDrive возвращает имя диска, который можно использовать для создания временных файлов. Если в системе есть жесткие диски, функция возвращает букву, соответствующую первому диску (обычно C:). В противном случае возвращается имя текущего диска.

Таким образом, для приложений Windows можно сформулировать еще одно правило.

Для создания временных файлов используйте имена, полученные от функции GetTempFileName. Не используйте фиксированные имена, закодированные внутри приложений, так как в Windows можно запустить несколько копий одного приложения.

Кодировка OEM

Так как для работы с файлами операционная система Windows использует файловую систему MS-DOS, для указания пути к файлам и каталогам необходимо использовать кодировку OEM , принятую в MS-DOS. Так как Windows работает с кодировкой ANSI , в некоторых случаях необходимо выполнять соответствующие преобразования, вызывая функции AnsiToOem и OemToAnsi .

Однако при открытии файла с помощью функций OpenFile и _lopen, определенных в программном интерфейсе Windows, вы можете не беспокоиться о кодировке, так как эти функции выполняют сами все необходимые преобразования.

Итак, следующее правило.

Принимайте во внимание то обстоятельство, что Windows и MS-DOS используют разную кодировку. При необходимости выполняйте преобразования из кодировки ANSI в кодировку OEM и обратно.

[Назад] [Содеожание] [Дальше]