Reactos
1/*
2 * SetupAPI DiskSpace functions
3 *
4 * Copyright 2004 CodeWeavers (Aric Stewart)
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19 */
20
21#include "setupapi_private.h"
22
23typedef struct {
24 WCHAR lpzName[20];
25 LONGLONG dwFreeSpace;
26 LONGLONG dwWantedSpace;
27} DRIVE_ENTRY, *LPDRIVE_ENTRY;
28
29typedef struct {
30 DWORD dwDriveCount;
31 DRIVE_ENTRY Drives[26];
32} DISKSPACELIST, *LPDISKSPACELIST;
33
34
35/***********************************************************************
36 * SetupCreateDiskSpaceListW (SETUPAPI.@)
37 */
38HDSKSPC WINAPI SetupCreateDiskSpaceListW(PVOID Reserved1, DWORD Reserved2, UINT Flags)
39{
40 WCHAR drives[255];
41 DWORD rc;
42 WCHAR *ptr;
43 LPDISKSPACELIST list=NULL;
44
45 TRACE("(%p, %u, 0x%08x)\n", Reserved1, Reserved2, Flags);
46
47 if (Reserved1 || Reserved2 || Flags & ~SPDSL_IGNORE_DISK)
48 {
49 SetLastError(ERROR_INVALID_PARAMETER);
50 return NULL;
51 }
52
53 rc = GetLogicalDriveStringsW(255,drives);
54
55 if (rc == 0)
56 return NULL;
57
58 list = HeapAlloc(GetProcessHeap(),0,sizeof(DISKSPACELIST));
59
60 list->dwDriveCount = 0;
61
62 ptr = drives;
63
64 while (*ptr)
65 {
66 DWORD type = GetDriveTypeW(ptr);
67 if (type == DRIVE_FIXED)
68 {
69 DWORD clusters;
70 DWORD sectors;
71 DWORD bytes;
72 DWORD total;
73 lstrcpyW(list->Drives[list->dwDriveCount].lpzName,ptr);
74 GetDiskFreeSpaceW(ptr,§ors,&bytes,&clusters,&total);
75 list->Drives[list->dwDriveCount].dwFreeSpace = clusters * sectors *
76 bytes;
77 list->Drives[list->dwDriveCount].dwWantedSpace = 0;
78 list->dwDriveCount++;
79 }
80 ptr += lstrlenW(ptr) + 1;
81 }
82 return list;
83}
84
85
86/***********************************************************************
87 * SetupCreateDiskSpaceListA (SETUPAPI.@)
88 */
89HDSKSPC WINAPI SetupCreateDiskSpaceListA(PVOID Reserved1, DWORD Reserved2, UINT Flags)
90{
91 return SetupCreateDiskSpaceListW( Reserved1, Reserved2, Flags );
92}
93
94/***********************************************************************
95 * SetupDuplicateDiskSpaceListW (SETUPAPI.@)
96 */
97HDSKSPC WINAPI SetupDuplicateDiskSpaceListW(HDSKSPC DiskSpace, PVOID Reserved1, DWORD Reserved2, UINT Flags)
98{
99 DISKSPACELIST *list_copy, *list_original = DiskSpace;
100
101 if (Reserved1 || Reserved2 || Flags)
102 {
103 SetLastError(ERROR_INVALID_PARAMETER);
104 return NULL;
105 }
106
107 if (!DiskSpace)
108 {
109 SetLastError(ERROR_INVALID_HANDLE);
110 return NULL;
111 }
112
113 list_copy = HeapAlloc(GetProcessHeap(), 0, sizeof(DISKSPACELIST));
114 if (!list_copy)
115 {
116 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
117 return NULL;
118 }
119
120 *list_copy = *list_original;
121
122 return list_copy;
123}
124
125/***********************************************************************
126 * SetupDuplicateDiskSpaceListA (SETUPAPI.@)
127 */
128HDSKSPC WINAPI SetupDuplicateDiskSpaceListA(HDSKSPC DiskSpace, PVOID Reserved1, DWORD Reserved2, UINT Flags)
129{
130 return SetupDuplicateDiskSpaceListW(DiskSpace, Reserved1, Reserved2, Flags);
131}
132
133/***********************************************************************
134 * SetupAddInstallSectionToDiskSpaceListA (SETUPAPI.@)
135 */
136BOOL WINAPI SetupAddInstallSectionToDiskSpaceListA(HDSKSPC DiskSpace,
137 HINF InfHandle, HINF LayoutInfHandle,
138 LPCSTR SectionName, PVOID Reserved1, UINT Reserved2)
139{
140 FIXME ("Stub\n");
141 return TRUE;
142}
143
144/***********************************************************************
145* SetupQuerySpaceRequiredOnDriveW (SETUPAPI.@)
146*/
147BOOL WINAPI SetupQuerySpaceRequiredOnDriveW(HDSKSPC DiskSpace,
148 LPCWSTR DriveSpec, LONGLONG *SpaceRequired,
149 PVOID Reserved1, UINT Reserved2)
150{
151 WCHAR *driveW;
152 unsigned int i;
153 LPDISKSPACELIST list = DiskSpace;
154 BOOL rc = FALSE;
155 static const WCHAR bkslsh[]= {'\\',0};
156
157 if (!DiskSpace)
158 {
159 SetLastError(ERROR_INVALID_HANDLE);
160 return FALSE;
161 }
162
163 if (!DriveSpec)
164 {
165 SetLastError(ERROR_INVALID_PARAMETER);
166 return FALSE;
167 }
168
169 driveW = HeapAlloc(GetProcessHeap(), 0, (lstrlenW(DriveSpec) + 2) * sizeof(WCHAR));
170 if (!driveW)
171 {
172 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
173 return FALSE;
174 }
175
176 lstrcpyW(driveW,DriveSpec);
177 lstrcatW(driveW,bkslsh);
178
179 TRACE("Looking for drive %s\n",debugstr_w(driveW));
180
181 for (i = 0; i < list->dwDriveCount; i++)
182 {
183 TRACE("checking drive %s\n",debugstr_w(list->Drives[i].lpzName));
184 if (lstrcmpW(driveW,list->Drives[i].lpzName)==0)
185 {
186 rc = TRUE;
187 *SpaceRequired = list->Drives[i].dwWantedSpace;
188 break;
189 }
190 }
191
192 HeapFree(GetProcessHeap(), 0, driveW);
193
194 if (!rc) SetLastError(ERROR_INVALID_DRIVE);
195 return rc;
196}
197
198/***********************************************************************
199* SetupQuerySpaceRequiredOnDriveA (SETUPAPI.@)
200*/
201BOOL WINAPI SetupQuerySpaceRequiredOnDriveA(HDSKSPC DiskSpace,
202 LPCSTR DriveSpec, LONGLONG *SpaceRequired,
203 PVOID Reserved1, UINT Reserved2)
204{
205 DWORD len;
206 LPWSTR DriveSpecW;
207 BOOL ret;
208
209 /* The parameter validation checks are in a different order from the
210 * Unicode variant of SetupQuerySpaceRequiredOnDrive. */
211 if (!DriveSpec)
212 {
213 SetLastError(ERROR_INVALID_PARAMETER);
214 return FALSE;
215 }
216
217 if (!DiskSpace)
218 {
219 SetLastError(ERROR_INVALID_HANDLE);
220 return FALSE;
221 }
222
223 len = MultiByteToWideChar(CP_ACP, 0, DriveSpec, -1, NULL, 0);
224
225 DriveSpecW = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
226 if (!DriveSpecW)
227 {
228 SetLastError(ERROR_NOT_ENOUGH_MEMORY);
229 return FALSE;
230 }
231
232 MultiByteToWideChar(CP_ACP, 0, DriveSpec, -1, DriveSpecW, len);
233
234 ret = SetupQuerySpaceRequiredOnDriveW(DiskSpace, DriveSpecW, SpaceRequired,
235 Reserved1, Reserved2);
236
237 HeapFree(GetProcessHeap(), 0, DriveSpecW);
238
239 return ret;
240}
241
242/***********************************************************************
243* SetupDestroyDiskSpaceList (SETUPAPI.@)
244*/
245BOOL WINAPI SetupDestroyDiskSpaceList(HDSKSPC DiskSpace)
246{
247 LPDISKSPACELIST list = (LPDISKSPACELIST)DiskSpace;
248 HeapFree(GetProcessHeap(),0,list);
249 return TRUE;
250}
251
252/***********************************************************************
253* SetupAddToDiskSpaceListA (SETUPAPI.@)
254*/
255BOOL WINAPI SetupAddToDiskSpaceListA(HDSKSPC diskspace, PCSTR targetfile,
256 LONGLONG filesize, UINT operation,
257 PVOID reserved1, UINT reserved2)
258{
259 FIXME(": stub\n");
260 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
261 return FALSE;
262}
263
264/***********************************************************************
265* SetupAddToDiskSpaceListW (SETUPAPI.@)
266*/
267BOOL WINAPI SetupAddToDiskSpaceListW(HDSKSPC diskspace, PCWSTR targetfile,
268 LONGLONG filesize, UINT operation,
269 PVOID reserved1, UINT reserved2)
270{
271 FIXME(": stub\n");
272 SetLastError(ERROR_CALL_NOT_IMPLEMENTED);
273 return FALSE;
274}