13
|
1 ---
|
16
|
2 marp: true
|
13
|
3 title: Gears OS UEFI対応
|
|
4 paginate: true
|
|
5
|
|
6 theme: default
|
|
7 size: 16:9
|
|
8 style: |
|
|
9 section {
|
|
10 background-color: #FFFFFF;
|
18
|
11 font-size: 40px;
|
13
|
12 color: #4b4b4b;
|
|
13 font-family: "Arial", "Hiragino Maru Gothic ProN";
|
|
14 }
|
|
15
|
|
16 section.title {
|
|
17 font-size: 40px;
|
|
18 padding: 40px;
|
|
19 }
|
|
20 section.title h1 {
|
|
21 text-align: center;
|
|
22 }
|
|
23
|
|
24 section.slide h1 {
|
|
25 position: absolute;
|
|
26 left: 50px; top: 35px;
|
|
27 }
|
|
28
|
|
29 ---
|
|
30 <!-- class: title -->
|
14
|
31 # <!--fit--> Gears OS のBootに関する研究
|
13
|
32
|
|
33 - 奥田光希
|
|
34 - 琉球大学工学部工学科知能情報コース
|
|
35 - 河野 真治
|
|
36 - 琉球大学工学部
|
|
37
|
|
38 ---
|
21
|
39
|
14
|
40 # OSとアプリケーションの信頼性を高めたい
|
13
|
41
|
14
|
42 - Meta計算を用いて信頼性を高めるGearsOSを提案している
|
|
43 - x.v6を元にRaspberry Pi上で動くGearsOSを実装中
|
21
|
44 - キーボードやマウスが使えない
|
|
45 - デバイスドライバを作る必要がある
|
14
|
46 ---
|
21
|
47 # BIOS問題
|
|
48 - x.v6の起動はBIOSを使っている
|
|
49 - IntelがCompatibility Support Module(CSM)をやめた
|
|
50 - BIOSを前提としたOSが動かなくなるかも
|
|
51 - キーボードやマウスはUSB
|
|
52 - USBドライバを作るのは難しい
|
|
53 ---
|
|
54 # <!--fit--> Gears OSをUEFIでBootさせよう
|
|
55 ---
|
|
56 # UEFIへの移行
|
14
|
57 - CPUなどの機種依存性を避けることができる
|
|
58 - GearsOSはCbC(Continuation based C)で記述されていて、CPUやデバイスに影響されない
|
|
59 - 様々な組み込みシステムに対してGearsOSを応用できる様になる
|
21
|
60 - UEFIのApplicationによりUSBドライバ開発が簡単になる
|
20
|
61
|
14
|
62 ---
|
21
|
63 # 研究の成果
|
|
64 - UEFIの開発環境をSingularityで作成した
|
|
65 - gnu-efiで作成したUEFI Applicationをqemu-system-armで動かすことができた
|
|
66 - RaspberryPiにUEFIをファームウェアとして設定し、実行することができた
|
|
67 - ミニマムなKernel Loaderを調査しARM xv6用に書き直した
|
|
68 ---
|
14
|
69 # CbC(Continuation based C)
|
15
|
70 - 並列信頼研究で開発されているプログラミング言語
|
|
71 - C言語の下位言語
|
|
72 - 関数呼び出しではなく継続(goto)
|
|
73 - 関数の代わりにCodeGearという単位でプログラミングを行う。
|
|
74
|
|
75 ---
|
21
|
76
|
14
|
77 # GearsOS
|
15
|
78 - 並列信頼研究で開発されているOS
|
|
79 - 信頼性と拡張性がテーマ
|
|
80 - CbCによって記述されている
|
|
81 - x.v6をCbCで書き直して実装している
|
14
|
82 ---
|
21
|
83
|
14
|
84 # UEFI
|
15
|
85 - Unified Extensible Firmware Interfaceの略
|
|
86 - OSとプラットフォームファームウェアの間のソフトウェアインタフェースを定義する仕様
|
|
87 - Intel、AMD、Apple、Microsoftなどの企業からなるUnified EFI Forumの元で開発
|
|
88 - BIOSの後継
|
|
89 ---
|
21
|
90
|
|
91 # UEFIの利点
|
15
|
92 - CPUやドライバに依存しない
|
|
93 - 2TBを超える大きなディスクからBootできる
|
|
94 - メモリも64bitなら理論上16EB
|
21
|
95 - BIOSより高速でBoot
|
|
96 - オープン仕様だから開発が簡単
|
14
|
97
|
|
98 ---
|
21
|
99
|
14
|
100 # UEFI 開発環境
|
21
|
101 - EDK2
|
15
|
102 - gnu-efi
|
18
|
103 - qemu
|
21
|
104 - Singularity
|
15
|
105
|
|
106 ---
|
21
|
107
|
15
|
108 # gnu-efi
|
|
109 - システムのネイティブGCCでUEFIアプリケーションをコンパイルできる
|
|
110 - UEFI Applicationをリンクするためのライブラリがある
|
|
111 - UEFI Applicationの開発に特化している
|
18
|
112 - EDK2のファームウェアがベース
|
19
|
113 ---
|
21
|
114
|
19
|
115 # qemu
|
|
116 - 異なるアーキテクチャのプログラムを動かすエミュレータ
|
|
117 - 本開発ではX86上でARMを動かした
|
|
118 - gnu-efiで実装したUEFIを動かした
|
|
119
|
|
120
|
|
121 ---
|
|
122 # singularity
|
|
123 - ユーザーが自身の計算環境を完全再現し、保持できる様にしたLinuxコンテナ
|
|
124 - 学科の新システムで利用できる
|
|
125 - CbC GCC ARM CrossCompile環境を作った
|
|
126 - UEFIの開発環境を作った
|
|
127 ---
|
|
128 # UEFI Application
|
|
129 - UEFI Boot Managreがロード、実行するプログラムのこと
|
|
130 - C言語で記述可能
|
|
131 - OSがなくてもプログラムを書ける
|
|
132 - CPUやドライバに依存しない
|
18
|
133
|
|
134 ---
|
|
135 # UEFI Applicationの例
|
|
136 Hello.c
|
|
137 ```
|
|
138 #include <efi.h>
|
|
139 #include <efilib.h>
|
|
140
|
|
141 EFI_STATUS
|
|
142 EFIAPI
|
|
143 efi_main (EFI_HANDLE ImageHandle, EFI_SYSTEM_TABLE *SystemTable)
|
|
144 {
|
|
145 InitializeLib(ImageHandle, SystemTable);
|
|
146 Print(L"Hello, world!\n");
|
|
147 return EFI_SUCCESS;
|
|
148 }
|
|
149 ```
|
|
150 ---
|
21
|
151 # Gears OS UEFI Bootの課題
|
|
152 - UEFIからx.v6はBootできない
|
|
153 - x.v6はUEFIに対応されてない
|
|
154 - x.v6のBootLoaderが必要
|
|
155 - BootLoaderを作成する
|
|
156 ---
|
|
157 # Boot Loader
|
|
158
|
|
159 - OSをLoadしてBootさせる役割をもつプログラム
|
|
160 - UEFI ApplicationとしてC言語で実装できる
|
|
161 ---
|
|
162 # Boot Loaderの役割
|
|
163 1. 電源が入る
|
|
164 1. UEFIが立ち上がる
|
|
165 1. Boot ManagerからBootLoaderが起動する
|
|
166 1. BootLoaderがOSのKernelをメモリにLoadさせる
|
|
167 1. Kernelがinitプロセスを起動
|
|
168 1. initプロセスがOSのBootプロセスを起動
|
|
169 1. OSがBootされる
|
|
170
|
|
171 ---
|
|
172 # BootLoader.c
|
20
|
173 - efi_mainの引数設定
|
|
174
|
18
|
175 ```
|
|
176 #include<efi.h>
|
|
177 #include<efilib.h>
|
|
178
|
|
179 EFI_STATUS
|
|
180 efi_main(EFI_HANDLE ImageHandle, EFI_SYSTEM_TABLE *SystemTable)
|
|
181 {
|
|
182 EFI_DEVICE_PATH *Path;
|
|
183 EFI_LOADED_IMAGE *LoadedImageParent;
|
|
184 EFI_LOADED_IMAGE *LoadedImage;
|
|
185 EFI_HANDLE Image;
|
|
186 CHAR16 *Options = L"root=/dev/sda2 rootfstype=btrfs rw quiet splash";
|
|
187 EFI_STATUS Status=EFI_SUCCESS;
|
|
188
|
|
189 InitializeLib(ImageHandle, SystemTable);
|
|
190 Print(L"Hello, EFI!\n");
|
20
|
191 ```
|
|
192 ---
|
21
|
193 - uefi_call_wrapperでプロトコルを呼び出している
|
|
194
|
20
|
195 ```
|
|
196 Status = uefi_call_wrapper(BS->OpenProtocol, 6, ImageHandle, &
|
|
197 LoadedImageProtocol,(void**)&LoadedImageParent,
|
|
198 ImageHandle, NULL, EFI_OPEN_PROTOCOL_GET_PROTOCOL);
|
21
|
199 ```
|
|
200 - エラー文
|
|
201 ```
|
18
|
202 if (EFI_ERROR(Status)) {
|
|
203 Print(L"Could not get LoadedImageProtocol handler %r\n", Status);
|
|
204 return Status;
|
|
205 }
|
21
|
206 ```
|
|
207 ---
|
|
208 - xv6.imgのデバイスパスをPathに格納している
|
|
209 - このデバイスパスはKernelをLoadするときに使う
|
|
210 ```
|
18
|
211 Path = FileDevicePath(LoadedImageParent->DeviceHandle, L"\\xv6.img");
|
21
|
212 ```
|
|
213 - エラー文
|
|
214 ```
|
18
|
215 if (Path == NULL) {
|
|
216 Print(L"Could not get device path.");
|
|
217 return EFI_INVALID_PARAMETER;
|
|
218 }
|
20
|
219 ```
|
|
220 ---
|
21
|
221 - ここでデバイスパスを使いKernelをLoadする。
|
|
222 - これでKernelがメモリに展開される。
|
20
|
223 ```
|
21
|
224 Status = uefi_call_wrapper(BS->LoadImage, 6, FALSE, ImageHandle,
|
|
225 Path, NULL, 0, &Image);
|
|
226 ```
|
|
227 - エラー文
|
|
228 ```
|
18
|
229 if (EFI_ERROR(Status)) {
|
|
230 Print(L"Could not load %r", Status);
|
|
231 FreePool(Path);
|
|
232 return Status;
|
|
233 }
|
20
|
234 ```
|
|
235 ---
|
21
|
236 - LoadしたKernelイメージについてLoadedImageProtocolを入手
|
|
237 - LoadOptionsに起動オプションを指定し、Kernel コマンドラインを指定
|
20
|
238 ```
|
21
|
239 Status = uefi_call_wrapper(BS->OpenProtocol, 6,
|
|
240 Image, &LoadedImageProtocol,
|
20
|
241 (void**)&LoadedImage, ImageHandle, NULL, EFI_OPEN_PROTOCOL_GET_PROTOCOL);
|
18
|
242 if (EFI_ERROR(Status)) {
|
|
243 Print(L"Could not get LoadedImageProtocol handler %r\n", Status);
|
|
244 uefi_call_wrapper(BS->UnloadImage, 1, Image);
|
|
245 FreePool(Path);
|
|
246 return Status;
|
|
247 }
|
|
248 LoadedImage->LoadOptions = Options;
|
|
249 LoadedImage->LoadOptionsSize = (StrLen(LoadedImage->LoadOptions)+1) * sizeof(CHAR16);
|
20
|
250 Print(L"Hello,6!\n");
|
21
|
251 ```
|
|
252 ---
|
20
|
253
|
21
|
254 - Loadされたイメージを起動
|
|
255 - Kernelが起動する
|
|
256 ```
|
18
|
257 Status = uefi_call_wrapper(BS->StartImage, 3, Image, NULL, NULL);
|
|
258 uefi_call_wrapper(BS->UnloadImage, 1, Image);
|
|
259 FreePool(Path);
|
|
260
|
|
261 return EFI_SUCCESS;
|
|
262 }
|
|
263 ```
|
14
|
264 ---
|
20
|
265 # 大変だったこと
|
|
266 - EDK2は汎用的だがARMのConfigなどの書き換えが困難
|
|
267 - UEFI開発の情報が少なく、偏りがあった
|
|
268 - UEFI独特のプログラムの書き方があった
|
|
269 - 低レベルの開発に慣れていなかった
|
18
|
270
|
|
271 ---
|
|
272 # 今後の課題
|
14
|
273
|
18
|
274 - Singularity上のqemu-system-armにgdbを接続する
|
21
|
275 - そのgdbでKernel Loaderをデバックする
|
18
|
276 - xv6 KernelにUEFIからBootするコードを入れる
|
|
277 - xv6を書き換えたGearsOSを実装する
|
|
278 - USB Driverを実装し、キーボードやマウスを使える様にする
|
|
279
|
|
280 ---
|
21
|
281 # ご清聴ありがとうございました
|