Форум программистов, компьютерный форум, киберфорум
Visual C++
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
 
Рейтинг 4.60/179: Рейтинг темы: голосов - 179, средняя оценка - 4.60
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62

С++ чтение секторов диска

27.02.2011, 22:36. Показов 34990. Ответов 31
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
как по очереди прочитать все сектора на диске?
по идее должна использоваться функция ReadFile(hDevice, buf, 512, &dwBytesRead, NULL); но где подставить номер сектора или как перебрать все?

и как из функции DeviceIoControl вытащить количество секторов

вот сам код до которого додумался, но далее буксую на месте, надеюсь на подсказку)

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
#include <iostream>
#include <windows.h>
 
using namespace std;
 
int main()
{
    HANDLE hDevice;               // handle to the drive to be examined
    DISK_GEOMETRY pdg;           // геометрическая структура дискового устройства
    BOOL bResult;                 // флажок общих результатов
    DWORD junk;                   // сбрасываем результаты
 
    byte buf[512];              //БУФФеР
    DWORD dwBytesRead;
 
 
 
    hDevice = CreateFile("\\\\.\\D:",  // открываемое устройство
                    0,                // нет доступа к устройству
                    FILE_SHARE_READ | // режим совместного использования
                    FILE_SHARE_WRITE, 
                    NULL,             // атрибуты безопасности по умолчанию
                    OPEN_EXISTING,    // расположение
                    0,                // атрибуты файла
                    NULL);            // не копировать атрибуты файла
 
    
    if (hDevice != INVALID_HANDLE_VALUE)
    {
 
 
        bResult = DeviceIoControl(hDevice,  // запрошенное устройство
                IOCTL_DISK_GET_DRIVE_GEOMETRY,  // выполняемая операция
                NULL, 0, // буфера ввода нет
                &pdg, sizeof(pdg),     // буфер вывода
                &junk,                 // # возвращено байтов
                (LPOVERLAPPED) NULL);   // синхронизация ввода/вывода (I/O)
 
 
 
 
        ReadFile(hDevice, buf, 512, &dwBytesRead, NULL); 
 
        CloseHandle(hDevice);
    }
    else cout << "Error Open " << endl;
 
    cin.get();
}
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
27.02.2011, 22:36
Ответы с готовыми решениями:

Чтение секторов жёсткого в DOS
Добрый вечер! Проблема заключается именно в том, что программа должна работать под DOS, и ей не важно что есть на диске и какая там...

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

Ремап секторов диска с AF
Понадобилось сделать ремап на своём винче, много бэдов и блоков с чтением &gt;600 ms (даже один с 56к ms!) Решил сделать через викторию, но,...

31
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
28.02.2011, 16:56
C++
1
2
3
4
5
6
7
8
9
10
typedef struct _DISK_GEOMETRY
{
    LARGE_INTEGER Cylinders; // Количество цилиндров
    MEDIA_TYPE MediaType;
    DWORD TracksPerCylinder; // Количество дорожек на цилиндр
    DWORD SectorsPerTrack;  // Количество секторов на дорожку
    DWORD BytesPerSector;
} DISK_GEOMETRY;
 
pdg.Cylinders * pdg.TracksPerCylinder * pdg.SectorsPerTrack
Произведение значений этих трех полей даст общее количество секторов

Добавлено через 23 минуты
Цитата Сообщение от partos1 Посмотреть сообщение
как по очереди прочитать все сектора на диске?
по идее должна использоваться функция ReadFile(hDevice, buf, 512, &dwBytesRead, NULL); но где подставить номер сектора или как перебрать все?
Если читать в цикле, то чтение выполняется от начала до конца файла (или дискового устройства). Указатель в файле (диске) сдвигается автоматически. Номер сектора здесь нигде не ставится. Сдвиг указателя осуществляется на количество прочитанных БАЙТ, а не секторов. Но мы то можем узнать, сколько байт в секторе. Обычно 512, но в новых дисках может быть и не так. Поэтому берем это значение из DISK_GEOMETRY pdg.BytesPerSector. Если нужен доступ с произвольного места используется SetFilePointer или SetFilePointerEx (этот сгодится для дисков с огромной емкостью).
Читать дисковые устройства нужно квантами кратными размеру сектора. Если сектор 512 байт, то и читать нужно по 512 байт. Но в целях оптимизации лучше увеличить это значение. Например, по 4096 байт.

Добавлено через 5 часов 46 минут
Кстати, открывается раздел дискового устройства, а запрашиваются сведения о самом дисковом устройстве.
Цитата Сообщение от partos1 Посмотреть сообщение
C++
1
2
hDevice = CreateFile("\\\\.\\D:", ...
bResult = DeviceIoControl(hDevice, IOCTL_DISK_GET_DRIVE_GEOMETRY ...
Т.е. то, что будет в структуре DISK_GEOMETRY pdg относится ко всему диску. А на диске может быть несколько разделов. Но даже если на нем будет только один раздел, то размер этого раздела не будет совпадать с размером самого диска. Так что если нужен образ всего диска (с MBR, всеми разделами, неразмеченным пространством), то нужно открывать "\\\\.\\PhysicalDriveX".

Попробуй выполнить запрос
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
PARTITION_INFORMATION pi;
 
if (!DeviceIoControl(hDevice,
    IOCTL_DISK_GET_PARTITION_INFO,
    NULL,
    0,
    &pi,
    sizeof (PARTITION_INFORMATION),
    &bytesReturned,
    (LPOVERLAPPED)NULL))
{
    cout << "Error: " << GetLastError() << endl;
}
И посмотри, что будет в pi.PartitionLength.QuadPart и сравни с pdg.Cylinders.QuadPart * pdg.TracksPerCylinder * pdg.SectorsPerTrack * pdg.BytesPerSector
1
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
28.02.2011, 21:52  [ТС]
спасибо
0
Модератор
Эксперт по электронике
8978 / 6744 / 921
Регистрация: 14.02.2011
Сообщений: 23,854
28.02.2011, 23:52
давненько я не занимался дисками (со времен DOS)
но помоему для ОС минимальным значением является не сектор а клястер
для IBM размер сектора 512 (по крайней мере других не видел)
С уважением Валерий

Добавлено через 1 минуту
под ОС я имел ввиду FAT(12,16,32) NTFS
0
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
01.03.2011, 08:55  [ТС]
а можно байты прочтенные функцией
C++
1
ReadFile(hDevice, buf, 512, &dwBytesRead, NULL);
преобразовать в 2 код лучше в 16 код и вывести в файл или сout
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
01.03.2011, 10:20
Цитата Сообщение от ValeryS Посмотреть сообщение
но помоему для ОС минимальным значением является не сектор а клястер
Здесь чтение непосредственно секторов, безотносительно к файловой системе.
Цитата Сообщение от ValeryS Посмотреть сообщение
для IBM размер сектора 512 (по крайней мере других не видел)
Уже существуют и другие (точно не помню, вроде бы 2048)

Добавлено через 2 минуты
partos1,
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
#include <iostream>
#include <windows.h>
 
int main()
{
    using namespace std;
 
    // Дескриптор файлового устройства (раздела диска).
    HANDLE partition = INVALID_HANDLE_VALUE;
    // Сведения о разделе.
    PARTITION_INFORMATION partitionInfo = {0};
    // Сведения о геометрии диска, на котором расположен раздел.
    DISK_GEOMETRY diskGeometry = {0};
 
    // Дескриптор файла для сохранения образа раздела.
    HANDLE file = INVALID_HANDLE_VALUE;
 
    // Буфер для чтения.
    BYTE* buffer = NULL;
    // Размер буфера.
    DWORD bufferSize = 0;
 
    // Количество возвращенных байт.
    DWORD bytesReturned = 0;
    // Количество записанных байт.
    DWORD bytesWritten = 0;
 
    // Результат выполнения.
    BOOL result = FALSE;
 
    // Открываем раздел диска.
    if ((partition = CreateFileA("\\\\.\\G:",
        GENERIC_READ,
        FILE_SHARE_READ | FILE_SHARE_WRITE,
        NULL,
        OPEN_EXISTING,
        0,
        NULL)) == INVALID_HANDLE_VALUE)
    {
        cout << "Error: " << GetLastError() << endl;
        return (-1);
    }
 
    // Запрашиваем сведения о геометрии диска, на котором расположен раздел.
    if (!DeviceIoControl(partition,
        IOCTL_DISK_GET_DRIVE_GEOMETRY,
        NULL,
        0,
        &diskGeometry,
        sizeof (DISK_GEOMETRY),
        &bytesReturned,
        (LPOVERLAPPED)NULL))
    {
        cout << "Error: " << GetLastError() << endl;
        CloseHandle(partition);
        return (-2);
    }
 
    // Запрашиваем сведения о разделе.
    if (!DeviceIoControl(partition,
        IOCTL_DISK_GET_PARTITION_INFO,
        NULL,
        0,
        &partitionInfo,
        sizeof (PARTITION_INFORMATION),
        &bytesReturned,
        (LPOVERLAPPED)NULL))
    {
        cout << "Error: " << GetLastError() << endl;
        CloseHandle(partition);
        return (-3);
    }
 
    // Размер раздела.
    cout << "Partition's size (in bytes): " << partitionInfo.PartitionLength.QuadPart << endl;
    // Размер диска отличается от размера раздела (причем, может значительно отличаться).
    cout << "Disk's size (in bytes):      " << (diskGeometry.Cylinders.QuadPart) *
        diskGeometry.TracksPerCylinder * diskGeometry.SectorsPerTrack *
        diskGeometry.BytesPerSector << endl;
    cout << "Num of cylinders:    " << diskGeometry.Cylinders.QuadPart << endl;
    cout << "Tracks per cylinder: " << diskGeometry.TracksPerCylinder << endl;
    cout << "Sectors per track:   " << diskGeometry.SectorsPerTrack << endl;
    cout << "Bytes per sector:    " << diskGeometry.BytesPerSector << endl;
    system("PAUSE");
 
    // Создание файла для сохранения образа.
    if ((file = CreateFileA("E:\\partition.img",
        GENERIC_READ | GENERIC_WRITE,
        0,
        NULL,
        CREATE_ALWAYS,
        0,
        NULL)) == INVALID_HANDLE_VALUE)
    {
        cout << "Error: " << GetLastError() << endl;
        CloseHandle(partition);
        return (-4);
    }
 
 
    // Резервируем место на диске для сохранения образа раздела. Пока у нас файл 0 байт.
    //
    // Здесь мы передвинем указатель в файле за границу его конца на расстояние равное
    // длине нашего раздела. Тем самым мы увеличили размер файла (но это пока теоретически).
    if (!SetFilePointerEx(file, partitionInfo.PartitionLength, NULL, FILE_BEGIN))
    {
        cout << "Error: " << GetLastError() << endl;
        CloseHandle(file);
        CloseHandle(partition);
        return (-5);
    }
    // А вот здесь мы фиксируем новый размер файла физически.
    if (!SetEndOfFile(file))
    {
        cout << "Error: " << GetLastError() << endl;
        CloseHandle(file);
        CloseHandle(partition);
        return (-6);
    }
 
 
    // Устанавливаем размер буфера.
    bufferSize = diskGeometry.BytesPerSector * diskGeometry.SectorsPerTrack;
    // Выделение памяти для буфера указанного размера.
    buffer = new BYTE[bufferSize];
 
    // Переменные используемые для отображения процесса копирования.
    int p = 0;
    __int64 s = 0;
    __int64 t = (partitionInfo.PartitionLength.QuadPart / bufferSize) / 100;
 
 
    // Устанавливаем указатель на начало файла.
    SetFilePointer(file, 0, NULL, FILE_BEGIN);
 
    // Копирование раздела в файл.
    do
    {
        // Чтение секторов раздела.
        result = ReadFile(partition, buffer, bufferSize, &bytesReturned, NULL);
        if (!result)
        {
            cout << "Error: " << GetLastError() << endl;
            delete[] buffer;
            CloseHandle(file);
            CloseHandle(partition);
            return (-7);
        }
 
        // Запись секторов в файл образа.
        result = WriteFile(file, buffer, bytesReturned, &bytesWritten, NULL);
        if (!result)
        {
            cout << "Error: " << GetLastError() << endl;
            delete[] buffer;
            CloseHandle(file);
            CloseHandle(partition);
            return (-8);
        }
 
        if (!(s++ % (t)))
        {
            system("CLS");
            cout << "Copied " << p++ << " %" << endl;
        }
    }
    while (result && bytesReturned);
 
    cout << "Partition copied successfully!\n";
 
    delete[] buffer;
    CloseHandle(file);
    CloseHandle(partition);
 
    system("PAUSE");
    return 0;
}
Попробуй. Открой потом образ в каком-нибудь дисковом редакторе, сравни с разделом диска
1
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
01.03.2011, 23:30  [ТС]
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
#include <iostream>
#include <windows.h>
 
using namespace std;
 
int main()
{
    HANDLE hDevice;               // handle to the drive to be examined
    HANDLE hFile;
    DISK_GEOMETRY pdg;           // геометрическая структура дискового устройства
    BOOL bResult;                 // флажок общих результатов
    DWORD junk;                   // сбрасываем результаты
    DWORD bytesReturned;
    int a,b,c;
    byte buf[512];              //БУФФеР
    DWORD dwBytesRead;
 
    typedef struct _DISK_GEOMETRY
    {
        LARGE_INTEGER Cylinders; // Количество цилиндров
        MEDIA_TYPE MediaType;
        DWORD TracksPerCylinder; // Количество дорожек на цилиндр
        DWORD SectorsPerTrack;  // Количество секторов на дорожку
        DWORD BytesPerSector;
    } DISK_GEOMETRY;
 
    hDevice = CreateFile("\\\\.\\F:", // открываемое устройство
                    0,                // нет доступа к устройству
                    FILE_SHARE_READ | // режим совместного использования
                    FILE_SHARE_WRITE, 
                    NULL,             // атрибуты безопасности по умолчанию
                    OPEN_EXISTING,    // расположение
                    0,                // атрибуты файла
                    NULL);            // не копировать атрибуты файла
 
    hFile = CreateFile("\\\\.\\H:",   // открываемое устройство
                    0,                // нет доступа к устройству
                    FILE_SHARE_READ | // режим совместного использования
                    FILE_SHARE_WRITE, 
                    NULL,             // атрибуты безопасности по умолчанию
                    OPEN_EXISTING,    // расположение
                    0,                // атрибуты файла
                    NULL);            // не копировать атрибуты файла
 
    if (hDevice != INVALID_HANDLE_VALUE)
    {
        cout << "         dear S.I. " << endl;
        cout << "    " << endl;
        cout << "I am glad to work with you" << endl;
 
        bResult = DeviceIoControl(hDevice,  // запрошенное устройство
                            IOCTL_DISK_GET_DRIVE_GEOMETRY,  // выполняемая операция
                            NULL, 0, // буфера ввода нет
                            &pdg, sizeof(pdg),     // буфер вывода
                            &junk,                 // # возвращено байтов
                            (LPOVERLAPPED) NULL);   // синхронизация ввода/вывода (I/O)
 
        if (bResult!=0)
        {
            cout << "bait v sektore = " << pdg.BytesPerSector << endl;
            cout << "size = " << pdg.Cylinders.QuadPart * pdg.TracksPerCylinder * pdg.SectorsPerTrack * pdg.BytesPerSector << endl;
        }
 
        a = pdg.Cylinders.QuadPart * pdg.TracksPerCylinder * pdg.SectorsPerTrack * pdg.BytesPerSector/512;
 
        cout << c << endl;
 
for (int i = 0; i < c; i++)
{
        ReadFile(hDevice, buf, 512, &dwBytesRead, NULL); 
 
        WriteFile(hFile, buf, 512, &dwBytesRead, NULL); 
                c =i/a*100;
        cout << i << "      " << c << endl;
}
        CloseHandle(hDevice);
    }
    else cout << "Error Open " << endl;
 
    cin.get();
}
программка должна копировать диск F на диск H, но работает не корректно
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
02.03.2011, 10:13
А зачем вы определяете структуру заново
C++
1
2
3
4
5
6
7
8
typedef struct _DISK_GEOMETRY
{
    LARGE_INTEGER Cylinders; // Количество цилиндров
    MEDIA_TYPE MediaType;
    DWORD TracksPerCylinder; // Количество дорожек на цилиндр
    DWORD SectorsPerTrack;  // Количество секторов на дорожку
    DWORD BytesPerSector;
} DISK_GEOMETRY;
В чем выражается некорректная работа?

Добавлено через 23 минуты
Я смотрю вы используете ограничение цикла i < c, а c у вас не инициализирована. Потом в цикле вы присваиваете c = i / a * 100. Все это очень подозрительно выглядит
Еще вы используете очень маленький буфер (512 байт) и выполняете вычисления в цикле. Это на скорость влияет (раздел 8ГБ будет час копироваться). Увеличьте буфер, уберите ненужные вычисления из цикла.
А лучше модифицируйте мой код (выше). Замените в нем file = CreateFileA("E:\\partition.img", на окртытие раздела и выкинте из него перемещения указателей в файле.
0
7 / 7 / 1
Регистрация: 02.03.2011
Сообщений: 19
02.03.2011, 11:06
Цитата Сообщение от bigredcat Посмотреть сообщение
Здесь чтение непосредственно секторов, безотносительно к файловой системе.

Уже существуют и другие (точно не помню, вроде бы 2048)
2048 у CD/DVD, по сути нет разницы, через DeviceIOControl можно получить размер сектора.
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
02.03.2011, 13:25
barmaley2005 Ошибся я, не 2048, а 4096. Но такие диски уже есть
Переход к жестким дискам нового формата с секторами размером 4 КБ
0
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
02.03.2011, 16:01  [ТС]
почему-то буксует открытие 2 го диска (не рабатывает функций createFile (////.//F)
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
#include <iostream>
#include <windows.h>
using namespace std;
 
int main()
{
        
 
        // Дескриптор файлового устройства (раздела диска).
        HANDLE partition = INVALID_HANDLE_VALUE;
        // Сведения о разделе.
        PARTITION_INFORMATION partitionInfo = {0};
        // Сведения о геометрии диска, на котором расположен раздел.
        DISK_GEOMETRY diskGeometry = {0};
 
        // Дескриптор файла для сохранения образа раздела.
        HANDLE file = INVALID_HANDLE_VALUE;
 
        // Буфер для чтения.
        BYTE* buffer = NULL;
        // Размер буфера.
        DWORD bufferSize = 0;
 
        // Количество возвращенных байт.
        DWORD bytesReturned = 0;
        // Количество записанных байт.
        DWORD bytesWritten = 0;
 
        // Результат выполнения.
        BOOL result;BOOL result1;
 
        // Открываем раздел диска читаем.
        partition = CreateFile("\\\\.\\H:",
                GENERIC_READ,
                FILE_SHARE_READ | FILE_SHARE_WRITE,
                NULL,
                OPEN_EXISTING,
                0,
                NULL);
                
        if (partition == INVALID_HANDLE_VALUE)
        {
                cout << "read disk (H) dont open" << endl;
                cout << "Error: " << GetLastError() << endl;
        }
 
                // Создание файла для сохранения  пишем.
        file = CreateFile("\\\\.\\F:",
                GENERIC_WRITE,
                0,
                NULL,
                CREATE_ALWAYS,
                0,
                NULL);
 
        if (file == INVALID_HANDLE_VALUE)
                {
                cout << "write disk (F) dont open" << endl;
                cout << "Error: " << GetLastError() << endl;
                }
 
 
        // Запрашиваем сведения о геометрии диска, на котором расположен раздел.
        if (!DeviceIoControl(partition,
                IOCTL_DISK_GET_DRIVE_GEOMETRY,
                NULL,
                0,
                &diskGeometry,
                sizeof (DISK_GEOMETRY),
                &bytesReturned,
                (LPOVERLAPPED)NULL))
        {
                cout << "Error: " << GetLastError() << endl;
                CloseHandle(partition);
                return (-2);
        }
 
        // Запрашиваем сведения о разделе.
        if (!DeviceIoControl(partition,
                IOCTL_DISK_GET_PARTITION_INFO,
                NULL,
                0,
                &partitionInfo,
                sizeof (PARTITION_INFORMATION),
                &bytesReturned,
                (LPOVERLAPPED)NULL))
        {
                cout << "Error: " << GetLastError() << endl;
                CloseHandle(partition);
                return (-3);
        }
 
        // Размер раздела.
        cout << "Partition's size (in bytes): " << partitionInfo.PartitionLength.QuadPart << endl;
        // Размер диска отличается от размера раздела (причем, может значительно отличаться).
        cout << "Disk's size (in bytes):      " << (diskGeometry.Cylinders.QuadPart) *
                diskGeometry.TracksPerCylinder * diskGeometry.SectorsPerTrack *
                diskGeometry.BytesPerSector << endl;
        cout << "Num of cylinders:    " << diskGeometry.Cylinders.QuadPart << endl;
        cout << "Tracks per cylinder: " << diskGeometry.TracksPerCylinder << endl;
        cout << "Sectors per track:   " << diskGeometry.SectorsPerTrack << endl;
        cout << "Bytes per sector:    " << diskGeometry.BytesPerSector << endl;
        system("PAUSE");
 
 
  
        // Устанавливаем размер буфера.
        bufferSize = diskGeometry.BytesPerSector * diskGeometry.SectorsPerTrack;
        // Выделение памяти для буфера указанного размера.
        buffer = new BYTE[bufferSize];
 
        // Переменные используемые для отображения процесса копирования.
        int p = 0;
        __int64 s = 0;
        __int64 t = (partitionInfo.PartitionLength.QuadPart / bufferSize) / 100;
        cout << "t:    " << t << endl;
/*
 
        // Копирование раздела в файл.
        do
        {
                // Чтение секторов раздела.
                result = ReadFile(partition, buffer, bufferSize, &bytesReturned, NULL);
                if (!result)
                {
                        cout << "Error: " << GetLastError() << endl;
                        delete[] buffer;
                        CloseHandle(file);
                        CloseHandle(partition);
                        return (-7);
                }
 
 
                 // Запись секторов в файл образа.
                result1 = WriteFile(file, buffer, bytesReturned, &bytesWritten, NULL);
                if (!result1)
                {
                        cout << "Error: " << GetLastError() << endl;
                        delete[] buffer;
                        CloseHandle(file);
                        CloseHandle(partition);
                        return (-8);
                }
 
                if (!(s++ % (t)))
                {
                        system("CLS");
                        cout << "Copied " << p++ << " %" << endl;
                }
        }
        while (result && bytesReturned);
*/
        cout << "Partition copied successfully!\n";
 
        delete[] buffer;
        CloseHandle(file);
        CloseHandle(partition);
 
        system("PAUSE");
        return 0;
}
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
02.03.2011, 16:50
Я забыл про то, что файл реально создавался. Для дисковых устройств допустим только OPEN_EXISTING - открываем только существующий раздел.
C++
1
2
3
4
5
6
7
8
// Создание файла для сохранения  пишем.
file = CreateFile("\\\\.\\F:",
    GENERIC_WRITE,
    0,
    NULL,
    CREATE_ALWAYS, // <-- так нельзя, нужно OPEN_EXISTING
    0,
    NULL);
Да, и если что, то требуются права администратора.
И, конечно, данные раздела, на который пишешь, потеряешь. Любая ошибка может обернуться серьезными проблемамиО_о. Совету эксперементировать на виртуальной машине
1
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
02.03.2011, 17:47  [ТС]
теперь не хочет работать функция writefile
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
02.03.2011, 18:05
Цитата Сообщение от partos1 Посмотреть сообщение
теперь не хочет работать функция writefile
Код ошибки какой?
0
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
02.03.2011, 18:25  [ТС]
Цитата Сообщение от bigredcat Посмотреть сообщение
Код ошибки какой?
error 6


возвращает -8
0
7 / 7 / 1
Регистрация: 02.03.2011
Сообщений: 19
02.03.2011, 18:34
Цитата Сообщение от partos1 Посмотреть сообщение
error 6


возвращает -8
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
        char errMsg[65];
        DWORD dw = GetLastError(); 
 
        FormatMessageA(
            FORMAT_MESSAGE_FROM_SYSTEM |
            FORMAT_MESSAGE_IGNORE_INSERTS,
            NULL,
            dw,
            MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
            (LPSTR)&errMsg,
            sizeof(errMsg), NULL );
 
        std::cout << errMsg << std::endl;
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
02.03.2011, 18:42
Цитата Сообщение от partos1 Посмотреть сообщение
error 6
У вас некорректный хендл файла. Вы его не закрыли случаем? Покажите код
0
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
02.03.2011, 18:47  [ТС]
вот сам код
C
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
#include <iostream>
#include <windows.h>
using namespace std;
 
int main()
{
        
 
        // Дескриптор файлового устройства (раздела диска).
        HANDLE partition = INVALID_HANDLE_VALUE;
        // Сведения о разделе.
        PARTITION_INFORMATION partitionInfo = {0};
        // Сведения о геометрии диска, на котором расположен раздел.
        DISK_GEOMETRY diskGeometry = {0};
 
        // Дескриптор файла для сохранения образа раздела.
        HANDLE file = INVALID_HANDLE_VALUE;
 
        // Буфер для чтения.
        BYTE* buffer = NULL;
        // Размер буфера.
        DWORD bufferSize = 0;
 
        // Количество возвращенных байт.
        DWORD bytesReturned = 0;
        // Количество записанных байт.
        DWORD bytesWritten = 0;
 
        // Результат выполнения.
        BOOL result;BOOL result1;
 
        // Открываем раздел диска читаем.
        partition = CreateFile("\\\\.\\H:",
                GENERIC_READ,
                FILE_SHARE_READ | FILE_SHARE_WRITE,
                NULL,
                OPEN_EXISTING,
                0,
                NULL);
                
        if (partition == INVALID_HANDLE_VALUE)
        {
                cout << "read disk (H) dont open" << endl;
                cout << "Error: " << GetLastError() << endl;
        }
 
                // Создание файла для сохранения  пишем.
        file = CreateFile("\\\\.\\F:",
                GENERIC_WRITE,
                FILE_SHARE_READ|FILE_SHARE_WRITE,
                NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
 
 
        if (file == INVALID_HANDLE_VALUE)
                {
                cout << "write disk (F) dont open" << endl;
                cout << "Error: " << GetLastError() << endl;
                }
 
 
        // Запрашиваем сведения о геометрии диска, на котором расположен раздел.
        if (!DeviceIoControl(partition,
                IOCTL_DISK_GET_DRIVE_GEOMETRY,
                NULL,
                0,
                &diskGeometry,
                sizeof (DISK_GEOMETRY),
                &bytesReturned,
                (LPOVERLAPPED)NULL))
        {
                cout << "Error: " << GetLastError() << endl;
                CloseHandle(partition);
        }
 
        // Запрашиваем сведения о разделе.
        if (!DeviceIoControl(partition,
                IOCTL_DISK_GET_PARTITION_INFO,
                NULL,
                0,
                &partitionInfo,
                sizeof (PARTITION_INFORMATION),
                &bytesReturned,
                (LPOVERLAPPED)NULL))
        {
                cout << "Error: " << GetLastError() << endl;
                CloseHandle(partition);
        }
 
        // Размер раздела.
        cout << "Partition's size (in bytes): " << partitionInfo.PartitionLength.QuadPart << endl;
        // Размер диска отличается от размера раздела (причем, может значительно отличаться).
        cout << "Disk's size (in bytes):      " << (diskGeometry.Cylinders.QuadPart) *
                diskGeometry.TracksPerCylinder * diskGeometry.SectorsPerTrack *
                diskGeometry.BytesPerSector << endl;
        cout << "Num of cylinders:    " << diskGeometry.Cylinders.QuadPart << endl;
        cout << "Tracks per cylinder: " << diskGeometry.TracksPerCylinder << endl;
        cout << "Sectors per track:   " << diskGeometry.SectorsPerTrack << endl;
        cout << "Bytes per sector:    " << diskGeometry.BytesPerSector << endl;
        system("PAUSE");
 
 
  
        // Устанавливаем размер буфера.
        bufferSize = diskGeometry.BytesPerSector * diskGeometry.SectorsPerTrack;
        // Выделение памяти для буфера указанного размера.
        buffer = new BYTE[bufferSize];
 
        // Переменные используемые для отображения процесса копирования.
        int p = 0;
        __int64 s = 0;
        __int64 t = (partitionInfo.PartitionLength.QuadPart / bufferSize) / 100;
        cout << "t:    " << t << endl;
 
 
        // Копирование раздела в файл.
        do
        {
                // Чтение секторов раздела.
                result = ReadFile(partition, buffer, bufferSize, &bytesReturned, NULL);
                if (!result)
                {
                        cout << "Error: " << GetLastError() << endl;
                        delete[] buffer;
                        CloseHandle(file);
                        CloseHandle(partition);
                        return (-7);
                }
 
 
                 // Запись секторов в файл образа.
                result1 = WriteFile(file, buffer, bytesReturned, &bytesWritten, NULL);
                if (!result1)
                {
 
                        cout << "Error: " << GetLastError() << endl;
                        delete[] buffer;
                        CloseHandle(file);
                        CloseHandle(partition);
                        return (-8);
                }
 
                if (!(s++ % (t)))
                {
                        system("CLS");
                        cout << "Copied " << p++ << " %" << endl;
                }
        }
        while (result && bytesReturned);
 
        cout << "Partition copied successfully!\n";
 
        delete[] buffer;
        CloseHandle(file);
        CloseHandle(partition);
 
        system("PAUSE");
        return 0;
}
0
375 / 322 / 32
Регистрация: 24.02.2011
Сообщений: 1,512
Записей в блоге: 1
02.03.2011, 19:23
Странно, но у меня все работает. Сейчас специально добавил в VMware два отдельных диска (виртуальных конечно, с распределением под них дискового пространства), создал на каждом по разделу, задал разные метки, на первый добавил файл. Запустил программу. Все скопировалось. Только результаты были видны не сразу (и F5 не помогло), пришлось в Управлении дисками изменить букву диска (удалить букву, а потом добавить). И все OK. Оба диска стали с одинаковой меткой и файл на втором диске появился и содержимое в нем сохранилось.

У вас вобще процесс копирования не начинается? Вы копируете с флешки на флешку?
0
2 / 2 / 2
Регистрация: 14.11.2010
Сообщений: 62
02.03.2011, 19:33  [ТС]
да с флешки на флешку
цикл do while если функцию writefile убрать читает без проблем
при добавление writefile на первом такте работы валетает
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
02.03.2011, 19:33
Помогаю со студенческими работами здесь

Чтение секторов с CD
Как и многие программеры-извращенцы,решил написать свою ОС в учебных целях. Т.к. нынче флоппиков мало, сразу перешел к чтению секторов с...

Найти количество кластеров и секторов диска
Как найти количество кластеров и секторов локального диска? И возможно ли обойтись без WinApi?

Количество секторов, кластеров и серийник диска
необходимо определить кол-во секторов, кластеров, байт в кластере и серийник диска перерыл функции из серии &quot; DriveInfo HardDisk =...

У свежекупленного диска много секторов с задержкой
Здравствуйте! В связи с проблемами с HDD (https://www.cyberforum.ru/hdd/thread1935738.html) купил новый. Toshiba P300 1 TB. Установил на...

Чтение секторов на диске
Подскажите, как в приложении Win32 прочитать на дискете сектор с заданным цилидром головкой и поверхностью. Не через CreateFile! ...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
20
Ответ Создать тему
Новые блоги и статьи
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка.
Programma_Boinc 23.12.2025
Thinkpad X220 Tablet — это лучший бюджетный ноутбук для учёбы, точка. Рецензия / Мнение Это мой обзор планшета X220 с точки зрения школьника. Недавно я решила попытаться уменьшить свой. . .
PhpStorm 2025.3: WSL Terminal всегда стартует в ~
and_y87 14.12.2025
PhpStorm 2025. 3: WSL Terminal всегда стартует в ~ (home), игнорируя директорию проекта Симптом: После обновления до PhpStorm 2025. 3 встроенный терминал WSL открывается в домашней директории. . .
Как объединить две одинаковые БД Access с разными данными
VikBal 11.12.2025
Помогите пожалуйста !! Как объединить 2 одинаковые БД Access с разными данными.
Новый ноутбук
volvo 07.12.2025
Всем привет. По скидке в "черную пятницу" взял себе новый ноутбук Lenovo ThinkBook 16 G7 на Амазоне: Ryzen 5 7533HS 64 Gb DDR5 1Tb NVMe 16" Full HD Display Win11 Pro
Музыка, написанная Искусственным Интеллектом
volvo 04.12.2025
Всем привет. Некоторое время назад меня заинтересовало, что уже умеет ИИ в плане написания музыки для песен, и, собственно, исполнения этих самых песен. Стихов у нас много, уже вышли 4 книги, еще 3. . .
От async/await к виртуальным потокам в Python
IndentationError 23.11.2025
Армин Ронахер поставил под сомнение async/ await. Создатель Flask заявляет: цветные функции - провал, виртуальные потоки - решение. Не threading-динозавры, а новое поколение лёгких потоков. Откат?. . .
Поиск "дружественных имён" СОМ портов
Argus19 22.11.2025
Поиск "дружественных имён" СОМ портов На странице: https:/ / norseev. ru/ 2018/ 01/ 04/ comportlist_windows/ нашёл схожую тему. Там приведён код на С++, который показывает только имена СОМ портов, типа,. . .
Сколько Государство потратило денег на меня, обеспечивая инсулином.
Programma_Boinc 20.11.2025
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
Ломающие изменения в C#.NStar Alpha
Etyuhibosecyu 20.11.2025
Уже можно не только тестировать, но и пользоваться C#. NStar - писать оконные приложения, содержащие надписи, кнопки, текстовые поля и даже изображения, например, моя игра "Три в ряд" написана на этом. . .
Мысли в слух
kumehtar 18.11.2025
Кстати, совсем недавно имел разговор на тему медитаций с людьми. И обнаружил, что они вообще не понимают что такое медитация и зачем она нужна. Самые базовые вещи. Для них это - когда просто люди. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru