3 * Copyright (C) 2002 ReactOS Team
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
20 * COPYRIGHT: See COPYING in the top level directory
21 * PROJECT: ReactOS text-mode setup
22 * FILE: subsys/system/usetup/bootsup.c
23 * PURPOSE: Bootloader support functions
24 * PROGRAMMER: Eric Kohl
32 #define SECTORSIZE 512
34 /* FUNCTIONS ****************************************************************/
38 CreateCommonFreeLoaderSections(PINICACHE IniCache
)
40 PINICACHESECTION IniSection
;
42 /* Create "FREELOADER" section */
43 IniSection
= IniCacheAppendSection(IniCache
,
46 /* DefaultOS=ReactOS */
47 IniCacheInsertKey(IniSection
,
54 IniCacheInsertKey(IniSection
,
64 /* Create "Display" section */
65 IniSection
= IniCacheAppendSection(IniCache
,
68 /* TitleText=ReactOS Boot Manager */
69 IniCacheInsertKey(IniSection
,
73 L
"ReactOS Boot Manager");
75 /* StatusBarColor=Cyan */
76 IniCacheInsertKey(IniSection
,
82 /* StatusBarTextColor=Black */
83 IniCacheInsertKey(IniSection
,
86 L
"StatusBarTextColor",
89 /* BackdropTextColor=White */
90 IniCacheInsertKey(IniSection
,
96 /* BackdropColor=Blue */
97 IniCacheInsertKey(IniSection
,
103 /* BackdropFillStyle=Medium */
104 IniCacheInsertKey(IniSection
,
107 L
"BackdropFillStyle",
110 /* TitleBoxTextColor=White */
111 IniCacheInsertKey(IniSection
,
114 L
"TitleBoxTextColor",
117 /* TitleBoxColor=Red */
118 IniCacheInsertKey(IniSection
,
124 /* MessageBoxTextColor=White */
125 IniCacheInsertKey(IniSection
,
128 L
"MessageBoxTextColor",
131 /* MessageBoxColor=Blue */
132 IniCacheInsertKey(IniSection
,
138 /* MenuTextColor=White */
139 IniCacheInsertKey(IniSection
,
146 IniCacheInsertKey(IniSection
,
152 /* TextColor=Yellow */
153 IniCacheInsertKey(IniSection
,
159 /* SelectedTextColor=Black */
160 IniCacheInsertKey(IniSection
,
163 L
"SelectedTextColor",
166 /* SelectedColor=Gray */
167 IniCacheInsertKey(IniSection
,
176 CreateFreeLoaderIniForDos(PWCHAR IniPath
,
180 PINICACHESECTION IniSection
;
182 IniCache
= IniCacheCreate();
184 CreateCommonFreeLoaderSections(IniCache
);
186 /* Create "Operating Systems" section */
187 IniSection
= IniCacheAppendSection(IniCache
,
188 L
"Operating Systems");
190 /* REACTOS=ReactOS */
191 IniCacheInsertKey(IniSection
,
197 /* ReactOS_Debug="ReactOS (Debug)" */
198 IniCacheInsertKey(IniSection
,
202 L
"\"ReactOS (Debug)\"");
204 /* DOS=Dos/Windows */
205 IniCacheInsertKey(IniSection
,
211 /* Create "ReactOS" section */
212 IniSection
= IniCacheAppendSection(IniCache
,
215 /* BootType=ReactOS */
216 IniCacheInsertKey(IniSection
,
222 /* SystemPath=<ArcPath> */
223 IniCacheInsertKey(IniSection
,
229 /* Create "ReactOS_Debug" section */
230 IniSection
= IniCacheAppendSection(IniCache
,
233 /* BootType=ReactOS */
234 IniCacheInsertKey(IniSection
,
240 /* SystemPath=<ArcPath> */
241 IniCacheInsertKey(IniSection
,
247 /* Options=/DEBUGPORT=SCREEN /NOGUIBOOT */
248 IniCacheInsertKey(IniSection
,
252 L
"/DEBUGPORT=SCREEN /NOGUIBOOT");
254 /* Create "DOS" section */
255 IniSection
= IniCacheAppendSection(IniCache
,
258 /* BootType=BootSector */
259 IniCacheInsertKey(IniSection
,
266 IniCacheInsertKey(IniSection
,
272 /* BootPartition=1 */
273 IniCacheInsertKey(IniSection
,
279 /* BootSector=BOOTSECT.DOS */
280 IniCacheInsertKey(IniSection
,
286 IniCacheSave(IniCache
, IniPath
);
287 IniCacheDestroy(IniCache
);
289 return(STATUS_SUCCESS
);
294 CreateFreeLoaderIniForReactos(PWCHAR IniPath
,
298 PINICACHESECTION IniSection
;
300 IniCache
= IniCacheCreate();
302 CreateCommonFreeLoaderSections(IniCache
);
304 /* Create "Operating Systems" section */
305 IniSection
= IniCacheAppendSection(IniCache
,
306 L
"Operating Systems");
308 /* ReactOS="ReactOS" */
309 IniCacheInsertKey(IniSection
,
315 /* ReactOS_Debug="ReactOS (Debug)" */
316 IniCacheInsertKey(IniSection
,
320 L
"\"ReactOS (Debug)\"");
322 /* Create "ReactOS" section */
323 IniSection
= IniCacheAppendSection(IniCache
,
326 /* BootType=ReactOS */
327 IniCacheInsertKey(IniSection
,
333 /* SystemPath=<ArcPath> */
334 IniCacheInsertKey(IniSection
,
340 /* Create "ReactOS_Debug" section */
341 IniSection
= IniCacheAppendSection(IniCache
,
344 /* BootType=ReactOS */
345 IniCacheInsertKey(IniSection
,
351 /* SystemPath=<ArcPath> */
352 IniCacheInsertKey(IniSection
,
358 /* Options=/DEBUGPORT=SCREEN /NOGUIBOOT */
359 IniCacheInsertKey(IniSection
,
363 L
"/DEBUGPORT=COM1 /NOGUIBOOT");
365 /* Save the ini file */
366 IniCacheSave(IniCache
, IniPath
);
367 IniCacheDestroy(IniCache
);
369 return(STATUS_SUCCESS
);
374 UpdateFreeLoaderIni(PWCHAR IniPath
,
379 PINICACHESECTION IniSection
;
380 PINICACHESECTION OsIniSection
;
381 WCHAR SectionName
[80];
383 WCHAR SystemPath
[200];
384 WCHAR SectionName2
[200];
389 RtlInitUnicodeString(&Name
,
392 Status
= IniCacheLoad(&IniCache
,
395 if (!NT_SUCCESS(Status
))
398 /* Get "Operating Systems" section */
399 IniSection
= IniCacheGetSection(IniCache
,
400 L
"Operating Systems");
401 if (IniSection
== NULL
)
403 IniCacheDestroy(IniCache
);
404 return(STATUS_UNSUCCESSFUL
);
407 /* Find an existing usable or an unused section name */
409 wcscpy(SectionName
, L
"ReactOS");
410 wcscpy(OsName
, L
"\"ReactOS\"");
413 Status
= IniCacheGetKey(IniSection
,
416 if (!NT_SUCCESS(Status
))
419 /* Get operation system section */
420 if (KeyData
[0] == '"')
422 wcscpy(SectionName2
, &KeyData
[1]);
423 j
= wcslen(SectionName2
);
426 SectionName2
[j
-1] = 0;
431 wcscpy(SectionName2
, KeyData
);
434 OsIniSection
= IniCacheGetSection(IniCache
,
436 if (OsIniSection
!= NULL
)
438 BOOLEAN UseExistingEntry
= TRUE
;
441 Status
= IniCacheGetKey(OsIniSection
,
444 if (NT_SUCCESS(Status
))
447 || (_wcsicmp(KeyData
, L
"ReactOS") != 0
448 && _wcsicmp(KeyData
, L
"\"ReactOS\"") != 0))
450 /* This is not a ReactOS entry */
451 UseExistingEntry
= FALSE
;
456 UseExistingEntry
= FALSE
;
459 if (UseExistingEntry
)
461 /* BootType is ReactOS. Now check SystemPath */
462 Status
= IniCacheGetKey(OsIniSection
,
465 if (NT_SUCCESS(Status
))
467 swprintf(SystemPath
, L
"\"%S\"", ArcPath
);
469 || (_wcsicmp(KeyData
, ArcPath
) != 0
470 && _wcsicmp(KeyData
, SystemPath
) != 0))
472 /* This entry is a ReactOS entry, but the SystemRoot does not
473 match the one we are looking for */
474 UseExistingEntry
= FALSE
;
479 UseExistingEntry
= FALSE
;
483 if (UseExistingEntry
)
485 IniCacheDestroy(IniCache
);
486 return(STATUS_SUCCESS
);
490 swprintf(SectionName
, L
"ReactOS_%lu", i
);
491 swprintf(OsName
, L
"\"ReactOS %lu\"", i
);
495 /* <SectionName>=<OsName> */
496 IniCacheInsertKey(IniSection
,
502 /* Create <SectionName> section */
503 IniSection
= IniCacheAppendSection(IniCache
,
506 /* BootType=ReactOS */
507 IniCacheInsertKey(IniSection
,
513 /* SystemPath=<ArcPath> */
514 IniCacheInsertKey(IniSection
,
520 IniCacheSave(IniCache
, IniPath
);
521 IniCacheDestroy(IniCache
);
523 return(STATUS_SUCCESS
);
528 SaveCurrentBootSector(PWSTR RootPath
,
531 OBJECT_ATTRIBUTES ObjectAttributes
;
532 IO_STATUS_BLOCK IoStatusBlock
;
538 /* Allocate buffer for bootsector */
539 BootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
542 if (BootSector
== NULL
)
543 return(STATUS_INSUFFICIENT_RESOURCES
);
545 /* Read current boot sector into buffer */
546 RtlInitUnicodeString(&Name
,
549 InitializeObjectAttributes(&ObjectAttributes
,
551 OBJ_CASE_INSENSITIVE
,
555 Status
= NtOpenFile(&FileHandle
,
560 FILE_SYNCHRONOUS_IO_NONALERT
);
561 if (!NT_SUCCESS(Status
))
563 RtlFreeHeap(ProcessHeap
, 0, BootSector
);
567 Status
= NtReadFile(FileHandle
,
577 if (!NT_SUCCESS(Status
))
579 RtlFreeHeap(ProcessHeap
, 0, BootSector
);
583 /* Write bootsector to DstPath */
584 RtlInitUnicodeString(&Name
,
587 InitializeObjectAttributes(&ObjectAttributes
,
593 Status
= NtCreateFile(&FileHandle
,
598 FILE_ATTRIBUTE_NORMAL
,
601 FILE_SYNCHRONOUS_IO_NONALERT
| FILE_SEQUENTIAL_ONLY
,
604 if (!NT_SUCCESS(Status
))
606 RtlFreeHeap(ProcessHeap
, 0, BootSector
);
610 Status
= NtWriteFile(FileHandle
,
621 /* Free the new boot sector */
622 RtlFreeHeap(ProcessHeap
, 0, BootSector
);
629 InstallFat16BootCodeToFile(PWSTR SrcPath
,
633 OBJECT_ATTRIBUTES ObjectAttributes
;
634 IO_STATUS_BLOCK IoStatusBlock
;
638 PUCHAR OrigBootSector
;
639 PUCHAR NewBootSector
;
641 /* Allocate buffer for original bootsector */
642 OrigBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
645 if (OrigBootSector
== NULL
)
646 return(STATUS_INSUFFICIENT_RESOURCES
);
648 /* Read current boot sector into buffer */
649 RtlInitUnicodeString(&Name
,
652 InitializeObjectAttributes(&ObjectAttributes
,
654 OBJ_CASE_INSENSITIVE
,
658 Status
= NtOpenFile(&FileHandle
,
663 FILE_SYNCHRONOUS_IO_NONALERT
);
664 if (!NT_SUCCESS(Status
))
666 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
670 Status
= NtReadFile(FileHandle
,
680 if (!NT_SUCCESS(Status
))
682 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
687 /* Allocate buffer for new bootsector */
688 NewBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
691 if (NewBootSector
== NULL
)
693 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
694 return(STATUS_INSUFFICIENT_RESOURCES
);
697 /* Read new bootsector from SrcPath */
698 RtlInitUnicodeString(&Name
,
701 InitializeObjectAttributes(&ObjectAttributes
,
703 OBJ_CASE_INSENSITIVE
,
707 Status
= NtOpenFile(&FileHandle
,
712 FILE_SYNCHRONOUS_IO_NONALERT
);
713 if (!NT_SUCCESS(Status
))
715 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
716 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
720 Status
= NtReadFile(FileHandle
,
730 if (!NT_SUCCESS(Status
))
732 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
733 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
737 /* Adjust bootsector (copy a part of the FAT BPB) */
738 memcpy((NewBootSector
+ 11), (OrigBootSector
+ 11), 51 /*fat BPB length*/);
740 /* Free the original boot sector */
741 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
743 /* Write new bootsector to DstPath */
744 RtlInitUnicodeString(&Name
,
747 InitializeObjectAttributes(&ObjectAttributes
,
753 Status
= NtCreateFile(&FileHandle
,
758 FILE_ATTRIBUTE_NORMAL
,
761 FILE_SYNCHRONOUS_IO_NONALERT
| FILE_SEQUENTIAL_ONLY
,
764 if (!NT_SUCCESS(Status
))
766 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
771 FilePosition
.QuadPart
= 0;
773 Status
= NtWriteFile(FileHandle
,
784 /* Free the new boot sector */
785 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
792 InstallFat32BootCodeToFile(PWSTR SrcPath
,
796 OBJECT_ATTRIBUTES ObjectAttributes
;
797 IO_STATUS_BLOCK IoStatusBlock
;
801 PUCHAR OrigBootSector
;
802 PUCHAR NewBootSector
;
803 LARGE_INTEGER FileOffset
;
805 /* Allocate buffer for original bootsector */
806 OrigBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
809 if (OrigBootSector
== NULL
)
810 return(STATUS_INSUFFICIENT_RESOURCES
);
812 /* Read current boot sector into buffer */
813 RtlInitUnicodeString(&Name
,
816 InitializeObjectAttributes(&ObjectAttributes
,
818 OBJ_CASE_INSENSITIVE
,
822 Status
= NtOpenFile(&FileHandle
,
827 FILE_SYNCHRONOUS_IO_NONALERT
);
828 if (!NT_SUCCESS(Status
))
830 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
834 Status
= NtReadFile(FileHandle
,
844 if (!NT_SUCCESS(Status
))
847 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
851 /* Allocate buffer for new bootsector (2 sectors) */
852 NewBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
855 if (NewBootSector
== NULL
)
857 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
858 return(STATUS_INSUFFICIENT_RESOURCES
);
861 /* Read new bootsector from SrcPath */
862 RtlInitUnicodeString(&Name
,
865 InitializeObjectAttributes(&ObjectAttributes
,
867 OBJ_CASE_INSENSITIVE
,
871 Status
= NtOpenFile(&FileHandle
,
876 FILE_SYNCHRONOUS_IO_NONALERT
);
877 if (!NT_SUCCESS(Status
))
879 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
880 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
884 Status
= NtReadFile(FileHandle
,
894 if (!NT_SUCCESS(Status
))
896 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
897 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
901 /* Adjust bootsector (copy a part of the FAT32 BPB) */
902 memcpy((NewBootSector
+ 3),
903 (OrigBootSector
+ 3),
904 87); /* FAT32 BPB length */
906 /* Disable the backup boot sector */
907 NewBootSector
[0x32] = 0x00;
908 NewBootSector
[0x33] = 0x00;
910 /* Free the original boot sector */
911 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
913 /* Write the first sector of the new bootcode to DstPath */
914 RtlInitUnicodeString(&Name
,
917 InitializeObjectAttributes(&ObjectAttributes
,
923 Status
= NtCreateFile(&FileHandle
,
928 FILE_ATTRIBUTE_NORMAL
,
931 FILE_SYNCHRONOUS_IO_NONALERT
| FILE_SEQUENTIAL_ONLY
,
934 if (!NT_SUCCESS(Status
))
936 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
940 Status
= NtWriteFile(FileHandle
,
950 if (!NT_SUCCESS(Status
))
952 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
956 /* Write the second sector of the new bootcode to boot disk sector 14 */
957 RtlInitUnicodeString(&Name
,
960 InitializeObjectAttributes(&ObjectAttributes
,
966 Status
= NtOpenFile(&FileHandle
,
971 FILE_SYNCHRONOUS_IO_NONALERT
);
972 if (!NT_SUCCESS(Status
))
974 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
978 FileOffset
.QuadPart
= (ULONGLONG
)(14 * SECTORSIZE
);
979 Status
= NtWriteFile(FileHandle
,
984 (NewBootSector
+ SECTORSIZE
),
988 if (!NT_SUCCESS(Status
))
993 /* Free the new boot sector */
994 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1001 InstallMbrBootCodeToDisk (PWSTR SrcPath
,
1004 OBJECT_ATTRIBUTES ObjectAttributes
;
1005 IO_STATUS_BLOCK IoStatusBlock
;
1006 UNICODE_STRING Name
;
1009 PPARTITION_SECTOR OrigBootSector
;
1010 PPARTITION_SECTOR NewBootSector
;
1012 /* Allocate buffer for original bootsector */
1013 OrigBootSector
= (PPARTITION_SECTOR
)RtlAllocateHeap(ProcessHeap
,
1015 sizeof(PARTITION_SECTOR
));
1016 if (OrigBootSector
== NULL
)
1017 return(STATUS_INSUFFICIENT_RESOURCES
);
1019 /* Read current boot sector into buffer */
1020 RtlInitUnicodeString(&Name
,
1023 InitializeObjectAttributes(&ObjectAttributes
,
1025 OBJ_CASE_INSENSITIVE
,
1029 Status
= NtOpenFile(&FileHandle
,
1034 FILE_SYNCHRONOUS_IO_NONALERT
);
1035 if (!NT_SUCCESS(Status
))
1037 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1041 Status
= NtReadFile(FileHandle
,
1050 NtClose(FileHandle
);
1051 if (!NT_SUCCESS(Status
))
1053 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1058 /* Allocate buffer for new bootsector */
1059 NewBootSector
= (PPARTITION_SECTOR
)RtlAllocateHeap(ProcessHeap
,
1061 sizeof(PARTITION_SECTOR
));
1062 if (NewBootSector
== NULL
)
1064 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1065 return(STATUS_INSUFFICIENT_RESOURCES
);
1068 /* Read new bootsector from SrcPath */
1069 RtlInitUnicodeString(&Name
,
1072 InitializeObjectAttributes(&ObjectAttributes
,
1074 OBJ_CASE_INSENSITIVE
,
1078 Status
= NtOpenFile(&FileHandle
,
1083 FILE_SYNCHRONOUS_IO_NONALERT
);
1084 if (!NT_SUCCESS(Status
))
1086 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1087 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1091 Status
= NtReadFile(FileHandle
,
1097 sizeof(PARTITION_SECTOR
),
1100 NtClose(FileHandle
);
1101 if (!NT_SUCCESS(Status
))
1103 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1104 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1108 /* Copy partition table from old MBR to new */
1109 RtlCopyMemory (&NewBootSector
->Signature
,
1110 &OrigBootSector
->Signature
,
1111 sizeof(PARTITION_SECTOR
) - offsetof(PARTITION_SECTOR
, Signature
) /* Length of partition table */);
1113 /* Free the original boot sector */
1114 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1116 /* Write new bootsector to RootPath */
1117 RtlInitUnicodeString(&Name
,
1120 InitializeObjectAttributes(&ObjectAttributes
,
1126 Status
= NtOpenFile(&FileHandle
,
1131 FILE_SYNCHRONOUS_IO_NONALERT
| FILE_SEQUENTIAL_ONLY
);
1132 if (!NT_SUCCESS(Status
))
1134 DPRINT1("NtOpenFile() failed (Status %lx)\n", Status
);
1135 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1139 Status
= NtWriteFile(FileHandle
,
1148 NtClose(FileHandle
);
1150 /* Free the new boot sector */
1151 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1158 InstallFat16BootCodeToDisk(PWSTR SrcPath
,
1161 OBJECT_ATTRIBUTES ObjectAttributes
;
1162 IO_STATUS_BLOCK IoStatusBlock
;
1163 UNICODE_STRING Name
;
1166 PUCHAR OrigBootSector
;
1167 PUCHAR NewBootSector
;
1169 /* Allocate buffer for original bootsector */
1170 OrigBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
1173 if (OrigBootSector
== NULL
)
1174 return(STATUS_INSUFFICIENT_RESOURCES
);
1176 /* Read current boot sector into buffer */
1177 RtlInitUnicodeString(&Name
,
1180 InitializeObjectAttributes(&ObjectAttributes
,
1182 OBJ_CASE_INSENSITIVE
,
1186 Status
= NtOpenFile(&FileHandle
,
1191 FILE_SYNCHRONOUS_IO_NONALERT
);
1192 if (!NT_SUCCESS(Status
))
1194 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1198 Status
= NtReadFile(FileHandle
,
1207 NtClose(FileHandle
);
1208 if (!NT_SUCCESS(Status
))
1210 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1215 /* Allocate buffer for new bootsector */
1216 NewBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
1219 if (NewBootSector
== NULL
)
1221 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1222 return(STATUS_INSUFFICIENT_RESOURCES
);
1225 /* Read new bootsector from SrcPath */
1226 RtlInitUnicodeString(&Name
,
1229 InitializeObjectAttributes(&ObjectAttributes
,
1231 OBJ_CASE_INSENSITIVE
,
1235 Status
= NtOpenFile(&FileHandle
,
1240 FILE_SYNCHRONOUS_IO_NONALERT
);
1241 if (!NT_SUCCESS(Status
))
1243 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1244 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1248 Status
= NtReadFile(FileHandle
,
1257 NtClose(FileHandle
);
1258 if (!NT_SUCCESS(Status
))
1260 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1261 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1265 /* Adjust bootsector (copy a part of the FAT16 BPB) */
1266 memcpy((NewBootSector
+ 3),
1267 (OrigBootSector
+ 3),
1268 59); /* FAT16 BPB length*/
1270 /* Free the original boot sector */
1271 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1273 /* Write new bootsector to RootPath */
1274 RtlInitUnicodeString(&Name
,
1277 InitializeObjectAttributes(&ObjectAttributes
,
1283 Status
= NtOpenFile(&FileHandle
,
1288 FILE_SYNCHRONOUS_IO_NONALERT
| FILE_SEQUENTIAL_ONLY
);
1289 if (!NT_SUCCESS(Status
))
1291 DPRINT1("NtOpenFile() failed (Status %lx)\n", Status
);
1292 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1297 FilePosition
.QuadPart
= 0;
1299 Status
= NtWriteFile(FileHandle
,
1308 NtClose(FileHandle
);
1310 /* Free the new boot sector */
1311 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1318 InstallFat32BootCodeToDisk(PWSTR SrcPath
,
1321 OBJECT_ATTRIBUTES ObjectAttributes
;
1322 IO_STATUS_BLOCK IoStatusBlock
;
1323 UNICODE_STRING Name
;
1326 PUCHAR OrigBootSector
;
1327 PUCHAR NewBootSector
;
1328 LARGE_INTEGER FileOffset
;
1329 USHORT BackupBootSector
;
1331 /* Allocate buffer for original bootsector */
1332 OrigBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
1335 if (OrigBootSector
== NULL
)
1336 return(STATUS_INSUFFICIENT_RESOURCES
);
1338 /* Read current boot sector into buffer */
1339 RtlInitUnicodeString(&Name
,
1342 InitializeObjectAttributes(&ObjectAttributes
,
1344 OBJ_CASE_INSENSITIVE
,
1348 Status
= NtOpenFile(&FileHandle
,
1353 FILE_SYNCHRONOUS_IO_NONALERT
);
1354 if (!NT_SUCCESS(Status
))
1356 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1360 Status
= NtReadFile(FileHandle
,
1369 NtClose(FileHandle
);
1370 if (!NT_SUCCESS(Status
))
1372 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1377 /* Allocate buffer for new bootsector (2 sectors) */
1378 NewBootSector
= (PUCHAR
)RtlAllocateHeap(ProcessHeap
,
1381 if (NewBootSector
== NULL
)
1383 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1384 return(STATUS_INSUFFICIENT_RESOURCES
);
1387 /* Read new bootsector from SrcPath */
1388 RtlInitUnicodeString(&Name
,
1391 InitializeObjectAttributes(&ObjectAttributes
,
1393 OBJ_CASE_INSENSITIVE
,
1397 Status
= NtOpenFile(&FileHandle
,
1402 FILE_SYNCHRONOUS_IO_NONALERT
);
1403 if (!NT_SUCCESS(Status
))
1405 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1406 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1410 Status
= NtReadFile(FileHandle
,
1419 NtClose(FileHandle
);
1420 if (!NT_SUCCESS(Status
))
1422 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1423 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1427 /* Adjust bootsector (copy a part of the FAT32 BPB) */
1428 memcpy((NewBootSector
+ 3),
1429 (OrigBootSector
+ 3),
1430 87); /* FAT32 BPB length */
1432 /* Get the location of the backup boot sector */
1433 BackupBootSector
= (OrigBootSector
[0x33] << 8) + OrigBootSector
[0x32];
1435 /* Free the original boot sector */
1436 RtlFreeHeap(ProcessHeap
, 0, OrigBootSector
);
1438 /* Write the first sector of the new bootcode to DstPath */
1439 RtlInitUnicodeString(&Name
,
1442 InitializeObjectAttributes(&ObjectAttributes
,
1448 Status
= NtOpenFile(&FileHandle
,
1453 FILE_SYNCHRONOUS_IO_NONALERT
| FILE_SEQUENTIAL_ONLY
);
1454 if (!NT_SUCCESS(Status
))
1456 DPRINT1("NtOpenFile() failed (Status %lx)\n", Status
);
1457 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1461 /* Write sector 0 */
1462 FileOffset
.QuadPart
= 0ULL;
1463 Status
= NtWriteFile(FileHandle
,
1472 if (!NT_SUCCESS(Status
))
1474 DPRINT1("NtWriteFile() failed (Status %lx)\n", Status
);
1475 NtClose(FileHandle
);
1476 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1480 /* Write backup boot sector */
1481 if ((BackupBootSector
!= 0x0000) && (BackupBootSector
!= 0xFFFF))
1483 FileOffset
.QuadPart
= (ULONGLONG
)((ULONG
)BackupBootSector
* SECTORSIZE
);
1484 Status
= NtWriteFile(FileHandle
,
1493 if (!NT_SUCCESS(Status
))
1495 DPRINT1("NtWriteFile() failed (Status %lx)\n", Status
);
1496 NtClose(FileHandle
);
1497 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1502 /* Write sector 14 */
1503 FileOffset
.QuadPart
= (ULONGLONG
)(14 * SECTORSIZE
);
1504 Status
= NtWriteFile(FileHandle
,
1509 (NewBootSector
+ SECTORSIZE
),
1513 if (!NT_SUCCESS(Status
))
1515 DPRINT1("NtWriteFile() failed (Status %lx)\n", Status
);
1517 NtClose(FileHandle
);
1519 /* Free the new boot sector */
1520 RtlFreeHeap(ProcessHeap
, 0, NewBootSector
);
1527 UnprotectBootIni(PWSTR FileName
,
1530 UNICODE_STRING Name
;
1531 OBJECT_ATTRIBUTES ObjectAttributes
;
1532 IO_STATUS_BLOCK IoStatusBlock
;
1533 FILE_BASIC_INFORMATION FileInfo
;
1537 RtlInitUnicodeString(&Name
,
1540 InitializeObjectAttributes(&ObjectAttributes
,
1542 OBJ_CASE_INSENSITIVE
,
1546 Status
= NtOpenFile(&FileHandle
,
1547 GENERIC_READ
|GENERIC_WRITE
,
1551 FILE_SYNCHRONOUS_IO_NONALERT
);
1552 if (Status
== STATUS_NO_SUCH_FILE
)
1554 DPRINT1("NtOpenFile() failed (Status %lx)\n", Status
);
1556 return(STATUS_SUCCESS
);
1558 if (!NT_SUCCESS(Status
))
1560 DPRINT1("NtOpenFile() failed (Status %lx)\n", Status
);
1564 Status
= NtQueryInformationFile(FileHandle
,
1567 sizeof(FILE_BASIC_INFORMATION
),
1568 FileBasicInformation
);
1569 if (!NT_SUCCESS(Status
))
1571 DPRINT1("NtQueryInformationFile() failed (Status %lx)\n", Status
);
1572 NtClose(FileHandle
);
1576 *Attributes
= FileInfo
.FileAttributes
;
1578 /* Delete attributes SYSTEM, HIDDEN and READONLY */
1579 FileInfo
.FileAttributes
= FileInfo
.FileAttributes
&
1580 ~(FILE_ATTRIBUTE_SYSTEM
| FILE_ATTRIBUTE_HIDDEN
| FILE_ATTRIBUTE_READONLY
);
1582 Status
= NtSetInformationFile(FileHandle
,
1585 sizeof(FILE_BASIC_INFORMATION
),
1586 FileBasicInformation
);
1587 if (!NT_SUCCESS(Status
))
1589 DPRINT1("NtSetInformationFile() failed (Status %lx)\n", Status
);
1592 NtClose(FileHandle
);
1598 ProtectBootIni(PWSTR FileName
,
1601 UNICODE_STRING Name
;
1602 OBJECT_ATTRIBUTES ObjectAttributes
;
1603 IO_STATUS_BLOCK IoStatusBlock
;
1604 FILE_BASIC_INFORMATION FileInfo
;
1608 RtlInitUnicodeString(&Name
,
1611 InitializeObjectAttributes(&ObjectAttributes
,
1613 OBJ_CASE_INSENSITIVE
,
1617 Status
= NtOpenFile(&FileHandle
,
1618 GENERIC_READ
|GENERIC_WRITE
,
1622 FILE_SYNCHRONOUS_IO_NONALERT
);
1623 if (!NT_SUCCESS(Status
))
1625 DPRINT1("NtOpenFile() failed (Status %lx)\n", Status
);
1629 Status
= NtQueryInformationFile(FileHandle
,
1632 sizeof(FILE_BASIC_INFORMATION
),
1633 FileBasicInformation
);
1634 if (!NT_SUCCESS(Status
))
1636 DPRINT1("NtQueryInformationFile() failed (Status %lx)\n", Status
);
1637 NtClose(FileHandle
);
1641 FileInfo
.FileAttributes
= FileInfo
.FileAttributes
| Attributes
;
1643 Status
= NtSetInformationFile(FileHandle
,
1646 sizeof(FILE_BASIC_INFORMATION
),
1647 FileBasicInformation
);
1648 if (!NT_SUCCESS(Status
))
1650 DPRINT1("NtSetInformationFile() failed (Status %lx)\n", Status
);
1653 NtClose(FileHandle
);
1659 UpdateBootIni(PWSTR BootIniPath
,
1663 UNICODE_STRING Name
;
1664 PINICACHE Cache
= NULL
;
1665 PINICACHESECTION Section
= NULL
;
1667 ULONG FileAttribute
;
1668 PWCHAR OldValue
= NULL
;
1670 RtlInitUnicodeString(&Name
,
1673 Status
= IniCacheLoad(&Cache
,
1676 if (!NT_SUCCESS(Status
))
1681 Section
= IniCacheGetSection(Cache
,
1682 L
"operating systems");
1683 if (Section
== NULL
)
1685 IniCacheDestroy(Cache
);
1686 return(STATUS_UNSUCCESSFUL
);
1689 /* Check - maybe record already exists */
1690 Status
= IniCacheGetKey(Section
,
1694 /* If either key was not found, or contains something else - add new one */
1695 if (!NT_SUCCESS(Status
) || wcscmp(OldValue
, EntryValue
))
1697 IniCacheInsertKey(Section
,
1704 Status
= UnprotectBootIni(BootIniPath
,
1706 if (!NT_SUCCESS(Status
))
1708 IniCacheDestroy(Cache
);
1712 Status
= IniCacheSave(Cache
,
1714 if (!NT_SUCCESS(Status
))
1716 IniCacheDestroy(Cache
);
1720 FileAttribute
|= (FILE_ATTRIBUTE_SYSTEM
| FILE_ATTRIBUTE_HIDDEN
| FILE_ATTRIBUTE_READONLY
);
1721 Status
= ProtectBootIni(BootIniPath
,
1724 IniCacheDestroy(Cache
);
1731 CheckInstallFatBootcodeToPartition(PUNICODE_STRING SystemRootPath
)
1733 if (DoesFileExist(SystemRootPath
->Buffer
, L
"ntldr") ||
1734 DoesFileExist(SystemRootPath
->Buffer
, L
"boot.ini"))
1738 else if (DoesFileExist(SystemRootPath
->Buffer
, L
"io.sys") ||
1739 DoesFileExist(SystemRootPath
->Buffer
, L
"msdos.sys"))
1749 InstallFatBootcodeToPartition(PUNICODE_STRING SystemRootPath
,
1750 PUNICODE_STRING SourceRootPath
,
1751 PUNICODE_STRING DestinationArcPath
,
1752 UCHAR PartitionType
)
1754 WCHAR SrcPath
[MAX_PATH
];
1755 WCHAR DstPath
[MAX_PATH
];
1758 /* FAT or FAT32 partition */
1759 DPRINT1("System path: '%wZ'\n", SystemRootPath
);
1761 if (DoesFileExist(SystemRootPath
->Buffer
, L
"ntldr") == TRUE
||
1762 DoesFileExist(SystemRootPath
->Buffer
, L
"boot.ini") == TRUE
)
1764 /* Search root directory for 'ntldr' and 'boot.ini'. */
1765 DPRINT("Found Microsoft Windows NT/2000/XP boot loader\n");
1767 /* Copy FreeLoader to the boot partition */
1768 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1769 wcscat(SrcPath
, L
"\\loader\\freeldr.sys");
1770 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1771 wcscat(DstPath
, L
"\\freeldr.sys");
1773 DPRINT("Copy: %S ==> %S\n", SrcPath
, DstPath
);
1774 Status
= SetupCopyFile(SrcPath
, DstPath
);
1775 if (!NT_SUCCESS(Status
))
1777 DPRINT1("SetupCopyFile() failed (Status %lx)\n", Status
);
1781 /* Create or update freeldr.ini */
1782 if (DoesFileExist(SystemRootPath
->Buffer
, L
"freeldr.ini") == FALSE
)
1784 /* Create new 'freeldr.ini' */
1785 DPRINT1("Create new 'freeldr.ini'\n");
1786 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1787 wcscat(DstPath
, L
"\\freeldr.ini");
1789 Status
= CreateFreeLoaderIniForReactos(DstPath
,
1790 DestinationArcPath
->Buffer
);
1791 if (!NT_SUCCESS(Status
))
1793 DPRINT1("CreateFreeLoaderIniForReactos() failed (Status %lx)\n", Status
);
1797 /* Install new bootcode */
1798 if (PartitionType
== PARTITION_FAT32
||
1799 PartitionType
== PARTITION_FAT32_XINT13
)
1801 /* Install FAT32 bootcode */
1802 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1803 wcscat(SrcPath
, L
"\\loader\\fat32.bin");
1804 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1805 wcscat(DstPath
, L
"\\bootsect.ros");
1807 DPRINT1("Install FAT32 bootcode: %S ==> %S\n", SrcPath
, DstPath
);
1808 Status
= InstallFat32BootCodeToFile(SrcPath
,
1810 SystemRootPath
->Buffer
);
1811 if (!NT_SUCCESS(Status
))
1813 DPRINT1("InstallFat32BootCodeToFile() failed (Status %lx)\n", Status
);
1819 /* Install FAT16 bootcode */
1820 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1821 wcscat(SrcPath
, L
"\\loader\\fat.bin");
1822 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1823 wcscat(DstPath
, L
"\\bootsect.ros");
1825 DPRINT1("Install FAT bootcode: %S ==> %S\n", SrcPath
, DstPath
);
1826 Status
= InstallFat16BootCodeToFile(SrcPath
,
1828 SystemRootPath
->Buffer
);
1829 if (!NT_SUCCESS(Status
))
1831 DPRINT1("InstallFat16BootCodeToFile() failed (Status %lx)\n", Status
);
1838 /* Update existing 'freeldr.ini' */
1839 DPRINT1("Update existing 'freeldr.ini'\n");
1840 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1841 wcscat(DstPath
, L
"\\freeldr.ini");
1843 Status
= UpdateFreeLoaderIni(DstPath
,
1844 DestinationArcPath
->Buffer
);
1845 if (!NT_SUCCESS(Status
))
1847 DPRINT1("UpdateFreeLoaderIni() failed (Status %lx)\n", Status
);
1852 /* Update 'boot.ini' */
1853 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1854 wcscat(DstPath
, L
"\\boot.ini");
1856 DPRINT1("Update 'boot.ini': %S\n", DstPath
);
1857 Status
= UpdateBootIni(DstPath
,
1858 L
"C:\\bootsect.ros",
1860 if (!NT_SUCCESS(Status
))
1862 DPRINT1("UpdateBootIni() failed (Status %lx)\n", Status
);
1866 else if (DoesFileExist(SystemRootPath
->Buffer
, L
"io.sys") == TRUE
||
1867 DoesFileExist(SystemRootPath
->Buffer
, L
"msdos.sys") == TRUE
)
1869 /* Search for root directory for 'io.sys' and 'msdos.sys'. */
1870 DPRINT1("Found Microsoft DOS or Windows 9x boot loader\n");
1872 /* Copy FreeLoader to the boot partition */
1873 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1874 wcscat(SrcPath
, L
"\\loader\\freeldr.sys");
1875 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1876 wcscat(DstPath
, L
"\\freeldr.sys");
1878 DPRINT("Copy: %S ==> %S\n", SrcPath
, DstPath
);
1879 Status
= SetupCopyFile(SrcPath
, DstPath
);
1880 if (!NT_SUCCESS(Status
))
1882 DPRINT1("SetupCopyFile() failed (Status %lx)\n", Status
);
1886 /* Create or update 'freeldr.ini' */
1887 if (DoesFileExist(SystemRootPath
->Buffer
, L
"freeldr.ini") == FALSE
)
1889 /* Create new 'freeldr.ini' */
1890 DPRINT1("Create new 'freeldr.ini'\n");
1891 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1892 wcscat(DstPath
, L
"\\freeldr.ini");
1894 Status
= CreateFreeLoaderIniForDos(DstPath
,
1895 DestinationArcPath
->Buffer
);
1896 if (!NT_SUCCESS(Status
))
1898 DPRINT1("CreateFreeLoaderIniForDos() failed (Status %lx)\n", Status
);
1902 /* Save current bootsector as 'BOOTSECT.DOS' */
1903 wcscpy(SrcPath
, SystemRootPath
->Buffer
);
1904 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1905 wcscat(DstPath
, L
"\\bootsect.dos");
1907 DPRINT1("Save bootsector: %S ==> %S\n", SrcPath
, DstPath
);
1908 Status
= SaveCurrentBootSector(SrcPath
,
1910 if (!NT_SUCCESS(Status
))
1912 DPRINT1("SaveCurrentBootSector() failed (Status %lx)\n", Status
);
1916 /* Install new bootsector */
1917 if (PartitionType
== PARTITION_FAT32
||
1918 PartitionType
== PARTITION_FAT32_XINT13
)
1920 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1921 wcscat(SrcPath
, L
"\\loader\\fat32.bin");
1923 DPRINT1("Install FAT32 bootcode: %S ==> %S\n", SrcPath
, SystemRootPath
->Buffer
);
1924 Status
= InstallFat32BootCodeToDisk(SrcPath
,
1925 SystemRootPath
->Buffer
);
1926 if (!NT_SUCCESS(Status
))
1928 DPRINT1("InstallFat32BootCodeToDisk() failed (Status %lx)\n", Status
);
1934 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1935 wcscat(SrcPath
, L
"\\loader\\fat.bin");
1937 DPRINT1("Install FAT bootcode: %S ==> %S\n", SrcPath
, SystemRootPath
->Buffer
);
1938 Status
= InstallFat16BootCodeToDisk(SrcPath
,
1939 SystemRootPath
->Buffer
);
1940 if (!NT_SUCCESS(Status
))
1942 DPRINT1("InstallFat16BootCodeToDisk() failed (Status %lx)\n", Status
);
1949 /* Update existing 'freeldr.ini' */
1950 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1951 wcscat(DstPath
, L
"\\freeldr.ini");
1953 Status
= UpdateFreeLoaderIni(DstPath
,
1954 DestinationArcPath
->Buffer
);
1955 if (!NT_SUCCESS(Status
))
1957 DPRINT1("UpdateFreeLoaderIni() failed (Status %lx)\n", Status
);
1964 /* No or unknown boot loader */
1965 DPRINT1("No or unknown boot loader found\n");
1967 /* Copy FreeLoader to the boot partition */
1968 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
1969 wcscat(SrcPath
, L
"\\loader\\freeldr.sys");
1970 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1971 wcscat(DstPath
, L
"\\freeldr.sys");
1973 DPRINT1("Copy: %S ==> %S\n", SrcPath
, DstPath
);
1974 Status
= SetupCopyFile(SrcPath
, DstPath
);
1975 if (!NT_SUCCESS(Status
))
1977 DPRINT1("SetupCopyFile() failed (Status %lx)\n", Status
);
1981 /* Create or update 'freeldr.ini' */
1982 if (DoesFileExist(SystemRootPath
->Buffer
, L
"freeldr.ini") == FALSE
)
1984 /* Create new freeldr.ini */
1985 wcscpy(DstPath
, SystemRootPath
->Buffer
);
1986 wcscat(DstPath
, L
"\\freeldr.ini");
1988 DPRINT1("Copy: %S ==> %S\n", SrcPath
, DstPath
);
1989 Status
= CreateFreeLoaderIniForReactos(DstPath
,
1990 DestinationArcPath
->Buffer
);
1991 if (!NT_SUCCESS(Status
))
1993 DPRINT1("CreateFreeLoaderIniForReactos() failed (Status %lx)\n", Status
);
1997 /* Save current bootsector as 'BOOTSECT.OLD' */
1998 wcscpy(SrcPath
, SystemRootPath
->Buffer
);
1999 wcscpy(DstPath
, SystemRootPath
->Buffer
);
2000 wcscat(DstPath
, L
"\\bootsect.old");
2002 DPRINT1("Save bootsector: %S ==> %S\n", SrcPath
, DstPath
);
2003 Status
= SaveCurrentBootSector(SrcPath
,
2005 if (!NT_SUCCESS(Status
))
2007 DPRINT1("SaveCurrentBootSector() failed (Status %lx)\n", Status
);
2011 /* Install new bootsector */
2012 if (PartitionType
== PARTITION_FAT32
||
2013 PartitionType
== PARTITION_FAT32_XINT13
)
2015 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
2016 wcscat(SrcPath
, L
"\\loader\\fat32.bin");
2018 DPRINT("Install FAT32 bootcode: %S ==> %S\n", SrcPath
, SystemRootPath
->Buffer
);
2019 Status
= InstallFat32BootCodeToDisk(SrcPath
,
2020 SystemRootPath
->Buffer
);
2021 if (!NT_SUCCESS(Status
))
2023 DPRINT1("InstallFat32BootCodeToDisk() failed (Status %lx)\n", Status
);
2029 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
2030 wcscat(SrcPath
, L
"\\loader\\fat.bin");
2032 DPRINT("Install FAT bootcode: %S ==> %S\n", SrcPath
, SystemRootPath
->Buffer
);
2033 Status
= InstallFat16BootCodeToDisk(SrcPath
,
2034 SystemRootPath
->Buffer
);
2035 if (!NT_SUCCESS(Status
))
2037 DPRINT1("InstallFat16BootCodeToDisk() failed (Status %lx)\n", Status
);
2044 /* Update existing 'freeldr.ini' */
2045 wcscpy(DstPath
, SystemRootPath
->Buffer
);
2046 wcscat(DstPath
, L
"\\freeldr.ini");
2048 Status
= UpdateFreeLoaderIni(DstPath
,
2049 DestinationArcPath
->Buffer
);
2050 if (!NT_SUCCESS(Status
))
2052 DPRINT1("UpdateFreeLoaderIni() failed (Status %lx)\n", Status
);
2058 return STATUS_SUCCESS
;
2063 InstallFatBootcodeToFloppy(PUNICODE_STRING SourceRootPath
,
2064 PUNICODE_STRING DestinationArcPath
)
2066 WCHAR SrcPath
[MAX_PATH
];
2067 WCHAR DstPath
[MAX_PATH
];
2070 /* Copy FreeLoader to the boot partition */
2071 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
2072 wcscat(SrcPath
, L
"\\loader\\freeldr.sys");
2074 wcscpy(DstPath
, L
"\\Device\\Floppy0\\freeldr.sys");
2076 DPRINT("Copy: %S ==> %S\n", SrcPath
, DstPath
);
2077 Status
= SetupCopyFile(SrcPath
, DstPath
);
2078 if (!NT_SUCCESS(Status
))
2080 DPRINT1("SetupCopyFile() failed (Status %lx)\n", Status
);
2084 /* Create new 'freeldr.ini' */
2085 wcscpy(DstPath
, L
"\\Device\\Floppy0\\freeldr.ini");
2087 DPRINT("Create new 'freeldr.ini'\n");
2088 Status
= CreateFreeLoaderIniForReactos(DstPath
,
2089 DestinationArcPath
->Buffer
);
2090 if (!NT_SUCCESS(Status
))
2092 DPRINT1("CreateFreeLoaderIniForReactos() failed (Status %lx)\n", Status
);
2096 /* Install FAT12/16 boosector */
2097 wcscpy(SrcPath
, SourceRootPath
->Buffer
);
2098 wcscat(SrcPath
, L
"\\loader\\fat.bin");
2100 wcscpy(DstPath
, L
"\\Device\\Floppy0");
2102 DPRINT("Install FAT bootcode: %S ==> %S\n", SrcPath
, DstPath
);
2103 Status
= InstallFat16BootCodeToDisk(SrcPath
,
2105 if (!NT_SUCCESS(Status
))
2107 DPRINT1("InstallFat16BootCodeToDisk() failed (Status %lx)\n", Status
);
2111 return STATUS_SUCCESS
;