9
9
はじめに
10
10
========
11
11
12
- Linuxにおける/proc/irq/\<IRQ\>/smp\_affinityはハードウェアにどのような設定を行うことにより実現されているのか 、或いは最近のPCアーキテクチャにおける割り込みの仕組みはどうなっているのか、という辺りが知りたかったので調べてみた。
12
+ Linuxにおける/proc/irq/\<IRQ\>/smp_affinityはハードウェアにどのような設定を行うことにより実現されているのか 、或いは最近のPCアーキテクチャにおける割り込みの仕組みはどうなっているのか、という辺りが知りたかったので調べてみた。
13
13
14
14
結構こんがらがっているので、予想外に時間を食ってしまった…まだ調べ尽くせていないが、一旦現時点での理解を書いておこうと思う。
15
15
@@ -23,7 +23,7 @@ Linuxにおける/proc/irq/\<IRQ\>/smp\_affinityはハードウェアにどの
23
23
24
24
3. Legacyな8259割り込みコントローラを使うことは考慮しない
25
25
26
- 4. x86\_64向けLinuxカーネル (解析に使っているバージョンは3.2.0+)が動作している
26
+ 4. x86_64向けLinuxカーネル (解析に使っているバージョンは3.2.0+)が動作している
27
27
28
28
5. 仮想化は使用しない
29
29
@@ -76,7 +76,7 @@ MSI-X割り込み
76
76
Capability Structure
77
77
--------------------
78
78
79
- @BIOSInitを見るとイメージが分かると思うが 、Configuration SpaceからLinked
79
+ @BIOSInit を見るとイメージが分かると思うが 、Configuration SpaceからLinked
80
80
List状に複数のcapabilityが繋がる構造になっていて、CAPIDが0xd0なのがMSIのフィールドで、ここにはMSICTL,
81
81
MSIAR, MSIDRの3つのレジスタがある。
82
82
@@ -168,38 +168,36 @@ Vectorに割り込み先LAPICのVector番号を指定。
168
168
Linuxカーネルで実際にレジスタの値を設定している所を見てみる
169
169
-----------------------------------------------------------
170
170
171
- msi\_compose\_msg [^1]でレジスタに書き込みたい値を用意しているので、これを見てみる。
172
- $ msg->address\_lo$がMSIARレジスタで、$ apic->irq\_dest\_mode$が0ならphysical
171
+ msi_compose_msg [^1]でレジスタに書き込みたい値を用意しているので、これを見てみる。
172
+ msg->address_loがMSIARレジスタで、 apic->irq_dest_modeが0ならphysical
173
173
mode、1ならlogical
174
- modeを設定、$ apic->irq\_delivery\_mode$がdest\_LowestPrioならRedirectable(MSI\_ADDR\_REDIRECTION\_LOWPRI )を、そうでなければDirected(MSI\_ADDR\_REDIRECTION\_CPU )を設定、変数destをDestination
174
+ modeを設定、apic->irq_delivery_modeがdest_LowestPrioならRedirectable(MSI_ADDR_REDIRECTION_LOWPRI )を、そうでなければDirected(MSI_ADDR_REDIRECTION_CPU )を設定、変数destをDestination
175
175
IDとして設定している。
176
176
177
- $ msg->data$がMSIDRレジスタで、$ apic->irq\_delivery\_mode$がdest\_LowestPrioならLowest
178
- priorityを、そうでなければFixedを設定、$ cfg->vector$の値をInterrupt
177
+ msg->dataがMSIDRレジスタで、 apic->irq_delivery_modeがdest_LowestPrioならLowest
178
+ priorityを、そうでなければFixedを設定、cfg->vectorの値をInterrupt
179
179
Vectorとして設定している。
180
180
181
- $ apic->irq\_dest\_mode$と$apic->irq\_delivery\_mode$の値はIO
182
- APICのドライバ毎に違うのだが、x86\_64の標準ドライバのapic\_flat\_64 .c[^2]ではirq\_dest\_modeは1 ,
183
- irq\_delivery\_modeはdest\_LowestPrioに設定されている 。
181
+ apic->irq_dest_modeとapic->irq_delivery_modeの値はIO
182
+ APICのドライバ毎に違うのだが、x86_64の標準ドライバのapic_flat_64 .c[^2]ではirq_dest_modeは1 ,
183
+ irq_delivery_modeはdest_LowestPrioに設定されている 。
184
184
185
- これらの値は割り込み初期化時に設定され、/proc/irq/\<IRQ\>/smp\_affinityの書き換え時にも維持される 。
186
- smp\_affinityの書き換え時には 、Destination IDとInterrupt
185
+ これらの値は割り込み初期化時に設定され、/proc/irq/\<IRQ\>/smp_affinityの書き換え時にも維持される 。
186
+ smp_affinityの書き換え時には 、Destination IDとInterrupt
187
187
Vectorだけが変更される[^3]。
188
188
189
189
全ての環境でLogical modeかつLowest
190
190
priorityが使えるとは限らないので、場合によってはPhysical
191
- Modeで初期化されていてsmp\_affinityの値を0xffにしてもCPU0にしか割り込まないという挙動を行う事も有り得る 。
191
+ Modeで初期化されていてsmp_affinityの値を0xffにしてもCPU0にしか割り込まないという挙動を行う事も有り得る 。
192
192
実際、論理CPUが12個あるCore i7上でLinux
193
193
3.2.0+を走らせている環境ではExtended Physical
194
194
Modeで初期化されていて、割り込み分散が行われていなかった。
195
195
196
- $ /proc/irq/<IRQ>/smp\_affinity$の書き換えでPCIコンフィグレーション空間はどのように書き換わるか
196
+ /proc/irq/\ <IRQ\>/smp_affinityの書き換えでPCIコンフィグレーション空間はどのように書き換わるか
197
197
----------------------------------------------------------------------------------------------
198
198
199
199
例えばThinkpad x200にはこんなデバイスがあります。 (dmesgから抜粋)
200
200
201
- [H]
202
-
203
201
e1000e : Intel(R) PRO/1000 Network Driver - 1.5.1-k
204
202
e1000e : Copyright(c) 1999 - 2011 Intel Corporation.
205
203
e1000e 0000:00:19.0 : PCI INT A -> GSI 20 (level, low) -> IRQ 20
@@ -212,14 +210,12 @@ $/proc/irq/<IRQ>/smp\_affinity$の書き換えでPCIコンフィグレーショ
212
210
213
211
IRQ44のMSI割り込みを一つ持つe1000eで、PCIのアドレスは00:19.0ですね。
214
212
215
- [H]
216
213
217
214
# cat /proc/irq/44/smp_affinity
218
215
3
219
216
220
217
CPUはcpu0とcpu1なので、全てのCPUのビットを立ててるから3。
221
218
222
- [H]
223
219
224
220
# grep eth4 /proc/interrupts
225
221
44 : 50037 49330 PCI-MSI-edge eth4
@@ -228,7 +224,6 @@ CPUはcpu0とcpu1なので、全てのCPUのビットを立ててるから3。
228
224
RegisterとMSI Data
229
225
Registerにはどのような値が設定されているか確認してみます。
230
226
231
- [H]
232
227
233
228
# lspci -vvvv -s 00:19.0
234
229
00:19.0 Ethernet controller : Intel Corporation 82567LM Gigabit Network Connection (rev 03)
@@ -259,8 +254,6 @@ MSI」の「Address」と「Data」の所ですが、これをビットフィー
259
254
260
255
こちらが改造後のコード[^4]になります。 早速実行してみます。
261
256
262
- [H]
263
-
264
257
# gcc -lpci msireg.c
265
258
# ./a.out 00:19.0
266
259
Message Signalled Interrupts : 64bit+ Queue=0/0 Enable+
@@ -269,9 +262,8 @@ MSI」の「Address」と「Data」の所ですが、これをビットフィー
269
262
data=41b9 trigger=edge level=assert delivery_mode=lowpri vector=185
270
263
271
264
Logical modeでLowpri、destid=3、vector=185になってるのが分かります。
272
- ここでsmp\_affinityを変えてみましょう 。
265
+ ここでsmp_affinityを変えてみましょう 。
273
266
274
- [H]
275
267
276
268
# echo 1 > /proc/irq/44/smp_affinity
277
269
# ./a.out 00:19.0
@@ -280,17 +272,7 @@ Logical modeでLowpri、destid=3、vector=185になってるのが分かりま
280
272
address_lo=fee0100c dest_mode=logical redirection=lowpri dest_id=1
281
273
data=41b9 trigger=edge level=assert delivery_mode=lowpri vector=185
282
274
283
- dest\_idが1に書き換わったのが見て取れます。
284
-
285
- <span>5</span> BIOSがPCI Expressを初期化する手順が見えてきた :
286
- なひたふJTAG日記
287
- <http://nahitafu.cocolog-nifty.com/nahitafu/2007/02/pci_express_2b63.html>
288
- Intel® 64 and IA-32 Architectures Software Developer Manuals
289
- <http://www.intel.com/content/www/us/en/processors/architectures-software-developer-manuals.html>
290
- Intel® 5520/5500 Chipset : Datasheet
291
- <http://www.intel.com/content/www/us/en/chipsets/5520-5500-chipset-ioh-datasheet.html>
292
- PCI Local Bus Specification Revision 3.0 PCI Express 2.0 Base
293
- Specification Revision 0.9
275
+ dest_idが1に書き換わったのが見て取れます。
294
276
295
277
[^1] : <http://lxr.linux.no/linux+v3.2/arch/x86/kernel/apic/io_apic.c#L3167>
296
278
@@ -299,3 +281,29 @@ Specification Revision 0.9
299
281
[^3] : <http://lxr.linux.no/linux+v3.2/arch/x86/kernel/apic/io_apic.c#L3201>
300
282
301
283
[^4] : <https://gist.github.com/1568777>
284
+
285
+ ライセンス
286
+ ==========
287
+
288
+ Copyright (c) 2014 Takuya ASADA. 全ての原稿データ は
289
+ クリエイティブ・コモンズ 表示 - 継承 4.0 国際
290
+ ライセンスの下に提供されています。
291
+
292
+ 参考文献
293
+ ========
294
+ ---
295
+ references:
296
+ - id: BIOSInit
297
+ title: 'BIOSがPCI Expressを初期化する手順が見えてきた:なひたふJTAG日記'
298
+ URL: 'http://nahitafu.cocolog-nifty.com/nahitafu/2007/02/pci_express_2b63.html '
299
+ - id: SDM
300
+ title: 'Intel® 64 and IA-32 Architectures Software Developer Manuals'
301
+ URL: 'http://www.intel.com/content/www/us/en/processors/architectures-software-developer-manuals.html '
302
+ - id: chipset
303
+ title: 'Intel® 5520/5500 Chipset: Datasheet'
304
+ URL: 'http://www.intel.com/content/www/us/en/chipsets/5520-5500-chipset-ioh-datasheet.html '
305
+ - id: PCI3.0
306
+ title: PCI Local Bus Specification Revision 3.0
307
+ - id: PCIe
308
+ title: PCI Express 2.0 Base Specification Revision 0.9
309
+ ...
0 commit comments