Root/
Source at commit 157 created 13 years 9 months ago. By scrax, Made a new layout for the installer. Added advanced Options subfolder with some options to test. Added No chameleon base installation option. Updated localizable.string in IT and EN folders. New background by iFabio added | |
---|---|
1 | /*␊ |
2 | * resume.c␊ |
3 | * ␊ |
4 | *␊ |
5 | * Created by mackerintel on 1/22/09.␊ |
6 | * Copyright 2009 mackerintel. All rights reserved.␊ |
7 | *␊ |
8 | */␊ |
9 | ␊ |
10 | #include "saio_internal.h"␊ |
11 | #include "libsa.h"␊ |
12 | #include "IOHibernatePrivate.h"␊ |
13 | #include "memory.h"␊ |
14 | #include "bootstruct.h"␊ |
15 | #include "boot.h"␊ |
16 | #include "pci.h"␊ |
17 | ␊ |
18 | extern int previewTotalSectors;␊ |
19 | extern int previewLoadedSectors;␊ |
20 | extern uint8_t *previewSaveunder;␊ |
21 | ␊ |
22 | static unsigned long␊ |
23 | getmemorylimit(void)␊ |
24 | {␊ |
25 | int line;␊ |
26 | int i;␊ |
27 | MemoryRange *mp = bootInfo->memoryMap;␊ |
28 | ␊ |
29 | // Activate and clear page 1␊ |
30 | line = 1;␊ |
31 | for (i = 0; i < bootInfo->memoryMapCount; i++)␊ |
32 | {␊ |
33 | if((mp->type == 1) && ((unsigned long)mp->base == 0x100000))␊ |
34 | {␊ |
35 | return (unsigned long)(mp->base + mp->length);␊ |
36 | }␊ |
37 | mp++;␊ |
38 | }␊ |
39 | return 0x10000000;␊ |
40 | }␊ |
41 | ␊ |
42 | static void WakeKernel(IOHibernateImageHeader * header)␊ |
43 | {␊ |
44 | ␉uint32_t proc;␊ |
45 | ␉unsigned long cnt, newSP;␊ |
46 | ␉unsigned long *src, *dst;␊ |
47 | ␉unsigned int ␉count;␊ |
48 | ␉unsigned int ␉page;␊ |
49 | ␉unsigned int ␉compressedSize;␊ |
50 | ␉int32_t ␉byteCnt;␊ |
51 | ␉u_int32_t ␉lowHalf, highHalf;␊ |
52 | ␉u_int32_t ␉sum;␊ |
53 | ␉␊ |
54 | ␉printf("\nWake Kernel!\n");␊ |
55 | ␉␊ |
56 | ␉dst = (unsigned long *) (header->restore1CodePage << 12);␊ |
57 | ␉count = header->restore1PageCount;␊ |
58 | ␉proc = (header->restore1CodeOffset + ((uint32_t) dst));␊ |
59 | ␉newSP = header->restore1StackOffset + (header->restore1CodePage << 12);␊ |
60 | ␉␊ |
61 | ␉src = (unsigned long *) (((u_int32_t) &header->fileExtentMap[0]) ␊ |
62 | ␉␉␉␉␉␉␉ + header->fileExtentMapSize);␊ |
63 | ␉sum = 0;␊ |
64 | ␉␊ |
65 | ␉for (page = 0; page < count; page++)␊ |
66 | ␉{␊ |
67 | ␉␉compressedSize = 4096;␊ |
68 | ␉␉␊ |
69 | ␉␉lowHalf = 1;␊ |
70 | ␉␉highHalf = 0;␊ |
71 | ␉␉␊ |
72 | ␉␉for (cnt = 0; cnt < compressedSize; cnt += 0x20) {␊ |
73 | ␉␉␉dst[0] = src[0];␊ |
74 | ␉␉␉dst[1] = src[1];␊ |
75 | ␉␉␉dst[2] = src[2];␊ |
76 | ␉␉␉dst[3] = src[3];␊ |
77 | ␉␉␉dst[4] = src[4];␊ |
78 | ␉␉␉dst[5] = src[5];␊ |
79 | ␉␉␉dst[6] = src[6];␊ |
80 | ␉␉␉dst[7] = src[7];␊ |
81 | ␉␉␉for (byteCnt = 0; byteCnt < 0x20; byteCnt++) {␊ |
82 | ␉␉␉␉lowHalf += ((u_int8_t *) dst)[byteCnt];␊ |
83 | ␉␉␉␉highHalf += lowHalf;␊ |
84 | ␉␉␉}␊ |
85 | ␉␉␉src += 8;␊ |
86 | ␉␉␉dst += 8;␊ |
87 | ␉␉}␊ |
88 | ␉␉␊ |
89 | ␉␉lowHalf %= 65521L;␊ |
90 | ␉␉highHalf %= 65521L;␊ |
91 | ␉␉sum += (highHalf << 16) | lowHalf;␊ |
92 | ␉}␊ |
93 | ␉header->actualRestore1Sum = sum;␊ |
94 | ␉startprog (proc, header);␊ |
95 | ␉␊ |
96 | ␉return;␊ |
97 | }␊ |
98 | ␊ |
99 | void HibernateBoot(char *image_filename)␊ |
100 | {␊ |
101 | ␉long long size, imageSize, codeSize, allocSize;␊ |
102 | ␉long mem_base;␊ |
103 | ␉IOHibernateImageHeader _header;␊ |
104 | ␉IOHibernateImageHeader * header = &_header;␊ |
105 | ␉long buffer;␊ |
106 | ␉␊ |
107 | ␉size = ReadFileAtOffset (image_filename, header, 0, sizeof(IOHibernateImageHeader));␊ |
108 | ␉printf("header read size %x\n", size);␊ |
109 | ␉␉␊ |
110 | ␉imageSize = header->image1Size;␊ |
111 | ␉codeSize = header->restore1PageCount << 12;␊ |
112 | ␉if (kIOHibernateHeaderSignature != header->signature)␊ |
113 | ␉{␊ |
114 | ␉␉printf ("Incorrect image signature\n");␊ |
115 | ␉␉return;␊ |
116 | ␉}␊ |
117 | ␉if (header->encryptStart)␊ |
118 | ␉{␊ |
119 | ␉␉printf ("Resuming from Encrypted image is unsupported.\n"␊ |
120 | ␉␉␉␉"Uncheck \"Use secure virtual memory\" in \"Security\" pane on system preferences.\n"␊ |
121 | ␉␉␉␉"Press any key to proceed with normal boot.\n");␊ |
122 | ␉␉getc ();␊ |
123 | ␉␉return;␊ |
124 | ␉}␊ |
125 | // depends on NVRAM␊ |
126 | #if 0␊ |
127 | ␉{␊ |
128 | ␉␉uint32_t machineSignature;␊ |
129 | ␉␉size = GetProp(gChosenPH, kIOHibernateMachineSignatureKey, ␊ |
130 | ␉␉␉␉␉ (char *)&machineSignature, sizeof(machineSignature));␊ |
131 | ␉␉if (size != sizeof(machineSignature)) machineSignature = 0;␊ |
132 | ␉␉if (machineSignature != header->machineSignature)␊ |
133 | ␉␉␉break;␊ |
134 | ␉}␊ |
135 | #endif␊ |
136 | ␉␉␊ |
137 | ␉allocSize = imageSize + ((4095 + sizeof(hibernate_graphics_t)) & ~4095);␊ |
138 | ␊ |
139 | ␉mem_base = getmemorylimit() - allocSize;//TODO: lower this␊ |
140 | ␉␉␊ |
141 | ␉printf("mem_base %x\n", mem_base);␊ |
142 | ␉// Rek : hibernate fix ␊ |
143 | ␉if (!((long long)mem_base+allocSize<1024*bootInfo->extmem+0x100000))␊ |
144 | ␉{␊ |
145 | ␉␉printf ("Not enough space to restore image. Press any key to proceed with normal boot.\n");␊ |
146 | ␉␉getc ();␊ |
147 | ␉␉return;␊ |
148 | ␉}␊ |
149 | ␉␉␊ |
150 | ␉bcopy(header, (void *) mem_base, sizeof(IOHibernateImageHeader));␊ |
151 | ␉header = (IOHibernateImageHeader *) mem_base;␊ |
152 | ␉␉␊ |
153 | ␉imageSize -= sizeof(IOHibernateImageHeader);␊ |
154 | ␉buffer = (long)(header + 1);␊ |
155 | ␉␊ |
156 | ␉if (header->previewSize)␊ |
157 | ␉{␊ |
158 | ␉␉uint64_t preview_offset = header->fileExtentMapSize - sizeof(header->fileExtentMap) + codeSize;␊ |
159 | ␉␉uint8_t progressSaveUnder[kIOHibernateProgressCount][kIOHibernateProgressSaveUnderSize];␊ |
160 | ␉␉␉␊ |
161 | ␉␉ReadFileAtOffset (image_filename, (char *)buffer, sizeof(IOHibernateImageHeader), preview_offset+header->previewSize);␊ |
162 | ␉␉drawPreview ((void *)(long)(buffer+preview_offset + header->previewPageListSize), &(progressSaveUnder[0][0]));␊ |
163 | ␉␉previewTotalSectors = (imageSize-(preview_offset+header->previewSize))/512;␊ |
164 | ␉␉previewLoadedSectors = 0;␊ |
165 | ␉␉previewSaveunder = &(progressSaveUnder[0][0]);␊ |
166 | ␉␉if (preview_offset+header->previewSize<imageSize)␊ |
167 | ␉␉␉ReadFileAtOffset (image_filename, (char *)(long)(buffer+preview_offset+header->previewSize), ␊ |
168 | ␉␉␉␉␉␉␉ sizeof(IOHibernateImageHeader)+preview_offset+header->previewSize,␊ |
169 | ␉␉␉␉␉␉␉ imageSize-(preview_offset+header->previewSize));␊ |
170 | ␉␉previewTotalSectors = 0;␊ |
171 | ␉␉previewLoadedSectors = 0;␊ |
172 | ␉␉previewSaveunder = 0;␉␉␊ |
173 | #if 0␊ |
174 | ␉␉AsereBLN:␊ |
175 | ␉␉check_vga_nvidia() didn't work as expected (recursion level > 0 & return value).␊ |
176 | ␉␉Unforutnaltely I cannot find a note why to switch back to text mode for nVidia cards only␊ |
177 | ␉␉and because it check_vga_nvidia does not work (cards normally are behind a bridge) I will␊ |
178 | ␉␉remove it completely␊ |
179 | ␉␉setVideoMode( VGA_TEXT_MODE, 0 );␊ |
180 | #endif␊ |
181 | ␉}␊ |
182 | ␉else␊ |
183 | ␉␉ReadFileAtOffset (image_filename, (char *)buffer, sizeof(IOHibernateImageHeader), imageSize);␊ |
184 | ␉␊ |
185 | // Depends on NVRAM␊ |
186 | #if 0␊ |
187 | ␉if (header->encryptStart) {␊ |
188 | ␉␉// decryption data␊ |
189 | ␉␉static const unsigned char first_iv[AES_BLOCK_SIZE]␊ |
190 | ␉␉= { 0xa3, 0x63, 0x65, 0xa9, 0x0b, 0x71, 0x7b, 0x1c,␊ |
191 | ␉␉0xdf, 0x9e, 0x5f, 0x32, 0xd7, 0x61, 0x63, 0xda };␊ |
192 | ␉␉hibernate_cryptvars_t _cryptvars;␊ |
193 | ␉␉hibernate_cryptvars_t * cryptvars = &_cryptvars;␊ |
194 | ␉␉␊ |
195 | ␉␉aes_decrypt_key(&decryptkey,␊ |
196 | ␉␉␉␉␉␉decryptkeysize,␊ |
197 | ␉␉␉␉␉␉&cryptvars->ctx.decrypt);␊ |
198 | ␉␉␉␊ |
199 | ␉␉// set the vector for the following decryptions␊ |
200 | ␉␉bcopy(((uint8_t *) header) + header->image1Size - AES_BLOCK_SIZE, ␊ |
201 | ␉␉␉␉&cryptvars->aes_iv[0], AES_BLOCK_SIZE);␊ |
202 | ␉␉␉␊ |
203 | ␉␉// decrypt the buffer␊ |
204 | ␉␉uint32_t len = (uint32_t)(header->image1Size - header->encryptStart);␊ |
205 | ␉␉aes_decrypt_cbc(((uint8_t *) header) + header->encryptStart,␊ |
206 | ␉␉␉␉␉␉&first_iv[0],␊ |
207 | ␉␉␉␉␉␉len >> 4,␊ |
208 | ␉␉␉␉␉␉((uint8_t *) header) + header->encryptStart,␊ |
209 | ␉␉␉␉␉␉&cryptvars->ctx.decrypt);␊ |
210 | ␉␉bzero(&cryptvars->aes_iv[0], sizeof(cryptvars));␊ |
211 | ␉␉bzero(&decryptkey, sizeof(decryptkey));␊ |
212 | ␉}␊ |
213 | #endif␊ |
214 | ␉␊ |
215 | ␉WakeKernel(header);␊ |
216 | }␊ |
217 |