W poniższej publikacji przedstawione zostały informacje dotyczące sposobu uruchamiania systemów Windows 7 oraz Windows Server 2008 R2 w różnicowych (ang. Differencing) i rozszerzalnych (ang. Expandable) plikach VHD bez efektu niebieskiego ekranu śmierci BSOD (ang. Blue Screen Of Death).
Niniejszy artykuł powstał jako uzupełnienie i zarazem rozszerzenie informacji zawartych w artykule Roberta Stuczyńskiego pt. "Instalacja Windows 7 oraz Windows Server 2008 R2 w plikach VHD". Do zrozumienia treści opublikowanej w tym artykule niezbędne jest wcześniejsze zapoznanie się z artykułem Roberta. Artykuł został opublikowany na portalu WSS.pl w dniu 23 stycznia 2009 i jest dostępny tutaj.
W poniższej publikacji przedstawione zostały informacje dotyczące sposobu uruchamiania systemów Windows 7 oraz Windows Server 2008 R2 w różnicowych (ang. Differencing) i rozsfzerzalnych (ang. Expandable) plikach VHD. Sporo prób uruchomienia tych systemów w takich plikach kończyło się niepowodzeniem z efektem niebieskiego ekranu śmierci BSOD (ang. Blue Screen Of Death). Artykuł omawia również przyczynę takiego wystąpienia oraz pokazuje, jakie warunki muszą być spełnione, aby operacja zakończyła się sukcesem. Zostały w nim również zawarte informacje dotyczące obsługi różnicowych plików VHD.
BSOD podczas rozruchu
W momencie wydania systemów Windows 7 i Windows Server 2008 R2 w wersji beta, a następnie RC, sporo można było przeczytać zarówno na polskich, jak i zagranicznych blogach oraz forach o możliwości instalacji tych systemów w plikach VHD bez użycia wirtualizatorów. Zapewne jest to jedna z bardziej ciekawych funkcji tych systemów, która zasługuje na dużą pochwałę. Problemem okazały się próby wystartowania Windowsów z plików wirtualnych dysków rozszerzalnych oraz różnicowych. Część osób twierdziła, że u nich nie ma problemów związanych z takim rozruchem i wszystko dobrze działa. Druga połowa twierdziła, że taki start systemów nie jest możliwy, gdyż kończy się ekranem BSOD. Nie zagłębiając się w tym miejscu w szczegóły - obie grupy osób miały rację. Dla lepszego wytłumaczenia sytuacji będę się opierał na przykładowych wartościach, pokazujących zależności.
Kiedy utworzymy plik VHD rozszerzalny z zadeklarowaną wielkością np. 120GB lub plik różnicowy, który dziedziczy wielkość po pliku rodzica, to na dysku fizycznym taki plik będzie miał klika KB. Ta niewielka ilość danych to zaledwie wpisy w nagłówku oraz stopce z informacjami o strukturze pliku. Zapewne nie ma tutaj nic odkrywczego, bo tak było od zawsze. Problem BSOD występuje w momencie natywnego rozruchu systemu, kiedy na fizycznym dysku nie ma odpowiedniej ilości wolnego miejsca, potrzebnego do "wirtualnego" rozszerzenia pliku VHD do zadeklarowanej maksymalnej wielkości. Jak to rozumieć? Otóż, jak powszechnie wiadomo, pliki rozszerzalne VHD zawierają w sobie tylko dane faktycznie występujące na wirtualnym dysku, a pliki różnicowe zawierają dane wynikające z obliczeń pochodnej względem pliku rodzica. Natomiast podczas startu systemu z takich plików następuje "wirtualne" rozszerzenie zadeklarowanej wielkość do maksimum. Wirtualne, dlatego że plik fizycznie bez zmian ma nadal wielkość ograniczoną do wielkości posiadanych danych, natomiast startujący natywnie system widzi to jako przestrzeń potrzebną do alokacji pliku VHD na fizycznej partycji.

Rysunek 1. - VHD fizycznie na dysku

Rysunek 2. - VHD wirtualnie w załadowanym systemie
Przykład na rysunku 1. przedstawia fizyczny stan plików VHD, gdzie plik w7u-rc.vhd jest plikiem o stałym rozmiarze (ang. Fixed) w wielkości ~20GB. Drugi plik w7-rc-diff.vhd jest plikiem różnicowym względem w7u-rc.vhd i jego wielkość wynosi ~900MB, co jest wynikiem wyliczonej pochodnej z dodanych (usuniętych) danych. Sytuacja pliku różnicowego zmienia się po załadowaniu systemu z tego pliku, co prezentuje rysunek 2. Plik w7u-rc-diff.vhd rozszerzył wirtualnie swoją objętość do dziedziczonej wielkości ~20GB. Fizycznie jednak plik nadal zajmuje na dysku ~900MB. Kiedy plik rodzic byłby plikiem rozszerzalnym z zadeklarowaną wielkością np. 120GB, a fizycznie zajmowałby 10GB, to w momencie utworzenia pliku różnicowego i załadowania z niego systemu, plik różnicowy przybrałby postać ~120GB. Sytuacja analogicznie wygląda w przypadku rozruchu z plików rozszerzalnych - plik przyjmuje maksymalną wielkość zadeklarowaną.
Wracając do problemu BSOD - wystąpi on w momencie próby wirtualnego rozszerzenia pliku VHD, kiedy na fizycznej partycji nie będzie wystarczającej ilości wolnej przestrzeni, aby to uczynić. BSOD nie pojawi się, kiedy ta przestrzeń będzie dostępna dla wirtualnego rozszerzenia różnicowych (rozszerzalnych) plików VHD.
Tworzenie różnicowego VHD
Kiedy mamy już zainstalowany system Windows 7/Server 2008 R2 w pliku VHD, możemy go dostosować do naszych potrzeb względem sterowników, aktualizacji, aplikacji oraz całego indywidualnego użycia. Po tych operacjach zalecane jest wykonanie defragmentacji wszystkich wirtualnych partycji znajdujących się w pliku VHD.
Defragmentacja
Operację defragmentacji wykonać można z linii poleceń (Start » cmd » Shitf+Ctrl+Enter) za pomocą komendy defrag (rysunek 3) z przełącznikami /c /h /v, co spowoduje automatyczne defragmentowanie wszystkich partycji z normalnym obciążeniem procesora w trybie podglądu. Można też użyć do tego GUI systemowego (Start » dfrgui » Shift+Ctrl+Enter) i ręcznie wykonać defragmentację (rysunek 4.). Wykonanie defragmentacji wymaga podniesienia uprawnień do Administratora, dlatego do jej uruchomienia używana jest dodatkowo kombinacja klawiszy Shift+Ctrl+Enter, która wykonuje od razu żądaną operację podniesienia uprawnień.

Rysunek 3. - Defragmentacja - linia poleceń

Rysunek 4. - Defragmentacja - GUI
Po zakończeniu defragmentacji nie wykonujemy już żadnych dodatkowych czynności w systemie, tylko go zamykamy. Komputer startujemy z nośnika instalacyjnego (DVD, USB, etc…) Windows 7/Server 2008 R2 i w momencie pojawienia się pierwszego ekranu instalacji (rysunek 5.) wciskamy kombinację klawiszy Shift+F10 celem otworzenia linii poleceń.

Rysunek 5. - Pierwszy ekran instalacji
Kompaktowanie
Jeżeli system był zainstalowany w rozszerzalnym pliku VHD, należy przeprowadzić kompaktowanie pliku celem redukcji rozmiaru i usunięcia nieaktualnych informacji z pliku VHD. Operację tę przeprowadza się za pomocą narzędzia linii poleceń diskpart, gdzie wykonujemy w następującej kolejności polecenia w otworzonej wcześniej konsoli:
- Uruchomienie programu diskpart.
diskpart
- Wskazanie pliku VHD.
select vdisk file=D:\w7u-rc.vhd
- Operacja kompaktowania.
compact vdisk
- Wyjście z programu diskpart.
exit
W powyższym przykładzie lokalizacja pliku VHD jest wymyślona - należy użyć własnej. Rysunek 6. pokazuje efekt działania powyższych komend.

Rysunek 6. - Kompaktowanie pliku VHD
Różnicowy VHD
Niezależnie od tego, czy macierzysty dysk VHD jest typu stałego czy rozszerzalnego, przed utworzeniem różnicowego dysku VHD zalecane jest nadanie plikowi atrybutu "tylko do odczytu". Efekt uzyskamy przez wydanie polecenia:
attrib +r D:\w7u-rc.vhd
Kiedy się już ma kompletnie przygotowany wzorcowy plik VHD, można przystąpić do procedury tworzenia pliku różnicowego. Do tej procedury również zostanie użyty program diskpart. Poniżej lista komend, jakie wykonujemy.
- Uruchomienie programu diskpart.
diskpart
- Utworzenie nowego różnicowego pliku VHD ze wskazaniem na plik rodzica.
create vdisk file=D:\w7u-rc-diff.vhd parent=D:\w7u-rc.vhd
- Wyjście z programu diskpart.
exit
Efekt wykonania powyższych poleceń przedstawia rysunek 7.

Rysunek 7. - Tworzenie różnicowego VHD
Procedura przygotowania oraz tworzenia różnicowego pliku VHD dobiegła końca. Można przystąpić do kolejnego etapu, jakim jest stworzenie wpisów w menadżerze rozruchu.
Edycja Windows Boot Manager
Aby uruchomić system operacyjny z różnicowego pliku VHD, musimy zadeklarować nowy wpis w menadżerze rozruchu. Procedurę tę należy wykonać przy pomocy narzędzia linii poleceń bdcedit.
Pierwszą czynnością jest znalezienie GUID obecnego wpisu odpowiadającego za ładowanie systemu. GUID znajduje się pod kluczem identifier.
bcdedit /v
W momencie uzyskania GUID istniejącego wpisu dotyczącego Windows 7/Server 2008 R2 tworzymy jego kopię, zmieniając opis dla rozróżnienia pozycji.
bcdedit /copy {GUID} /d "Windows 7 VHD Diff"
W momencie skopiowania pozycji wyświetli się od razu GUID nowego wpisu. Należy go użyć podczas wskazania nowego pliku VHD jako urządzenia. Podczas podawania ścieżki kluczowe jest wprowadzenie [locate] zamiast literki partycji.
bcdedit /set {Nowy_GUID} device vhd=[locate]\w7u-rc-diff.vhd
Podobnie do poprzedniego wpisu wskazujemy ścieżki urządzenia z systemem operacyjnym, również zwracając uwagę na GUID nowej pozycji oraz wyrażenie [locate].
bcdedit /set {Nowy_GUID} osdevice vhd=[locate]\w7u-rc-diff.vhd
Rysunek 8. przedstawia przykładową powyższą procedurę.

Rysunek 8. - Operacja tworzenia nowego wpisu w bcdedit
Jeżeli decydujemy się tylko na model startu z dysków różnicowych, zalecane jest usunięcie oryginalnego wpisu Windows 7/Server 2008 R2.
bcdedit /delete {GUID}
Po stworzeniu wpisu dotyczącego różnicowego pliku VHD wystarczy zresetować komputer i wybrać dodaną pozycję. Jeżeli wszystkie warunki opisane w sekcji BSOD podczas rozruchu zostaną spełnione, z sukcesem uruchomimy system, a wszelkie zmiany zostaną zapisane w utworzonym pliku VHD. Takich plików różnicowych wraz z wpisem do Windows Boot Manager można zrobić kilka i według potrzeby ładować podczas startu interesującą nas pozycję. Dzięki takiemu rozwiązaniu możemy mieć kilka różnych konfiguracji z niezależnym oprogramowaniem. Model taki może również się sprawdzić w testowaniu pewnych rozwiązań na zasadzie snapshotów znanych z wirtualizacji.
Snapshot niewirtualny
Jedną z bardziej wygodnych funkcji używanych w wirtualizacji jest Snapshot, czyli "zdjęcie" obecnego stanu systemu operacyjnego oraz danych. Dzięki temu można np. wykonać ryzykowną operację i w razie niepowodzenia wrócić w kilka sekund do chwili wykonania snapshota. Kiedy ryzykowna operacja się powiedzie, wystarczy usunąć taki snapshot, a wszelkie zmiany zostaną zastosowane do systemu wejściowego. Podobny schemat działania można osiągnąć w natywnym ładowaniu systemu z różnicowych dysków VHD. Schemat wygląda następująco:
- Tworzymy różnicowy VHD i dodajemy wpis do menadżera rozruchu.
- Ładujemy system z różnicowego pliku VHD.
- Wykonujemy ryzykowną operację.
- Jeżeli się nie udała, kasujemy różnicowy VHD i tworzymy nowy, czysty, powtarzając inny schemat ryzykownej operacji.
- Jeżeli się udała, robimy połączenie dysku różnicowego z dyskiem rodzica, operujemy dalej na systemie z pojedynczym systemowym plikiem VHD.
W tej sekcji omówiona zostanie ostatnia pozycja powyższego schematu, czyli jak połączyć różnicowy plik VHD z plikiem rodzica. Aby dokonać tę operację musimy - podobnie jak w przypadku tworzenia różnicowego VHD - wystartować komputer z nośnika instalacyjnego Windows 7/Server 2008 R2, a następnie otworzyć linię poleceń. Operację łączenia plików VHD przeprowadza się przy użyciu narzędzia diskpart.
- Uruchomienie programu diskpart.
diskpart
- Wskazanie różnicowego pliku VHD.
select vdisk file=D:\w7u-rc-diff.vhd
- Operacja łączenia pliku różnicowego z plikiem rodzica.
merge vdisk depth=1
- Wyjście z programu diskpart.
exit
Powyższy przykład odnosi się do sytuacji, kiedy łańcuch dziedziczenia jest równy jednemu plikowi różnicowemu. W przypadku głębszego zagnieżdżenia operuje się parametrem depth. Zamieszczony poniżej rysunek 9. prezentuje operację łączenia plików VHD.

Rysunek 9. - Operacja łączenia plików VHD
Po skończeniu operacji plik różnicowy można usunąć, a system załadować już z pliku głównego.
Odnośniki
Podsumowanie
Przedstawione w artykule informacje wyjaśniają przyczyny występowania BSOD podczas startu systemu z różnicowego lub rozszerzalnego pliku VHD oraz mają na celu uzupełnić wachlarz możliwości zaprezentowanych w artykule "Instalacja Windows 7 oraz Windows Server 2008 R2 w plikach VHD" z naciskiem na pracę z różnicowymi plikami VHD. W treści nie ma precyzyjnie opisanych scenariuszy zastosowania różnicowych plików VHD - te czytelnik musi sam sobie wykreować, mając rozszerzoną wiedzę i większe możliwości. Zapewne te ostatnie pomogą znacznie skrócić czas administracyjny lub zwiększyć komfort pracy.
Autor:

Dariusz Porowski
(MCTS, MCITP)
www.porowski.pro
Konsultant IT w obszarze technologii serwerowych, infrastruktury oraz wirtualizacji opartej o rozwiązania firmy Microsoft. Współzałożyciel oraz lider offline-owej grupy: Łódzka Grupa Profesjonalistów IT & .NET
Artykuł w wersji: