Reactos
1/*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS VFAT filesystem library
4 * FILE: lib\fslib\vfatlib\common.c
5 * PURPOSE: Common code for Fat support
6 * PROGRAMMERS: Casper S. Hornstrup (chorns@users.sourceforge.net)
7 * Eric Kohl
8 * Hermes Belusca-Maito (hermes.belusca@sfr.fr)
9 */
10
11/* INCLUDES *******************************************************************/
12
13#include "vfatlib.h"
14
15#define NDEBUG
16#include <debug.h>
17
18/* FUNCTIONS ******************************************************************/
19
20ULONG
21GetShiftCount(IN ULONG Value)
22{
23 ULONG i = 1;
24
25 while (Value > 0)
26 {
27 i++;
28 Value /= 2;
29 }
30
31 return i - 2;
32}
33
34ULONG
35CalcVolumeSerialNumber(VOID)
36{
37 LARGE_INTEGER SystemTime;
38 TIME_FIELDS TimeFields;
39 ULONG Serial;
40 PUCHAR Buffer;
41
42 NtQuerySystemTime(&SystemTime);
43 RtlTimeToTimeFields(&SystemTime, &TimeFields);
44
45 Buffer = (PUCHAR)&Serial;
46 Buffer[0] = (UCHAR)(TimeFields.Year & 0xFF) + (UCHAR)(TimeFields.Hour & 0xFF);
47 Buffer[1] = (UCHAR)(TimeFields.Year >> 8) + (UCHAR)(TimeFields.Minute & 0xFF);
48 Buffer[2] = (UCHAR)(TimeFields.Month & 0xFF) + (UCHAR)(TimeFields.Second & 0xFF);
49 Buffer[3] = (UCHAR)(TimeFields.Day & 0xFF) + (UCHAR)(TimeFields.Milliseconds & 0xFF);
50
51 return Serial;
52}
53
54/***** Wipe function for FAT12, FAT16 and FAT32 formats *****/
55NTSTATUS
56FatWipeSectors(
57 IN HANDLE FileHandle,
58 IN ULONG TotalSectors,
59 IN ULONG SectorsPerCluster,
60 IN ULONG BytesPerSector,
61 IN OUT PFORMAT_CONTEXT Context)
62{
63 IO_STATUS_BLOCK IoStatusBlock;
64 PUCHAR Buffer;
65 LARGE_INTEGER FileOffset;
66 ULONGLONG Sector;
67 ULONG Length;
68 NTSTATUS Status;
69
70 Length = SectorsPerCluster * BytesPerSector;
71
72 /* Allocate buffer for the cluster */
73 Buffer = (PUCHAR)RtlAllocateHeap(RtlGetProcessHeap(),
74 HEAP_ZERO_MEMORY,
75 Length);
76 if (Buffer == NULL)
77 return STATUS_INSUFFICIENT_RESOURCES;
78
79 /* Wipe all clusters */
80 Sector = 0;
81 while (Sector + SectorsPerCluster < TotalSectors)
82 {
83 FileOffset.QuadPart = Sector * BytesPerSector;
84
85 Status = NtWriteFile(FileHandle,
86 NULL,
87 NULL,
88 NULL,
89 &IoStatusBlock,
90 Buffer,
91 Length,
92 &FileOffset,
93 NULL);
94 if (!NT_SUCCESS(Status))
95 {
96 DPRINT("NtWriteFile() failed (Status %lx)\n", Status);
97 goto done;
98 }
99
100 UpdateProgress(Context, SectorsPerCluster);
101
102 Sector += SectorsPerCluster;
103 }
104
105 /* Wipe the trailing space behind the last cluster */
106 if (Sector < TotalSectors)
107 {
108 DPRINT("Remaining sectors %lu\n", TotalSectors - Sector);
109
110 FileOffset.QuadPart = Sector * BytesPerSector;
111 Length = (TotalSectors - Sector) * BytesPerSector;
112
113 Status = NtWriteFile(FileHandle,
114 NULL,
115 NULL,
116 NULL,
117 &IoStatusBlock,
118 Buffer,
119 Length,
120 &FileOffset,
121 NULL);
122 if (!NT_SUCCESS(Status))
123 {
124 DPRINT("NtWriteFile() failed (Status %lx)\n", Status);
125 goto done;
126 }
127
128 UpdateProgress(Context, TotalSectors - Sector);
129 }
130
131done:
132 /* Free the buffer */
133 RtlFreeHeap(RtlGetProcessHeap(), 0, Buffer);
134 return Status;
135}
136
137/* EOF */