покластерная запись в файл
От: RedHair  
Дата: 14.10.04 15:40
Оценка:
У меня следующая проблема.
Создаю файл — CreateFile(). Записываю в него некоторые данные, которые представляют собой строки в ANSI — WriteFile(). Это происходит на диске с размером кластера 4кб.
Далее копирую этот файл (xcopy) из командной строки на диск с размером кластера 512б.
Файл сильно фрагментируется. Мои текстовые фразы разрываются.
В итоге, когда я пытаюсь физически (открывая диск все тем же CreateFile()) на диске найти эти фразы — они не ищутся.
Примечание: если создавать файл заново (например в проводнике), и копировать туда содержание исходного файла — все прекрасно ищется?


Вопрос:
0. могут ли фразы в исходном файлек не искаться не из-за дефрагментации, а по другим причинам?
1. как добиться того, чтобы ничинать запись в файл непосредственно с начала кластера?
2. если нельзя добиться п1 — как сделать дефрагментацию?

МСДН предлагает решение на основе DeviceIOControl — в общих чертах: искать место на диске, где есть несколько свободных кластеров подряд и туда переписывать файл.

ИМХО — это достаточно муторно! И не поступать же мне так с каждым переписываемым файлом!

М.б. посоветуете, как заполнять прямо непосредственно кластеры, а не писать в файл по указателю?
Re: покластерная запись в файл
От: Alex Alexandrov США  
Дата: 14.10.04 19:04
Оценка:
Здравствуйте, RedHair, Вы писали:

R> У меня следующая проблема.

R> Создаю файл — CreateFile(). Записываю в него некоторые данные, которые
R> представляют собой строки в ANSI — WriteFile(). Это происходит на диске
R> с размером кластера 4кб. Далее копирую этот файл (xcopy) из командной
R> строки на диск с размером кластера 512б. Файл сильно фрагментируется.
R> Мои текстовые фразы разрываются. В итоге, когда я пытаюсь физически
R> (открывая диск все тем же CreateFile()) на диске найти эти фразы — они
R> не ищутся. Примечание: если создавать файл заново (например в
R> проводнике), и копировать туда содержание исходного файла — все
R> прекрасно ищется?
R>
R>
R> Вопрос:
R> 0. могут ли фразы в исходном файлек не искаться не из-за дефрагментации,
R> а по другим причинам? 1. как добиться того, чтобы ничинать запись в файл
R> непосредственно с начала кластера? 2. если нельзя добиться п1 — как
R> сделать дефрагментацию?
R>
R> МСДН предлагает решение на основе DeviceIOControl — в общих чертах:
R> искать место на диске, где есть несколько свободных кластеров подряд и
R> туда переписывать файл.
R>
R> ИМХО — это достаточно муторно! И не поступать же мне так с каждым
R> переписываемым файлом!
R>
R> М.б. посоветуете, как заполнять прямо непосредственно кластеры, а не
R> писать в файл по указателю?

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

-- Всего хорошего!
-- Alex Alexandrov, e-mail: alex_alexandrov(at)fromru(dot)com
Posted via RSDN NNTP Server 1.9 gamma
It's kind of fun to do the impossible (Walt Disney)
Re[2]: покластерная запись в файл
От: RedHair  
Дата: 15.10.04 05:47
Оценка:
Здравствуйте, Alex Alexandrov, Вы писали:

AA>При использовании CreateFile и прочих сервисов операционной системы совершенно необязательно думать о проблемах фрагментации данных. Это совершенно другой уровень абстракции и помочь ему Вы вряд ли сможете. Все, что Вы написали про проблемы с фрагментированностью файла — ерунда полная. Ищите более банальную ошибку.


Ерунда полная — это хороший ответ

Допустим, что ошибка вполне банальная. Но вопрос не снимается — можно ли к-л более-менее простыми методами управлять записью в конкретные кластеры?
Например, если мне, наоборот, необходимо фрагментировать файл, ну скажем для тестирования к-н навороченного дефрагментатора.

Меня не сильно напряжет спуститься на уровень ниже — вот только как?
Re: покластерная запись в файл
От: Pavel Dvorkin Россия  
Дата: 15.10.04 06:10
Оценка:
Привет!

RedHair wrote:
>
> У меня следующая проблема.
> Создаю файл — CreateFile(). Записываю в него некоторые данные, которые представляют собой строки в ANSI — WriteFile(). Это происходит на диске с размером кластера 4кб.

Мимоходом маленькое замечание. WriteFile не знает никаких строк в ANSI,
она только записвает байты. Уверен, что здесь все в порядке ?

> Далее копирую этот файл (xcopy) из командной строки на диск с размером кластера 512б.

> Файл сильно фрагментируется. Мои текстовые фразы разрываются.
> В итоге, когда я пытаюсь физически (открывая диск все тем же CreateFile()) на диске найти эти фразы — они не ищутся.

Этого не может быть, потому что это противоречит основным принципам.
Почему — об этом достаточно написал Alex Alexandrov, повторяться не
буду. Насчет того, что ты не можешь найти свои фразы

1. Проверь, есть ли они в оригинале.
2. Сравни оригинал и копию —

C:> fc original.txt copy.txt (если файлы текстовые)

C:> fc original.dat copy.dat /B (если файлы двоичные)


>Примечание: если создавать файл заново (например в проводнике), и копировать туда содержание

исходного файла — все прекрасно ищется?

Это как так ? Создавать файл в проводнике и после этого копировать туда
содержимое ? Я такого в проводнике делать не умею. Проводник просто
копирует файл, затирая прежний файл.


>

> Вопрос:
> 0. могут ли фразы в исходном файлек не искаться не из-за дефрагментации, а по другим причинам?

Могут. Причина одна — записал не то

> 1. как добиться того, чтобы ничинать запись в файл непосредственно с начала кластера?


Кластеры тебя волновать не должны. Работа с кластерами АБСОЛЮТНО
ПРОЗРАЧНА для приложений, их не касается, какие кластеры выделяются.
Содержимое файла от расположения кластеров не зависит.

> 2. если нельзя добиться п1 — как сделать дефрагментацию?


Не стоит. Лучше ищи ошибку у себя.

--
With best regards,
Pavel Dvorkin
Posted via RSDN NNTP Server 1.9 gamma
With best regards
Pavel Dvorkin
Re[3]: покластерная запись в файл
От: Guard_h4s Россия  
Дата: 15.10.04 06:12
Оценка:
Здравствуйте, RedHair, Вы писали:

RH>Меня не сильно напряжет спуститься на уровень ниже — вот только как?


На уровне WinAPI вызовов — никак. Да очень ли это нужно?
Странные у вас проблемы с файлом. Такого быть не должно.
Re[2]: покластерная запись в файл
От: Злость Россия  
Дата: 15.10.04 06:37
Оценка:
Здравствуйте, Pavel Dvorkin, Вы писали:

[skip]
>>Примечание: если создавать файл заново (например в проводнике), и копировать туда содержание
PD>исходного файла — все прекрасно ищется?

PD>Это как так ? Создавать файл в проводнике и после этого копировать туда

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

Могу подсказать — Файл -> Создать -> Текстовой документ (что там вызывается уже другой разговор).

А вот то что у автора топика — скорее всего ошибка при записи — это да.
Правда, Ложь — мне все одно — я имею свое мнение.
Если функция недокументированна — это не значит, что ее не используют все ваши конкуренты в своих продуктах.
Любой строй переходный и отрицать это значит быть закостенелым идиотом.
Re[3]: покластерная запись в файл
От: Pavel Dvorkin Россия  
Дата: 15.10.04 06:53
Оценка:
Привет!

Злость wrote:
>
> Здравствуйте, Pavel Dvorkin, Вы писали:
>
> [skip]
> >>Примечание: если создавать файл заново (например в проводнике), и копировать туда содержание
> PD>исходного файла — все прекрасно ищется?
>
> PD>Это как так ? Создавать файл в проводнике и после этого копировать туда
> PD>содержимое ? Я такого в проводнике делать не умею. Проводник просто
> PD>копирует файл, затирая прежний файл.
>
> Могу подсказать — Файл -> Создать -> Текстовой документ (что там вызывается уже другой разговор).

Как файл в проводнике создать — это я понимаю, а как потом туда
копировать ?

Еще раз!
>если создавать файл заново (например в проводнике), и копировать туда содержание
>исходного файла — все прекрасно ищется?

Я это мог бы понять так —

CreateFile — создали файл и получили хендл.
По этому хендлу копируем из другого файла (не важно как)

На эти два действия нужны 2 пункта меню (или что-то аналогичное)

Но если в проводнике начнут про открытие файлов и хендлы говорить — мир
рехнется!

Я только одну программу от MS знаю, где можно хендлы явно открывать —
Disk Probe. Но она не для пользователей.


--
With best regards,
Pavel Dvorkin
Posted via RSDN NNTP Server 1.9 gamma
With best regards
Pavel Dvorkin
Re[2]: покластерная запись в файл
От: RedHair  
Дата: 15.10.04 08:14
Оценка:
Во-первых, большое спасибо за ответ.

Во-вторых.

В который раз убеждаюсь, что прежде чем что-то спрашивать надо двадцать пять тысяч раз проверить себя, и изучить все что только можно изучить.
Проблема действительно оказалась гораздо проще — бардак с кодировками. Строчки были ансишные, программка-искалка искали юникодовские. Путем простых телодвижение все стало искаться нормально.

PD>Мимоходом маленькое замечание. WriteFile не знает никаких строк в ANSI,

PD>она только записвает байты. Уверен, что здесь все в порядке ?

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

>> Далее копирую этот файл (xcopy) из командной строки на диск с размером кластера 512б.

>> Файл сильно фрагментируется. Мои текстовые фразы разрываются.
>> В итоге, когда я пытаюсь физически (открывая диск все тем же CreateFile()) на диске найти эти фразы — они не ищутся.

PD>Этого не может быть, потому что это противоречит основным принципам.

PD>Почему — об этом достаточно написал Alex Alexandrov, повторяться не
PD>буду. Насчет того, что ты не можешь найти свои фразы

Почему бы этому не быть? Представьте себе ситуацию — вы создаете большой (100кб, к примеру) файл, куда пишете некие данные. Вполне возможна ситуация, когда файл фрагментируется и данные разорвутся — на физическом уровне.
Далее, если открыть диск (не файл), и начать в нем искать кусок своих данных, вы вполне его не найдете, ведь первая треть его находится в одном кластере, а вторая — совсем в другом, не идущем непосредственно за первым.

>> 0. могут ли фразы в исходном файлек не искаться не из-за дефрагментации, а по другим причинам?


PD>Могут. Причина одна — записал не то


Признаю себя ослом!!!

>> 1. как добиться того, чтобы ничинать запись в файл непосредственно с начала кластера?


PD>Кластеры тебя волновать не должны. Работа с кластерами АБСОЛЮТНО

PD>ПРОЗРАЧНА для приложений, их не касается, какие кластеры выделяются.
PD>Содержимое файла от расположения кластеров не зависит.

Большое спасибо!
Итак ясно, что таблица размещения хранит цепочку кластеров и все данные на уровне приложений будут непрерывны.
Вопрос, тем не менее, остается достаточно интересным, с познавательной точки зрения!!!
Re[3]: покластерная запись в файл
От: Pavel Dvorkin Россия  
Дата: 15.10.04 09:42
Оценка: 6 (1)
Привет!

RedHair wrote:
> Почему бы этому не быть? Представьте себе ситуацию — вы создаете большой (100кб, к примеру) файл, куда пишете некие данные. Вполне возможна ситуация, когда файл фрагментируется и данные разорвутся — на физическом уровне.

Ну 100 Кб — это не большой, а маленький файл. Большой — это 10 Гбайт
. Но дело, конечно, не в этом.

> Далее, если открыть диск (не файл), и начать в нем искать кусок своих данных, вы вполне его не найдете, ведь первая треть его находится в одном кластере, а вторая — совсем в другом, не идущем непосредственно за первым.


Вот здесь твоя ошибка (точнее, непонимание) и заключается.
Работа с файлами идет на разных уровнях.
A.На нашем уровне (обычное Win32 приложение) файл — это
последовательность байт определенного размера. Все. Больше ничего. Как
они там хранятся — НАС ВООБЩЕ НЕ КАСАЕТСЯ. Хоть в кластерах, хоть с
помощью духа святого. Мы этого не знаем, не хотим знать и не имеем права
знать. В любом случае, для нас файл непрерывный. Других НЕ БЫВАЕТ.

B.А на уровне ниже можно обсуждать его ФИЗИЧЕСКОЕ размещение. Если HDD
или FDD — в кластерах. Если в сети — сетевой редиректор чего-то там
делает и откуда-то эти байты файла берет и куда-то записывает. Если он
от MS — одним способом. Если от Netware — совсем по-другому. Если файл
на CDROM — там тоже по-своему. Более того, файл может в действительности
находиться на ftp сервере (FtpGetFile) и для доступа к нему используется
ftp протокол, а где сам файл — о том только хозяин ftp сервера (который
вообще может быть машиной на Unix) знает.

C.А еще ниже — область электроники/оптики/магнитооптики. Там тебе
объяснят, что такое 0 и что такое 1 на винчестере, как реально
(намагниченности, интенсивности и т.п.) хранятся данные на носители. Это
уже физиков епархия.

Сейчас ты на уровне A. Поэтому уровни B и C тебя не касаются вообще.
Драйвер файловой системы или редиректор сети (они на уровне B) сделают
все, что надо, чтобы для тебя файл казался непрерывным.

А вот если сама начнешь писать драйвер файловой системы — тогда да,
тогда тебе придется думать о том, в каких кластерах (а может, и не
кластерах размещать данные и как сделать так, чтобы на уровне A их
видели непрерывными файлами. Но про уровень C даже здесь не надо думать.

А если переквалифицируешься в разработчики аппаратуры , то придется
узнать все про намагниченности, интенсивности и т.п., и сделать
аппаратуру так, чтобы на уровне B с ней могли работать.

Я упростил. В действительности уровень B состоит из ряда подуровней
(драйвер файловой системы, драйвер томов (кстати, он позволяет (о ужас!
хранить файл не только фрагментированным на диске, но хранить его
куски на разных дисках вообще), драйвер физического диска. И каждый из
этих подуровней ничего не знает о подуровне ниже и не хочет знать.

> Признаю себя ослом!!!


Не надо так. Все могут ошибаться

> Вопрос, тем не менее, остается достаточно интересным, с познавательной точки зрения!!!


А вот это уже серьезный вопрос.
В действительности все что я сказал, верно с одной поправкой. А именно —
фрагментирование может замедлить работу с файлом. Для меня он
непрерывный, так, но реально-то нет. Чем больше движений головки, тем
медленнее работа.
О дефрагментации см. MSDN, Defragmenting Files. Но прежде надо хорошо
понять, как файлы хранятся на томах NTFS, что такое VCN-LCN и т.д.

--
With best regards,
Pavel Dvorkin
Posted via RSDN NNTP Server 1.9 gamma
With best regards
Pavel Dvorkin
Re[4]: покластерная запись в файл
От: RedHair  
Дата: 15.10.04 10:56
Оценка:
Итак!

PD>Ну 100 Кб — это не большой, а маленький файл. Большой — это 10 Гбайт

PD>. Но дело, конечно, не в этом.

Большой — относительно размера кластера в смысле бОльше чем размер кластера.

>> Далее, если открыть диск (не файл), и начать в нем искать кусок своих данных, вы вполне его не найдете, ведь первая треть его находится в одном кластере, а вторая — совсем в другом, не идущем непосредственно за первым.


PD>Вот здесь твоя ошибка (точнее, непонимание) и заключается.

PD>Работа с файлами идет на разных уровнях.
PD>A.На нашем уровне (обычное Win32 приложение) файл — это
PD>последовательность байт определенного размера. Все. Больше ничего. Как
PD>они там хранятся — НАС ВООБЩЕ НЕ КАСАЕТСЯ. Хоть в кластерах, хоть с
PD>помощью духа святого. Мы этого не знаем, не хотим знать и не имеем права
PD>знать. В любом случае, для нас файл непрерывный. Других НЕ БЫВАЕТ.


Вполне возможно, я чего не понимаю. Постараюсь объяснить, что я имею в виду.
Представьте себе ситуацию: у вас есть некие данные в некоем файле. Допустим для вас они представляют собой расскз Тургенева. С физической точки зрения, это пресловутые нолики и единички.
Что случится с вашим рассказом при записи на сильно фрагментированные диск? — он тоже будет фрагментированным.
На физическом уровне фраза "возчик был невысокий, крепкого сложения" (точнее последовательность ноликов-единичек, ее представляющая) разорвется на (предположим) два куска "возчик был невы" и "сокий, крепкого сложения".
Далее представим ситуацию, когда вы файл случайно затерли. И теперь, единственная для вас возможность (на уровне А) восстановит ваш файл — открыть ваш диск — CreateFile("\\.\C",....) и считывать оттуда куски информации пока не найдете свою фразу.
Одна проблема — вы ее не найдете никогда- потому что физически она хранится разорвано.

Вот собственно, ход моих размышлений. Я не права?

PD>Я упростил. В действительности уровень B состоит из ряда подуровней

PD>(драйвер файловой системы, драйвер томов (кстати, он позволяет (о ужас!
PD> хранить файл не только фрагментированным на диске, но хранить его
PD>куски на разных дисках вообще), драйвер физического диска. И каждый из
PD>этих подуровней ничего не знает о подуровне ниже и не хочет знать.


Мдаа... Сильно. а где можно про это прочитать? МСДН Дефрагментация — уже читала.
Я бы не сказала, что там очень подробно...
Re[5]: покластерная запись в файл
От: Pavel Dvorkin Россия  
Дата: 15.10.04 11:39
Оценка:
Привет!

RedHair wrote:
> Вполне возможно, я чего не понимаю. Постараюсь объяснить, что я имею в виду.
> Представьте себе ситуацию: у вас есть некие данные в некоем файле. Допустим для вас они представляют собой расскз Тургенева. С физической точки зрения, это пресловутые нолики и единички.
> Что случится с вашим рассказом при записи на сильно фрагментированные диск? — он тоже будет фрагментированным.

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

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


Да, ну и пусть себе. Именно так.

Могу еще один пример с твоим Тургеневым привести. Представь себе, что
книги у тебя нет, а я тебе рассказ вслух читаю (файл читается). Читаю я,
разумеется, последовательно, рассказ ты получишь непрерывный, а в
действительности я начало из одной книге прочитал, середину из другой
(неважно почему), конец вообще по памяти выдал (когда я учился, нас
заставляли наизусть заучивать последний абзац из "Отцы и дети" . Для
меня (драйвера) Тургенев фрагментирован по двум книгам и моей памяти.
Для тебя (программы) непрерывен.


> Далее представим ситуацию, когда вы файл случайно затерли. И теперь, единственная для вас возможность (на уровне А) восстановит ваш файл — открыть ваш диск — CreateFile("\\.\C",....) и считывать оттуда куски информации пока не найдете свою фразу.

> Одна проблема — вы ее не найдете никогда- потому что физически она хранится разорвано.

Совершенно верно. Эта задача в общем случае не решается. То есть
восстановить файл в общем случае нельзя (в частных — очень даже можно, и
программ таких много). Нельзя потому, что информация о том, где он там
хранился (в каких кластерах) после стирания утеряна. Хотя сами кластеры
пока что не изменились (до новой записи в них, они же теперь свободные),
но мы не знаем, где они.

Хранения файла не непрерывным куском, а фрагментами — это плата за
удобство работы. Если файлы хранить непрерывными кусками, проблем больше
будет. Файлы создаются, удаляются, диск фрагментируется, и очень быстро
это приведет к тому. что на диске места свободного будет много, а взять
нельзя, так как нужного размера кусок не находится — очень много очень
маленьких участков. Ну и другая проблема — новый файл создается, какой у
него размер в конце концов будет — пока что неизвестно. Как место для
него резервировать ? А если он расти начнет, а дальше занято ?

Отсюда компромисс — файлы хранятся экстентами (кластерами и т.п.), а
если надо или хочется — можно их дефрагментировать. Но автоматически это
не делается.



> Мдаа... Сильно. а где можно про это прочитать? МСДН Дефрагментация — уже читала.


Если найдешь книгу "Соломон, Руссинович Внутренний мир Windows 2000" и
поймешь, что там написано (не обижайся — для начала будет
достаточно. Структура FAT и NTFS там в общих чертах описана.


--
With best regards,
Pavel Dvorkin
Posted via RSDN NNTP Server 1.9 gamma
With best regards
Pavel Dvorkin
Re[4]: покластерная запись в файл
От: Stanky  
Дата: 19.10.04 19:17
Оценка:
> На уровне WinAPI вызовов — никак.
>
А если:
CreateFile(TEXT("\\\\.\\PhysicalDriveX")...);

или
CreateFile(TEXT("\\.\X:")...);

Ну и дальше уже надо знать саму файловую систему!!!
Posted via RSDN NNTP Server 1.9 gamma
Не бойся выглядеть глупо, от этого ты выглядишь ещё глупей!!!
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.