kernel に組み込む

i8253 PIT をアクセスするドライバのうち、i8253 の channel 1 を platform device として登録する i8253_ref_setup.c を kernel に組み込み、その結果を確かめることをします。

kernel source にパッチを当てる

添付ファイル filei8253_ref_setup.diff は kernel source に当てるパッチです。内容は Kconfig と Makefile 修正の詳細i8253_ref 全体のデータ構造i8253_ref_setup.c: kernel に platform device を登録する を参照して下さい。このファイルをダウンロードして、kernel source の root directory (linux-stable) にカレント・ディレクトリを移し、次の様にして kernel にパッチを当てます。色々と修正を試みた後、ソースを元に戻すことも考慮し、branch i8253_ref_setup を作る操作も込みで示しています。branch 名は好きに付けても良いです。

linux-stable $ git checkout -b i8253_ref_setup
linux-stable $ git patch down_loaded_directory/i8253_ref_setup.diff

続けて新しく追加した configuration 項目 (Kconfig の内容) を .config に反映するため make menuconfig を実行します。

linux-stable $ make menuconfig

menuconfig の中で Processor type and features を選択します。

 .config - Linux/x86 4.1.27 Kernel Configuration
 ──────────────────────────────────────────────────────────────────────────────
  ┌───────────────── Linux/x86 4.1.27 Kernel Configuration ─────────────────┐
  │  Arrow keys navigate the menu.  <Enter> selects submenus ---> (or empty │
  │  submenus ----).  Highlighted letters are hotkeys.  Pressing <Y>        │
  │  includes, <N> excludes, <M> modularizes features.  Press <Esc><Esc> to │
  │  exit, <?> for Help, </> for Search.  Legend: [*] built-in  [ ]         │
  │ ┌─────────────────────────────────────────────────────────────────────┐ │
  │ │    [*] 64-bit kernel                                                │ │
  │ │        General setup  --->                                          │ │
  │ │    [*] Enable loadable module support  --->                         │ │
  │ │    [*] Enable the block layer  --->                                 │ │
  │ │        Processor type and features  --->                            │ │
  │ │        Power management and ACPI options  --->                      │ │
  │ │        Bus options (PCI etc.)  --->                                 │ │
  │ │        Executable file formats / Emulations  --->                   │ │
  │ │    [*] Networking support  --->                                     │ │
  │ │        Device Drivers  --->                                         │ │
  │ │        Firmware Drivers  --->                                       │ │
  │ │        File systems  --->                                           │ │
  │ │        Kernel hacking  --->                                         │ │
  │ │        Security options  --->                                       │ │
  │ │    -*- Cryptographic API  --->                                      │ │
  │ │    -*- Virtualization  --->                                         │ │
  │ └────┴(+)─────────────────────────────────────────────────────────────┘ │
  ├─────────────────────────────────────────────────────────────────────────┤
  │        <Select>    < Exit >    < Help >    < Save >    < Load >         │
  └─────────────────────────────────────────────────────────────────────────┘

項目 I8253 PIT Refresh timer driver に * を付けた状態にします。menuconfig を .config に変更を反映する選択をして終了します。

 .config - Linux/x86 4.1.27 Kernel Configuration
 > Processor type and features; ────────────────────────────────────────────────
  ┌────────────────────── Processor type and features ──────────────────────┐
  │  Arrow keys navigate the menu.  <Enter> selects submenus ---> (or empty │
  │  submenus ----).  Highlighted letters are hotkeys.  Pressing <Y>        │
  │  includes, <N> excludes, <M> modularizes features.  Press <Esc><Esc> to │
  │  exit, <?> for Help, </> for Search.  Legend: [*] built-in  [ ]         │
  │ ┌────^(-)─────────────────────────────────────────────────────────────┐ │
  │ │    [*]   Enable IOSF sideband access through debugfs                │ │
  │ │    [*] Single-depth WCHAN output                                    │ │
  │ │    [*] Linux guest support  --->                                    │ │
  │ │        Processor family (Generic-x86-64)  --->                      │ │
  │ │    [*] Supported processor vendors  --->                            │ │
  │ │    [*] I8253 PIT Refresh timer driver (NEW)                         │ │
  │ │    [*] Enable DMI scanning                                          │ │
  │ │    [*] Old AMD GART IOMMU support                                   │ │
  │ │    [*] IBM Calgary IOMMU support                                    │ │
  │ │    [*]   Should Calgary be enabled by default?                      │ │
  │ │    [ ] Enable Maximum number of SMP Processors and NUMA Nodes       │ │
  │ │    (256) Maximum number of CPUs                                     │ │
  │ │    [*] SMT (Hyperthreading) scheduler support                       │ │
  │ │    [*] Multi-core scheduler support                                 │ │
  │ │        Preemption Model (Voluntary Kernel Preemption (Desktop))  ---│ │
  │ │    [*] Reroute for broken boot IRQs                                 │ │
  │ └────┴(+)─────────────────────────────────────────────────────────────┘ │
  ├─────────────────────────────────────────────────────────────────────────┤
  │        <Select>    < Exit >    < Help >    < Save >    < Load >         │
  └─────────────────────────────────────────────────────────────────────────┘

I8253 PIT Refresh timer driver の階層がおかしくないか?

"I8253 PIT Refresh timer driver" のメニュー階層に違和感があるのは確かです。メニュー階層を menu-endmenu で作るか、config 項目を "Device Drivers" の囲みの中に作るかすれば違和感は減ると思います。ソースファイルの位置と Kconfig ファイルの位置関係もなるべく近くにしつつ menuconfig も違和感なく構成するのに難しい題材なのかもしれません。Kconfig についての詳細は /Documentation/kbuild/kconfig-language.txt を見て下さい。

構築 と install

構築と install は チュートリアルページの構築編 を参考にして下さい。このページのパッチを当てる前に # make modules_install; make install が済んでいて、構築済みの kernel 起動を確認できているならば grub の修正と更新手順を省略して下さい。

動作確認

kernel に組み込んだ i8253_ref_setup.c で platform device を組み込みました。組み込んだ kernel を起動すると kernel (/drivers/base) で管理している device の情報に変化が起きています。変化を見ていきます。

/proc/ioports

i8253_ref_setup.c の中で resource 構造体の配列で定義した I/O ポートが /proc/ioports に反映されます。ポート名は /include/linux 以下に配置した i8253_ref.h の中で定義されています。

~ $ cd /proc
/proc $ cat ioports
0000-0cf7 : PCI Bus 0000:00
  0000-001f : dma1
  0020-0021 : pic1
  0040-0043 : timer0
    0041-0041 : refresh_counter
    0043-0043 : control_word
  0050-0053 : timer1
  0060-0060 : keyboard
  0061-0061 : PNP0800:00
  0064-0064 : keyboard
  0070-0071 : rtc0
  0080-008f : dma page reg
  00a0-00a1 : pic2
  00c0-00df : dma2
  00f0-00ff : PNP0C04:00
    00f0-00ff : fpu
  0170-0177 : 0000:00:06.0
    0170-0177 : pata_amd
-- snip --

/sys/devices/platform/i8253_ref.0.auto

i8253_ref_setup.c の中で platform_device_register() で登録したデバイスが i8253_ref.0.auto ディレクトリとして現れます。platform_device 構造体のメンバを id = PLATFORM_DEVID_AUTO, id_auto = true としたので、デバイス名の後ろに ".0.auto" が自動的に付加されています。

/proc $ cd /sys/devices/platform
/sys/devices/platform $ ls -la
total 0
drwxr-xr-x 13 root root    0  9  9 10:46 .
drwxr-xr-x 12 root root    0  9  9 10:46 ..
drwxr-xr-x  4 root root    0  9  9 10:46 Fixed MDIO bus.0
drwxr-xr-x  3 root root    0  9  9 10:46 PNP0C0B:00
drwxr-xr-x  3 root root    0  9  9 10:46 PNP0C0C:00
drwxr-xr-x  3 root root    0  9  9 10:46 alarmtimer
drwxr-xr-x  4 root root    0  9  9 10:46 i8042
drwxr-xr-x  3 root root    0  9  9 10:46 i8253_ref.0.auto
drwxr-xr-x  3 root root    0  9  9 10:46 pcspkr
drwxr-xr-x  3 root root    0  9  9 10:46 platform-framebuffer.0
drwxr-xr-x  2 root root    0  9 10 16:11 power
drwxr-xr-x  4 root root    0  9  9 10:46 reg-dummy
drwxr-xr-x  4 root root    0  9  9 10:46 serial8250
-rw-r--r--  1 root root 4096  9  9 10:46 uevent
/sys/devices/platform $ cd i8253_ref.0.auto
/sys/devices/platform/i8253_ref.0.auto $ ls -la
 0
drwxr-xr-x  3 root root    0  9 10 16:11 .
drwxr-xr-x 13 root root    0  9 10 16:11 ..
-rw-r--r--  1 root root 4096  9 10 16:11 driver_override
-r--r--r--  1 root root 4096  9 10 16:11 modalias
drwxr-xr-x  2 root root    0  9 10 16:11 power
lrwxrwxrwx  1 root root    0  9  9 10:46 subsystem -> ../../../bus/platform
-rw-r--r--  1 root root 4096  9  9 10:46 uevent

ドライバ i8253_ref.c を組み込むと /sys/devices/platform/i8253_ref.0.auto ディレクトリの中に counter, rate ノードが sysfs_create_group() の呼び出しによって作られます。次は i8253_ref.c から構築した i8253_ref.ko を組み込んだ後の様子です。

/sys/devices/platform/i8253_ref.0.auto # ls -la
total 0
drwxr-xr-x  3 root root    0  9 10 16:12 .
drwxr-xr-x 13 root root    0  9 10 16:11 ..
-r--r--r--  1 root root 4096  9 10 16:13 counter
lrwxrwxrwx  1 root root    0  9 10 16:13 driver -> ../../../bus/platform/drivers/i8253_ref
-rw-r--r--  1 root root 4096  9 10 16:11 driver_override
-rw-r--r--  1 root root 4096  9 10 16:13 dump_stack
-r--r--r--  1 root root 4096  9 10 16:11 modalias
drwxr-xr-x  2 root root    0  9 10 16:11 power
-rw-r--r--  1 root root 4096  9 10 16:13 rate
lrwxrwxrwx  1 root root    0  9 10 16:11 subsystem -> ../../../bus/platform
-rw-r--r--  1 root root 4096  9 10 16:11 uevent
/sys/devices/platform/i8253_ref.0.auto # echo 32768 > rate
/sys/devices/platform/i8253_ref.0.auto # cat rate
32768
/sys/devices/platform/i8253_ref.0.auto # cat counter
16752
/sys/devices/platform/i8253_ref.0.auto # cat counter
8201

kernel に静的にソースを結合する方法

パッチ filei8253_ref_setup.diff の中で、新しくソースファイルを用意する、あるいは既存のソースに修正を加えた場合に必要な作業の参考になる部分を見ていきます。

platform device として I8253 PIT を kernel に登録する処理 i8253_ref_setup.c を kernel に静的に結合する(スタティック・リンク)する方法を見ていきます。新しく作ったソース・ファイルを kernel にスタティック・リンクするのに最低限必要なことは次の通りです。

  • ソースを配置したディレクトリまたは root に辿る経路で近い場所にある Makefile を修正しコンパイル・リンクする対象に加える。
  • ソースファイルを配置したディレクトリまたは root に辿る経路で近い場所にある Kconfig ファイルに新しく作ったソースをコンパイル・リンク対象にするのかどうか make menuconfig で選択できる様にする。

make menuconfig で新しく加えたソース・ファイルをコンパイル対象にするかどうか選択できる様にしておくと、チーム開発をしている状況での問題の切り分け、開発環境の足並みが揃っていない状況で柔軟に対応することができます。

Makefile

/arch/x86/kernel/Makefile の変更箇所は次の通りです。

filei8253_ref-kernel-Makefile/Makefile.diff
  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
diff --git a/arch/x86/kernel/Makefile b/arch/x86/kernel/Makefile
index 9bcd0b5..077d68b 100644
--- a/arch/x86/kernel/Makefile
+++ b/arch/x86/kernel/Makefile
@@ -98,6 +98,7 @@ obj-$(CONFIG_PARAVIRT_CLOCK)  += pvclock.o
 obj-$(CONFIG_X86_PMEM_LEGACY)  += pmem.o
 
 obj-$(CONFIG_PCSPKR_PLATFORM)  += pcspeaker.o
+obj-$(CONFIG_I8253_REFRESH)    += i8253_ref_setup.o
 
 obj-$(CONFIG_X86_CHECK_BIOS_CORRUPTION) += check.o
 

obj-$(CONFIG_I8253_REFRESH) += i8253_ref_setup.o は CONFIG_I8253_REFRESH を展開した結果によって obj- += i8253_ref_setup.o または obj-y += i8253_ref_setup.o と解釈されます。ここでは出てきませんが CONFIG_I8253_REFRESH が tristate (モジュール) の場合は obj-m += i8253_ref_setup.o となる場合が有ります。obj-y += i8253_ref_setup.o となった場合、kernel に静的に結合します。

obj-* += file.o構築結果
obj- += file.ofile.c はコンパイルされない
obj-y += file.ofile.c は kernel に静的に結合(スタティックリンクされる)
obj-m += file.ofile.c はモジュールとして構築され file.ko が作られる (このページでは扱いません)

Kconfig

arch/x86/Kconfig の変更箇所は次の通りです。この Kconfig の位置は例外的に Makefile と ソースファイル i8253_ref_setup.c が有るディレクトリと違っています。この修正で make menuconfig で i8253_ref_setup.c を kernel に組み込むかどうか前節の Makefile の修正と併せ選択することができる様になります。詳細な書き方は /Documentation/kbuild/kconfig-language.txt を参照して下さい。

filei8253_ref-kernel-kconfig/Kconfig.diff
  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig
index 226d569..1074f0f 100644
--- a/arch/x86/Kconfig
+++ b/arch/x86/Kconfig
@@ -759,6 +759,14 @@ config APB_TIMER
          as it is off-chip. APB timers are always running regardless of CPU
          C states, they are used as per CPU clockevent device when possible.
 
+config I8253_REFRESH
+       bool "I8253 PIT Refresh timer driver"
+       default n
+       depends on X86
+       help
+         Access I8253 refresh timer.
+         Linux Driver Quest tutorial platform device.
+
 # Mark as expert because too many people got it wrong.
 # The code disables itself when not needed.
 config DMI

config I8253_REFRESH で選択項目を宣言します。ここでは接頭辞 CONFIG_ を付けずに書くことに注意して下さい。bool は y か n (定義しない)の選択だと言う意味です。default は n (定義しない)、 depends on X86 は X86(CONFIG_X86) が定義されれば選択項目に現れることを意味します。help は make menuconfig で help を要求したときに表示されるテキストです。他の項目で ---help--- と書かれているところもあります。どちらも同様に解釈されます。help の部分はインデントに意味があります。他の部分のインデントも慣例的に合わせて書くことをお勧めします。

追加した config 項目は make menuconfig のどこに現れるの?

make menuconfig を実行して追加した項目がどこに行ったか分からなくなるかもしれません。丁寧に Kconfig の menu-endmenu のネスティングを追って十分に理解する方法と、手っ取り早く知るために make menuconfig で対話的設定を開始したところで / を押してマクロ名を検索する方法があります。このページの例では I8253_REFRESH を探す文字列とします。Location: 以下に場所のパスが示されます。丁寧に Kconfig の階層構造を探すより早いです。

他の architecture や platform の場合、どこにソース・コードを追加して、どこの Makefile や Kconfig の修正をしたら良いの?

開発ターゲットの基板に実装されたテバイスを追加するために /arch/processor 以下に配置されたファイルを修正したり、追加するやり方に迷うかもしれません。ディレクトリ構成はプロセッサ(CPU)毎に大きく違います。見回してみて、しっくりする修正方法を考えてください。似たようなデバイスを見つけて並べるように修正するのが良いでしょう。他のプロセッサに比べて派生品種が多い ARM 系では /arch/arm/plat-platform に SoC 毎に派生するコード、/arch/arm/mach-machine に基板品種毎に派生する(付加した周辺回路によって派生する)コードが含まれることが多いです(SoC 毎に派生するコードもあります)。


添付ファイル: filei8253_ref_setup.diff 202件 [詳細]

トップ   編集 凍結 差分 バックアップ 添付 複製 名前変更 リロード   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS
Last-modified: 2017-09-14 (木) 01:59:26 (2434d)