What is Metasepi?

  • 1,440 views
Uploaded on

http://metasepi.masterq.net/

http://metasepi.masterq.net/

More in: Technology
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
No Downloads

Views

Total Views
1,440
On Slideshare
0
From Embeds
0
Number of Embeds
4

Actions

Shares
Downloads
11
Comments
1
Likes
5

Embeds 0

No embeds

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
    No notes for slide

Transcript

  • 1. What is Metasepi? Kiwamu Okabe
  • 2. プロローグ (cont.)
  • 3. プロローグ
  • 4. おしながき☆ Metasepiとは何か☆ なぜMetasepiを作るのか☆ 開発の戦略 (POSIX互換、スナッチ開発)☆ 実現方法 (NetBSDとjhcの採用)☆ デモ☆ Metasepiの今後
  • 5. Metasepiって何?☆ http://metasepi.masterq.net/☆ UNIXモドキkernelを型によって設計する☆ C言語での記述はできるかぎり小さく☆ 設計言語はHaskellでもOCamlでも☆ とにかく早くドッグフード可能にしよう!
  • 6. 名前の由来☆ コウイカの一種 Metasepia pfefferi☆ コウイカは大きな骨を持つ (型システム)☆ 墨はセピア色の原料 (古いOS領域に光を)☆ 威嚇のために体色を変える (最適な設計に)☆ λカ娘がイカちゃんだからhttp://www.paraiso-lang.org/ikmsm/
  • 7. どうしてMetasepiを作るの?☆ C言語より進化した言語を設計に使いたい☆ 既存設計を安全に改造できるようにしたい
  • 8. C言語より進化した機能って?☆ パターンマッチ☆ パッケージ☆ 名前空間☆ 型推論☆ 対話環境☆ 高階関数☆ GC
  • 9. そんな言語あるの?以下の言語はコンパイラで型推論を持つ。☆ Clean - http://clean.cs.ru.nl/☆ Coq - http://coq.inria.fr/☆ Haskell - http://www.haskell.org/☆ OCaml - http://caml.inria.fr/☆ SML/NJ - http://www.smlnj.org/などなど
  • 10. 安全に改造?OSSをほぼそのまま製品搭載できれば良いのですが、 機能を追加して製品設計するハメになることはありませんか?☆ システムコール追加☆ 起動時間改善☆ 気色わるいメモリマップ☆ ソフトリアルタイムスケジューラなどなど
  • 11. OSS改造あるある: fork
  • 12. OSS改造あるある: merge
  • 13. OSS改造あるある: 完全fork
  • 14. なぜこんなことに?
  • 15. でも改造するのは本家も同じ
  • 16. 既存コード改造工数を減らさねば☆ マネージャにmergeタイミング説得できない☆ 数々のforkが生まれるだけ?☆ このままではOSS社会は崩壊しまう...
  • 17. 一方MSは着々と手を打っている #1デバイスドライバに対する静的検証ツールをWDKで配布。http://msdn.microsoft.com/ja-jp/library/windows/hardware/gg487498.aspx"Static Driver Verifier (SDV) は、カーネル モード ドライバー用に設計されている、コンパイル時用の徹底した静的な検証ツールで、 徹底したテストでも発見されない可能性がある重大なエラーを検出します。 SDVは、C および C++ で記述されている Windows ドライバーのソース コードを体系的に分析します。 一連のインターフェイスの規則とオペレーティング システムのモデルを使用して、ドライバーが Windows オペレーティング システムと適切に動作しているかどうかを判断します。"
  • 18. 一方MSは着々と手を打っている #2http://research.microsoft.com/en-us/projects/singularity/"Singularity は マイクロソフトリサーチ が2003年から実験的に開発しているオペレーティングシステム (OS)。高度なディペンダブルOSとすることを目標とし、カーネルやデバイスドライバ、アプリケーションも全てマネージコードで書かれている。""バージョン1.1は2007年3月、バージョン2.0は2008年11月14日にリリースされ、開発は現在も進行中である。"
  • 19. 改造工数を小さくする方法はある?それが型システムです!
  • 20. 型システムのうまみ☆ ランタイムエラーを少なくできる☆ 参考:数理科学的バグ撲滅方法論のすすめhttp://itpro.nikkeibp.co.jp/article/COLUMN/20060915/248230/
  • 21. Metasepiはどうやって設計するの?☆ 既存のモノリシックkernelと同じ設計に☆ 当然POSIX互換☆ 既存kernelを少しずつ型で再設計☆ 動作可能状態を保ちながら開発(スナッチ)この設計をアラフラと呼ぶことにします。http://metasepi.masterq.net/posts/2013-01-09-design_arafura.html
  • 22. なぜPOSIX互換に?早い段階でドッグフード可能にするため!
  • 23. スナッチ開発http://ja.wikipedia.org/wiki/スナッチャー
  • 24. 実現方法☆ 開発言語: Haskellhttp://www.haskell.org/☆ コンパイラ: jhchttp://repetae.net/computer/jhc/☆ 元にするkernel: NetBSDhttp://netbsd.org/
  • 25. プログラミング言語Haskell☆ 純粋関数型プログラミング言語☆ 型クラスによる柔軟な表現☆ gcc比較で2.36のパフォーマンスhttp://benchmarksgame.alioth.debian.org/u64/which-programs-are-fastest.php☆ 近年はOCamlよりもプログラマが多い?
  • 26. jhcコンパイラhttp://repetae.net/computer/jhc/
  • 27. jhcはポータブルlibc不要バイナリ吐ける
  • 28. jhcのRTSは小さい☆ RTS = ランタイム = VMみたいなもん☆ C言語のみで記述されている☆ コメント込み3000行☆ これなら改造/自作できそう☆ 実はプリミティブ型がC言語型☆ C言語との相性が良い
  • 29. NetBSD kernel☆ 移植性高い = 高い抽象化☆ POSIX互換モノリシックkernel☆ ソースコード読みやすい☆ kernel内部APIドキュメント豊富http://netbsdman.masterq.net/☆ @master_q が昔仕事でいじってた
  • 30. 技術背景: 過去プロジェクトの失敗☆ 同様の試みは他にもある* Funk (OCaml製) http://home.gna.org/funk/* snowflake-os (OCaml製) http://code.google.com/p/snowflake-os/* House (Haskell製) http://programatica.cs.pdx.edu/House/* HaLVM (Haskell製) http://corp.galois.com/halvm/☆ しかし実用化には至っていない☆ スクラッチからkernelを書くのは無謀では?
  • 31. 作り方:NetBSD kernelを型で写経☆ C言語で書かれた☆ NetBSD kernelを☆ Haskellで少しずつ再設計して (スナッチ)☆ jhcでコンパイルする
  • 32. 具体例: bootloader 元/* https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/sys/arch/i386/stand/lib/menuutils.c */const struct bootblk_command commands[] = { { "help", command_help }, { "boot", command_boot }, { NULL, NULL },};voidbootmenu(void){ char input[80]; for (;;) { char *c = input; input[0] = 0; printf("> "); gets(input); while (*c == ) c++; if (*c) docommand(c); }}
  • 33. 具体例: bootloader スナッチ-- https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/metasepi-arafura/sys/arch/i386/stand/boot/Boot2Ara.hsforeign import ccall "glue_netbsdstand.h command_boot"c_command_boot :: Ptr a -> IO ()commands :: Map String (IO ())commands = Map.fromList [("help", command_help), ("?", command_help), ("boot", c_command_boot nullPtr)]main :: IO ()main = do putStrLn "Haskell bootmenu" forever $ do putStr "> " s <- getLine fromMaybe (putStr s) $ Map.lookup s commands
  • 34. 具体例: kernel 元 #1/* https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/sys/sys/lwp.h */struct lwp { /* --snip-- */ int l_flag; int l_stat; /* --snip-- */};/* These flags are kept in l_flag. */#define LW_IDLE 0x00000001#define LW_LWPCTL 0x00000002#define LW_SINTR 0x00000080#define LW_SA_SWITCHING 0x00000100#define LW_SYSTEM 0x00000200#define LW_SA 0x00000400#define LW_WSUSPEND 0x00020000/* Status values. */#define LSIDL 1#define LSRUN 2#define LSSLEEP 3#define LSSTOP 4#define LSZOMB 5
  • 35. 具体例: kernel 元 #2/* https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/sys/kern/kern_lwp.c */ switch (t->l_stat) { case LSRUN: case LSONPROC: t->l_flag |= LW_WSUSPEND; lwp_need_userret(t); lwp_unlock(t); break; case LSSLEEP: t->l_flag |= LW_WSUSPEND; if ((t->l_flag & LW_SINTR) != 0) setrunnable(t); else lwp_unlock(t); break; case LSSUSPENDED: lwp_unlock(t); break; case LSSTOP: t->l_flag |= LW_WSUSPEND; setrunnable(t); break;
  • 36. 具体例: kernel スナッチ #1data Lflag = Lflag { lwIdle :: Bool , lwLwpctl :: Bool , lwSintr :: Bool , lwSaSwitching :: Bool , lwSystem :: Bool , lwSa :: Bool , lwWsuspend :: Bool }data Lstat = LsIdl | LsRun | LsSleep | LsStop | LsZomb | LsOnProc | LsSuspendeddata Lwp = Lwp { lflag :: Lflag , lstat :: Lstat {-- ...... --} }data ErrNo = Eperm | Enoent | Esrch | Eintr | Eio | Enxio | E2big | Enoexec | Ebadf | Echild | Edeadlk
  • 37. 具体例: kernel スナッチ #2lwpSuspend :: Lwp -> Lwp -> IO (Either ErrNo ())lwpSuspend curl t = go $ lstat t where go LsRun = fRunOnproc go LsOnProc = fRunOnproc go LsSleep = do lwpSetFlag lwWsuspend if lwSintr . lflag $ t then setRunnable t else lwpUnlock t return $ Right () go LsSuspended = do lwpUnlock t return $ Right () go LsStop = do lwpSetFlag lwWsuspend setRunnable t return $ Right () go LsIdl = fIdlZomb go LsZomb = fIdlZomb fRunOnproc = do lwpSetFlag lwWsuspend lwpNeedUserret t lwpUnlock t return $ Right () fIdlZomb = do lwpUnlock t return $ Left Eintr
  • 38. 具体例: デバドラ 元 #1/* https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/sys/dev/usb/ehcireg.h */#define EHCI_USBINTR 0x08 /* RW Interrupt register */#define EHCI_USBSTS 0x04 /* RO, RW, RWC Status */#define EHCI_STS_IAA 0x00000020 /* intr on async adv */#define EHCI_STS_PCD 0x00000004 /* port change detect */#define EHCI_STS_ERRINT 0x00000002 /* error interrupt */#define EHCI_STS_INT 0x00000001 /* RWC interrupt */#define EHCI_STS_INTRS(x) ((x) & 0x3f)/* https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/sys/dev/usb/ehcivar.h */#define EREAD4(sc, a) bus_space_read_4((sc)->iot, (sc)->ioh, (a))#define EWRITE4(sc, a, x) bus_space_write_4((sc)->iot, (sc)->ioh,(a), (x))#define EOREAD4(sc, a) bus_space_read_4((sc)->iot, (sc)->ioh, (sc)->sc_offs+(a))#define EOWRITE4(sc, a, x) bus_space_write_4((sc)->iot, (sc)->ioh,(sc)->sc_offs+(a), (x))
  • 39. 具体例: デバドラ 元 #2/* https://gitorious.org/metasepi/netbsd-arafura/blobs/arafura/sys/dev/usb/ehci.c */Static int ehci_intr1(ehci_softc_t *sc) { u_int32_t intrs, eintrs; intrs = EHCI_STS_INTRS(EOREAD4(sc, EHCI_USBSTS)); eintrs = intrs & sc->sc_eintrs; EOWRITE4(sc, EHCI_USBSTS, intrs); /* Acknowledge */ if (eintrs & EHCI_STS_IAA) { wakeup(&sc->sc_async_head); eintrs &= ~EHCI_STS_IAA; } if (eintrs & (EHCI_STS_INT | EHCI_STS_ERRINT)) { usb_schedsoftintr(&sc->sc_bus); eintrs &= ~(EHCI_STS_INT | EHCI_STS_ERRINT); } if (eintrs & EHCI_STS_PCD) { ehci_pcd(sc, sc->sc_intrxfer); eintrs &= ~EHCI_STS_PCD; } if (eintrs != 0) { sc->sc_eintrs &= ~eintrs; EOWRITE4(sc, EHCI_USBINTR, sc->sc_eintrs); }
  • 40. 具体例: このデバドラは何してる?
  • 41. 具体例: デバドラ スナッチ #1data UsbdBus = UsbdBus -- xxxdata SoftContext = SC { scBus :: UsbdBus , iot :: Int , ioh :: Int , scOffs :: Int , scEintrs :: Int , scAsyncHead :: Ptr Int , scIntrXfer :: Ptr Int }type BusSpace m a = StateT SoftContext m atype Addr = IntehciUsbsts, ehciUsbIntr :: AddrehciUsbsts = 0x04ehciUsbIntr = 0x08ehciStsIaa, ehciStsPcd, ehciStsErrInt, ehciStsInt :: IntehciStsIaa = 0x00000020ehciStsPcd = 0x00000004ehciStsErrInt = 0x00000002ehciStsInt = 0x00000001
  • 42. 具体例: デバドラ スナッチ #2evalTmpl :: Int -> (SoftContext -> IO a) -> Int -> BusSpace IO IntevalTmpl flag io ei | ei .&. flag /= 0 = go | otherwise = return ei where go = do sc <- get liftIO . io $ sc return $ ei .&. complement flagevalWakeup, evalSoftIntr, evalPcd :: Int -> BusSpace IO IntevalWakeup = evalTmpl ehciStsIaa $ wakeUp . scAsyncHeadevalSoftIntr = evalTmpl (ehciStsErrInt .|. ehciStsInt)(usbSchedSoftIntr . scBus)evalPcd = evalTmpl ehciStsPcd (sc -> ehciPcd sc . scIntrXfer $ sc)evalWrite :: Int -> BusSpace IO ()evalWrite ei = when (ei /= 0) go where go = do sc <- get let newEi = scEintrs sc .&. complement ei put $ sc {scEintrs = newEi} busSpaceOwrite4 ehciUsbIntr newEi
  • 43. 具体例: デバドラ スナッチ #3evaluateIntr1 :: BusSpace IO ()evaluateIntr1 = do intrs <- fmap ehciStsIntrs $ busSpaceOread4 ehciUsbsts sc <- get let eintrs = intrs .&. scEintrs sc busSpaceOwrite4 ehciUsbsts eintrs evalWrite =<< evalPcd =<< evalSoftIntr =<< evalWakeup eintrs return () where ehciStsIntrs r = r .&. 0x3fehciIntr1 :: SoftContext -> IO (Either () SoftContext)ehciIntr1 sc = return . Right =<< execStateT evaluateIntr1 scwakeUp = undefinedusbSchedSoftIntr = undefinedehciPcd = undefinedbusSpaceOread4 = undefinedbusSpaceOwrite4 = undefined
  • 44. この作り方のメリット/デメリットメリット☆ 動作可能な状態を保ったまま型づけ可能☆ つまりドッグフードできる☆ C言語コードと共存可能デメリット☆ 関数型言語を生かした設計にはならない
  • 45. 現状jhcでbootloaderの一部をHaskellで書けた
  • 46. デモ☆ 動画http://www.nicovideo.jp/watch/sm19788831☆ ソースコードhttps://gitorious.org/metasepi/netbsd-arafura
  • 47. これからの調査/実装計画☆ bootloaderを使った型づけトレーニング☆ jhcのソースコード解析☆ jhcのGCを組み込み向けに改造☆ jhcが吐くコードの再入/並列実行☆ kernelの型づけ手法の確立
  • 48. Metasepiがもたらす副産物☆ Haskellコンパイラ内部詳細理解☆ NetBSD kernelの深い理解☆ 組み込みHaskell分野開拓
  • 49. その他Metasepiプロジェクト近傍