เบšเบปเบ”เปเบ™เบฐเบ™เปเบฒเบชเบฑเป‰เบ™เป†เบเปˆเบฝเบงเบเบฑเบš BPF เปเบฅเบฐ eBPF

เบชเบฐเบšเบฒเบเบ”เบต, Habr! เบžเบงเบเป€เบฎเบปเบฒเบ•เป‰เบญเบ‡เบเบฒเบ™เปเบˆเป‰เบ‡เปƒเบซเป‰เบ—เปˆเบฒเบ™เบฎเบนเป‰เบงเปˆเบฒเบžเบงเบเป€เบฎเบปเบฒเบเปเบฒเบฅเบฑเบ‡เบเบฐเบเบฝเบกเบซเบ™เบฑเบ‡เบชเบทเบชเปเบฒเบฅเบฑเบšเบเบฒเบ™เบ›เปˆเบญเบ."Linux Observability เบเบฑเบš BPF".

เบšเบปเบ”เปเบ™เบฐเบ™เปเบฒเบชเบฑเป‰เบ™เป†เบเปˆเบฝเบงเบเบฑเบš BPF เปเบฅเบฐ eBPF
เบ™เบฑเบšเบ•เบฑเป‰เบ‡เปเบ•เปˆเป€เบ„เบทเปˆเบญเบ‡ virtual BPF เบชเบทเบšเบ•เปเปˆเบžเบฑเบ”เบ—เบฐเบ™เบฒเปเบฅเบฐเบ–เบทเบเบ™เปเบฒเปƒเบŠเป‰เบขเปˆเบฒเบ‡เบˆเบดเบ‡เบˆเบฑเบ‡เปƒเบ™เบเบฒเบ™เบ›เบฐเบ•เบดเบšเบฑเบ”, เบžเบงเบเป€เบฎเบปเบฒเป„เบ”เป‰เปเบ›เบšเบปเบ”เบ„เบงเบฒเบกเบ—เบตเปˆเบญเบฐเบ—เบดเบšเบฒเบเป€เบ–เบดเบ‡เบ„เบงเบฒเบกเบชเบฒเบกเบฒเบ”เบ•เบปเป‰เบ™เบ•เปเปเบฅเบฐเบชเบฐเบ–เบฒเบ™เบฐเปƒเบ™เบ›เบฐเบˆเบธเบšเบฑเบ™เบชเปเบฒเบฅเบฑเบšเบ—เปˆเบฒเบ™.

เปƒเบ™เบŠเบธเบกเบ›เบตเบกเปเปˆเป†เบกเบฒเบ™เบตเป‰, เป€เบ„เบทเปˆเบญเบ‡เบกเบทเปเบฅเบฐเป€เบ•เบฑเบเบ™เบดเบเบเบฒเบ™เบ‚เบฝเบ™เป‚เบ›เบฅเปเบเบฅเบกเป„เบ”เป‰เบเบฒเบเป€เบ›เบฑเบ™เบ—เบตเปˆเบ™เบดเบเบปเบกเบซเบฅเบฒเบเบ‚เบถเป‰เบ™เป€เบžเบทเปˆเบญเบŠเบปเบ”เป€เบŠเบตเบเบ‚เปเป‰เบˆเปเบฒเบเบฑเบ”เบ‚เบญเบ‡ Linux kernel เปƒเบ™เบเปเบฅเบฐเบ™เบตเบ—เบตเปˆเบ•เป‰เบญเบ‡เบเบฒเบ™เบเบฒเบ™เบ›เบธเบ‡เปเบ•เปˆเบ‡เปเบžเบฑเบเป€เบเบฑเบ”เบ—เบตเปˆเบกเบตเบ›เบฐเบชเบดเบ”เบ—เบดเบžเบฒเบšเบชเบนเบ‡. เบซเบ™เบถเปˆเบ‡เปƒเบ™เป€เบ•เบฑเบเบ™เบดเบเบ—เบตเปˆเบ™เบดเบเบปเบกเบ—เบตเปˆเบชเบธเบ”เบ‚เบญเบ‡เบ›เบฐเป€เบžเบ”เบ™เบตเป‰เปเบกเปˆเบ™เป€เบญเบตเป‰เบ™เบงเปˆเบฒ เบ‚เป‰เบฒเบก kernel (kernel bypass) เปเบฅเบฐเบญเบฐเบ™เบธเบเบฒเบ”เปƒเบซเป‰, bypassing เบŠเบฑเป‰เบ™เป€เบ„เบทเบญเบ‚เปˆเบฒเบ kernel, เป€เบžเบทเปˆเบญเบ›เบฐเบ•เบดเบšเบฑเบ”เบเบฒเบ™เบ›เบฐเบกเบงเบ™เบœเบปเบ™ packet เบ—เบฑเบ‡เบซเบกเบปเบ”เบˆเบฒเบเบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰. Bypassing kernel เบเบฑเบ‡เบเปˆเบฝเบงเบ‚เป‰เบญเบ‡เบเบฑเบšเบเบฒเบ™เบ„เบงเบšเบ„เบธเบกเบšเบฑเบ”เป€เบ„เบทเบญเบ‚เปˆเบฒเบเบˆเบฒเบ เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰. เปƒเบ™เบ„เปเบฒเบชเบฑเบšเบ•เปˆเบฒเบ‡เป†เบญเบทเปˆเบ™เป†, เป€เบกเบทเปˆเบญเป€เบฎเบฑเบ”เบงเบฝเบเบเบฑเบšเบšเบฑเบ”เป€เบ„เบทเบญเบ‚เปˆเบฒเบ, เบžเบงเบเป€เบฎเบปเบฒเบญเบตเบ‡เปƒเบชเปˆเบ„เบปเบ™เบ‚เบฑเบš เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰.

เป‚เบ”เบเบเบฒเบ™เป‚เบญเบ™เบเบฒเบ™เบ„เบงเบšเบ„เบธเบกเบญเบฑเบ™เป€เบ•เบฑเบกเบ—เบตเปˆเบ‚เบญเบ‡เบšเบฑเบ”เป€เบ„เบทเบญเบ‚เปˆเบฒเบเป„เบ›เบซเบฒเป‚เบ„เบ‡เบเบฒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰, เบžเบงเบเป€เบฎเบปเบฒเบซเบผเบธเบ”เบœเปˆเบญเบ™ kernel overhead (เบเบฒเบ™เบ›เปˆเบฝเบ™เบชเบฐเบžเบฒเบšเบเบฒเบ™, เบเบฒเบ™เบ›เบธเบ‡เปเบ•เปˆเบ‡เบŠเบฑเป‰เบ™เป€เบ„เบทเบญเบ‚เปˆเบฒเบ, เบเบฒเบ™เบ‚เบฑเบ”เบ‚เบงเบฒเบ‡, เปเบฅเบฐเบญเบทเปˆเบ™เป†), เป€เบŠเบดเปˆเบ‡เบกเบตเบ„เบงเบฒเบกเบชเปเบฒเบ„เบฑเบ™เบซเบผเบฒเบเป€เบกเบทเปˆเบญเปเบฅเปˆเบ™เบ”เป‰เบงเบเบ„เบงเบฒเบกเป„เบง 10Gb / s เบซเบผเบทเบชเบนเบ‡เบเบงเปˆเบฒ. Kernel bypass เบšเบงเบเบเบฑเบšเบเบฒเบ™เบ›เบฐเบชเบปเบกเบ›เบฐเบชเบฒเบ™เบ‚เบญเบ‡เบฅเบฑเบเบชเบฐเบ™เบฐเบญเบทเปˆเบ™เป† (เบเบฒเบ™โ€‹เบ›เบธเบ‡โ€‹เปเบ•เปˆเบ‡ batchโ€‹) เปเบฅเบฐโ€‹เบเบฒเบ™โ€‹เบ›เบฑเบšโ€‹เบ›เบฐโ€‹เบ•เบดโ€‹เบšเบฑเบ”โ€‹เบขเปˆเบฒเบ‡โ€‹เบฅเบฐโ€‹เบกเบฑเบ”โ€‹เบฅเบฐโ€‹เบงเบฑเบ‡ (เบšเบฑเบ™เบŠเบต NUMA, เบเบฒเบ™เปเบเบ CPU, เปเบฅเบฐเบญเบทเปˆเบ™เป†) เบชเบญเบ”เบ„เปˆเบญเบ‡เบเบฑเบšเบžเบทเป‰เบ™เบ–เบฒเบ™เบ‚เบญเบ‡เบเบฒเบ™เบ›เบฐเบกเบงเบ™เบœเบปเบ™เป€เบ„เบทเบญเบ‚เปˆเบฒเบเบ—เบตเปˆเบกเบตเบ›เบฐเบชเบดเบ”เบ—เบดเบžเบฒเบšเบชเบนเบ‡เปƒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบ‚เบญเบ‡เบœเบนเป‰เปƒเบŠเป‰. เบšเบฒเบ‡เบ—เบตเบ•เบปเบงเบขเปˆเบฒเบ‡เบ—เบตเปˆเป€เบ›เบฑเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡เบ‚เบญเบ‡เบงเบดเบ—เบตเบเบฒเบ™เปƒเบซเบกเปˆเปƒเบ™เบเบฒเบ™เบ›เบธเบ‡เปเบ•เปˆเบ‡เปเบžเบฑเบเป€เบเบฑเบ”เปเบกเปˆเบ™ DPDK เบˆเบฒเบ Intel (เบŠเบธเบ”เบ‚เปเป‰เบกเบนเบ™เปเบœเบ™เบžเบฑเบ”เบ—เบฐเบ™เบฒ), เป€เบ–เบดเบ‡เปเบกเปˆเบ™เบงเปˆเบฒเบกเบตเป€เบ„เบทเปˆเบญเบ‡เบกเบทเปเบฅเบฐเป€เบ•เบฑเบเบ™เบดเบเบ—เบตเปˆเบกเบตเบŠเบทเปˆเบชเบฝเบ‡เบญเบทเปˆเบ™เป†, เบฅเบงเบกเบ—เบฑเบ‡ VPP เบ‚เบญเบ‡ Cisco (Vector Packet Processing), Netmap เปเบฅเบฐ, เปเบ™เปˆเบ™เบญเบ™, เบ‡เบน.

เบเบฒเบ™โ€‹เบˆเบฑเบ”โ€‹เบ•เบฑเป‰เบ‡โ€‹เบเบฒเบ™โ€‹เบžเบปเบงโ€‹เบžเบฑเบ™โ€‹เป€เบ„เบทเบญโ€‹เบ‚เปˆเบฒเบโ€‹เปƒเบ™โ€‹เบžเบทเป‰เบ™โ€‹เบ—เบตเปˆโ€‹เบœเบนเป‰โ€‹เปƒเบŠเป‰โ€‹เบกเบตโ€‹เบ‚เปเป‰โ€‹เป€เบชเบโ€‹เบˆเปเบฒโ€‹เบ™เบงเบ™โ€‹เบซเบ™เบถเปˆเบ‡โ€‹:

  • OS kernel เปเบกเปˆเบ™เบŠเบฑเป‰เบ™ abstraction เบชเปเบฒเบฅเบฑเบšเบŠเบฑเบšเบžเบฐเบเบฒเบเบญเบ™เบฎเบฒเบ”เปเบง. เป€เบ™เบทเปˆเบญเบ‡เบˆเบฒเบเบงเปˆเบฒเป‚เบ„เบ‡เบเบฒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰เบ•เป‰เบญเบ‡เบˆเบฑเบ”เบเบฒเบ™เบŠเบฑเบšเบžเบฐเบเบฒเบเบญเบ™เบ‚เบญเบ‡เป€เบ‚เบปเบฒเป€เบˆเบปเป‰เบฒเป‚เบ”เบเบเบปเบ‡, เบžเบงเบเป€เบ‚เบปเบฒเบเบฑเบ‡เบ•เป‰เบญเบ‡เบˆเบฑเบ”เบเบฒเบ™เบฎเบฒเบ”เปเบงเบ‚เบญเบ‡เบ•เบปเบ™เป€เบญเบ‡. เบ™เบตเป‰เบกเบฑเบเบˆเบฐเบซเบกเบฒเบเป€เบ–เบดเบ‡เบเบฒเบ™เบ”เปเบฒเป€เบ™เบตเบ™เป‚เบ„เบ‡เบเบฒเบ™เป„เบ”เป€เบงเบตเบ‚เบญเบ‡เบ—เปˆเบฒเบ™เป€เบญเบ‡.
  • เป€เบ™เบทเปˆเบญเบ‡เบˆเบฒเบเบงเปˆเบฒเบžเบงเบเป€เบฎเบปเบฒเบเปเบฒเบฅเบฑเบ‡เบ›เบฐเบ–เบดเป‰เบกเบžเบทเป‰เบ™เบ—เบตเปˆ kernel เบ—เบฑเบ‡เบซเบกเบปเบ”, เบžเบงเบเป€เบฎเบปเบฒเบเบฑเบ‡เบเบปเบเป€เบฅเบตเบเบเบฒเบ™เบ—เปเบฒเบ‡เบฒเบ™เบ‚เบญเบ‡เป€เบ„เบทเบญเบ‚เปˆเบฒเบเบ—เบฑเบ‡เบซเบกเบปเบ”เบ—เบตเปˆเบชเบฐเบซเบ™เบญเบ‡เปƒเบซเป‰เป‚เบ”เบ kernel. เป‚เบ›เบฅเปเบเบฅเบกเบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰เบ•เป‰เบญเบ‡เบ›เบฐเบ•เบดเบšเบฑเบ”เบ„เบธเบ™เบชเบปเบกเบšเบฑเบ”เปƒเบซเบกเปˆเบ—เบตเปˆเบญเบฒเบ”เบˆเบฐเบชเบฐเบซเบ™เบญเบ‡เปƒเบซเป‰เป‚เบ”เบ kernel เบซเบผเบทเบฅเบฐเบšเบปเบšเบ›เบฐเบ•เบดเบšเบฑเบ”เบเบฒเบ™.
  • เบšเบฑเบ™เบ”เบฒเป‚เบ„เบ‡เบเบฒเบ™เป€เบฎเบฑเบ”เบงเบฝเบเบขเบนเปˆเปƒเบ™เป‚เบซเบกเบ” sandbox, เป€เบŠเบดเปˆเบ‡เบˆเปเบฒเบเบฑเบ”เบเบฒเบ™เป‚เบ•เป‰เบ•เบญเบšเบ‚เบญเบ‡เบžเบงเบเป€เบ‚เบปเบฒเบขเปˆเบฒเบ‡เบˆเบดเบ‡เบˆเบฑเบ‡เปเบฅเบฐเบ›เป‰เบญเบ‡เบเบฑเบ™เบšเปเปˆเปƒเบซเป‰เบžเบงเบเป€เบ‚เบปเบฒเบ›เบฐเบชเบปเบกเบ›เบฐเบชเบฒเบ™เบเบฑเบšเบžเบฒเบเบชเปˆเบงเบ™เบญเบทเปˆเบ™เป†เบ‚เบญเบ‡เบฅเบฐเบšเบปเบšเบ›เบฐเบ•เบดเบšเบฑเบ”เบเบฒเบ™.

เป‚เบ”เบเป€เบ™เบทเป‰เบญเปเบ—เป‰เปเบฅเป‰เบง, เปƒเบ™เป€เบงเบฅเบฒเบ—เบตเปˆเป€เบ„เบทเบญเบ‚เปˆเบฒเบเปƒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰, เบœเบปเบ™เบ›เบฐเป‚เบซเบเบ”เบ”เป‰เบฒเบ™เบเบฒเบ™เบ›เบฐเบ•เบดเบšเบฑเบ”เปเบกเปˆเบ™เบšเบฑเบ™เบฅเบธเป„เบ”เป‰เป‚เบ”เบเบเบฒเบ™เบเป‰เบฒเบเบเบฒเบ™เบ›เบธเบ‡เปเบ•เปˆเบ‡เปเบžเบฑเบเป€เบเบฑเบ”เบˆเบฒเบเปเบเปˆเบ™เป„เบ›เบซเบฒเบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰. XDP เป€เบฎเบฑเบ”เบเบปเบ‡เบเบฑเบ™เบ‚เป‰เบฒเบกเบขเปˆเบฒเบ‡เปเบ—เป‰เบˆเบดเบ‡: เบกเบฑเบ™เบเป‰เบฒเบเป‚เบ„เบ‡เบเบฒเบ™เป€เบ„เบทเบญเบ‚เปˆเบฒเบเบˆเบฒเบเบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰ (เบ•เบปเบงเบเบญเบ‡, เบ•เบปเบงเปเบเป‰เป„เบ‚, เป€เบชเบฑเป‰เบ™เบ—เบฒเบ‡, เปเบฅเบฐเบญเบทเปˆเบ™เป†) เป€เบ‚เบปเป‰เบฒเป„เบ›เปƒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเปเบเปˆเบ™. XDP เบญเบฐเบ™เบธเบเบฒเบ”เปƒเบซเป‰เบžเบงเบเป€เบฎเบปเบฒเบ›เบฐเบ•เบดเบšเบฑเบ”เบซเบ™เป‰เบฒเบ—เบตเปˆเป€เบ„เบทเบญเบ‚เปˆเบฒเบเบ—เบฑเบ™เบ—เบตเบ—เบตเปˆเปเบžเบฑเบเป€เบเบฑเบ”เบ•เบตเบเบฑเบšเบเบฒเบ™เป‚เบ•เป‰เบ•เบญเบšเป€เบ„เบทเบญเบ‚เปˆเบฒเบเปเบฅเบฐเบเปˆเบญเบ™เบ—เบตเปˆเบกเบฑเบ™เบˆเบฐเป€เบฅเบตเปˆเบกเป€เบ„เบทเปˆเบญเบ™เบเป‰เบฒเบเป„เบ›เบชเบนเปˆเบฅเบฐเบšเบปเบšเบเปˆเบญเบเป€เบ„เบทเบญเบ‚เปˆเบฒเบ kernel. เบ”เบฑเปˆเบ‡เบ™เบฑเป‰เบ™, เบ„เบงเบฒเบกเป„เบงเบเบฒเบ™เบ›เบธเบ‡เปเบ•เปˆเบ‡เปเบžเบฑเบเป€เบเบฑเบ”เป€เบžเบตเปˆเบกเบ‚เบถเป‰เบ™เบขเปˆเบฒเบ‡เบซเบผเบงเบ‡เบซเบผเบฒเบ. เบขเปˆเบฒเบ‡เปƒเบ”เบเปเบ•เบฒเบก, kernel เบญเบฐเบ™เบธเบเบฒเบ”เปƒเบซเป‰เบœเบนเป‰เปƒเบŠเป‰เบ›เบฐเบ•เบดเบšเบฑเบ”เป‚เบ„เบ‡เบเบฒเบ™เบ‚เบญเบ‡เป€เบ‚เบปเบฒเป€เบˆเบปเป‰เบฒเบขเบนเปˆเปƒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆ kernel เปเบ™เบงเปƒเบ”? เบเปˆเบญเบ™เบ—เบตเปˆเบˆเบฐเบ•เบญเบšเบ„เปเบฒเบ–เบฒเบกเบ™เบตเป‰, เปƒเบซเป‰เป€เบšเบดเปˆเบ‡เบงเปˆเบฒ BPF เปเบกเปˆเบ™เบซเบเบฑเบ‡.

BPF เปเบฅเบฐ eBPF

เป€เบ–เบดเบ‡เบงเปˆเบฒเบˆเบฐเบกเบตเบŠเบทเปˆเบ—เบตเปˆเบชเบฑเบšเบชเบปเบ™, BPF (Berkeley Packet Filtering) เปเบกเปˆเบ™, เปƒเบ™เบ„เบงเบฒเบกเป€เบ›เบฑเบ™เบˆเบดเบ‡, เบฎเบนเบšเปเบšเบšเป€เบ„เบทเปˆเบญเบ‡ virtual. เป€เบ„เบทเปˆเบญเบ‡ virtual เบ™เบตเป‰เป„เบ”เป‰เบ–เบทเบเบญเบญเบเปเบšเบšเปƒเบ™เป€เบšเบทเป‰เบญเบ‡เบ•เบปเป‰เบ™เป€เบžเบทเปˆเบญเบˆเบฑเบ”เบเบฒเบ™เบเบฑเบšเบเบฒเบ™เบเบฑเปˆเบ™เบ•เบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”, เป€เบžเบฒเบฐเบชเบฐเบ™เบฑเป‰เบ™เบˆเบถเปˆเบ‡เบกเบตเบŠเบทเปˆ.

เบซเบ™เบถเปˆเบ‡เปƒเบ™เป€เบ„เบทเปˆเบญเบ‡เบกเบทเบ—เบตเปˆเบกเบตเบŠเบทเปˆเบชเบฝเบ‡เบ—เบตเปˆเบชเบธเบ”เบ—เบตเปˆเปƒเบŠเป‰ BPF เปเบกเปˆเบ™ tcpdump. เป€เบกเบทเปˆเบญเบˆเบฑเบšเปเบžเบฑเบเป€เบเบฑเบ”เป‚เบ”เบเปƒเบŠเป‰ tcpdump เบœเบนเป‰เปƒเบŠเป‰เบชเบฒเบกเบฒเบ”เบฅเบฐเบšเบธเบเบฒเบ™เบชเบฐเปเบ”เบ‡เบญเบญเบเป€เบžเบทเปˆเบญเบเบฑเปˆเบ™เบ•เบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”. เบชเบฐเป€เบžเบฒเบฐเปเบžเบฑเบเป€เบเบฑเบ”เบ—เบตเปˆเบเบปเบ‡เบเบฑเบšเบเบฒเบ™เบชเบฐเปเบ”เบ‡เบœเบปเบ™เบ™เบตเป‰เบˆเบฐเบ–เบทเบเบšเบฑเบ™เบ—เบถเบ. เบชเปเบฒเบฅเบฑเบšเบ•เบปเบงเบขเปˆเบฒเบ‡, เบ„เปเบฒเบงเปˆเบฒ "tcp dst port 80โ€ เปเบฒเบเป€เบ–เบดเบ‡เปเบžเบฑเบเป€เบเบฑเบ” TCP เบ—เบฑเบ‡เปเบปเบ”เบ—เบตเปˆเบกเบฒเบฎเบญเบ”เบžเบญเบ” 80. เบ„เบญเบกเบžเบตเบงเป€เบŠเบตเบชเบฒเบกเบฒเบ”เบซเบเปเป‰เบเบฒเบ™เบชเบฐเปเบ”เบ‡เบญเบญเบเบ™เบตเป‰เป‚เบ”เบเบเบฒเบ™เบ›เปˆเบฝเบ™เป€เบ›เบฑเบ™ BPF bytecode.

$ sudo tcpdump -d "tcp dst port 80"
(000) ldh [12] (001) jeq #0x86dd jt 2 jf 6
(002) ldb [20] (003) jeq #0x6 jt 4 jf 15
(004) ldh [56] (005) jeq #0x50 jt 14 jf 15
(006) jeq #0x800 jt 7 jf 15
(007) ldb [23] (008) jeq #0x6 jt 9 jf 15
(009) ldh [20] (010) jset #0x1fff jt 15 jf 11
(011) ldxb 4*([14]&0xf)
(012) ldh [x + 16] (013) jeq #0x50 jt 14 jf 15
(014) ret #262144
(015) ret #0

เบ™เบตเป‰เปเบกเปˆเบ™เบชเบดเปˆเบ‡เบ—เบตเปˆเป‚เบ„เบ‡เบเบฒเบ™เบ‚เป‰เบฒเบ‡เป€เบ—เบดเบ‡เบ™เบตเป‰เป€เบฎเบฑเบ”เป‚เบ”เบเบžเบทเป‰เบ™เบ–เบฒเบ™:

  • เบ„เปเบฒเปเบ™เบฐเบ™เปเบฒ (000): เป‚เบซเบฅเบ”เปเบžเบฑเบเป€เบเบฑเบ”เบขเบนเปˆเบ—เบตเปˆ offset 12, เป€เบ›เบฑเบ™เบ„เปเบฒ 16-bit, เป€เบ‚เบปเป‰เบฒเป„เบ›เปƒเบ™ accumulator. Offset 12 เป€เบ—เบปเปˆเบฒเบเบฑเบš ethertype เบ‚เบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”.
  • เบ„เปเบฒเปเบ™เบฐเบ™เปเบฒ (001): เบ›เบฝเบšเบ—เบฝเบšเบ„เปˆเบฒเปƒเบ™ accumulator เบเบฑเบš 0x86dd, เบ™เบฑเป‰เบ™เปเบกเปˆเบ™, เบ”เป‰เบงเบเบ„เปˆเบฒ ethertype เบชเปเบฒเบฅเบฑเบš IPv6. เบ–เป‰เบฒเบœเบปเบ™เป„เบ”เป‰เบฎเบฑเบšเปเบกเปˆเบ™เบ„เบงเบฒเบกเบˆเบดเบ‡, เบซเบผเบฑเบ‡เบˆเบฒเบเบ™เบฑเป‰เบ™, เป‚เบ›เบฅเปเบเบฅเบก counter เป„เบ›เบซเบฒเบ„เปเบฒเปเบ™เบฐเบ™เปเบฒ (002), เปเบฅเบฐเบ–เป‰เบฒเบšเปเปˆเปเบกเปˆเบ™, เบซเบผเบฑเบ‡เบˆเบฒเบเบ™เบฑเป‰เบ™เป„เบ›เบซเบฒ (006).
  • เบ„เปเบฒเปเบ™เบฐเบ™เปเบฒ (006): เบ›เบฝเบšเบ—เบฝเบšเบ„เปˆเบฒเบเบฑเบš 0x800 (เบ„เปˆเบฒ ethertype เบชเปเบฒเบฅเบฑเบš IPv4). เบ–เป‰เบฒเบ„เปเบฒเบ•เบญเบšเปเบกเปˆเบ™เบ„เบงเบฒเบกเบˆเบดเบ‡, เบซเบผเบฑเบ‡เบˆเบฒเบเบ™เบฑเป‰เบ™เป‚เบ„เบ‡เบเบฒเบ™เบˆเบฐเป„เบ›เบซเบฒ (007), เบ–เป‰เบฒเบšเปเปˆเปเบกเปˆเบ™, เบซเบผเบฑเบ‡เบˆเบฒเบเบ™เบฑเป‰เบ™เป„เบ›เบซเบฒ (015).

เปเบฅเบฐเบญเบทเปˆเบ™เป†เบˆเบปเบ™เบเปˆเบงเบฒเป‚เบ„เบ‡เบเบฒเบ™เบเบฒเบ™เบเบฑเปˆเบ™เบ•เบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”เบˆเบฐเบชเบปเปˆเบ‡เบ„เบทเบ™เบœเบปเบ™เป„เบ”เป‰เบฎเบฑเบš. เบ›เบปเบเบเบฐเบ•เบดเปเบฅเป‰เบงเบ™เบตเป‰เปเบกเปˆเบ™ Boolean. เบเบฒเบ™เบชเบปเปˆเบ‡เบ„เบทเบ™เบ„เปˆเบฒเบ—เบตเปˆเบšเปเปˆเปเบกเปˆเบ™เบชเบนเบ™ (เบ„เปเบฒเปเบ™เบฐเบ™เปเบฒ (014)) เบซเบกเบฒเบเบ„เบงเบฒเบกเบงเปˆเบฒเปเบžเบฑเบเป€เบเบฑเบ”เบ–เบทเบเบเบญเบกเบฎเบฑเบš, เปเบฅเบฐเบเบฒเบ™เบชเบปเปˆเบ‡เบ„เบทเบ™เบ„เปˆเบฒเบชเบนเบ™ (เบ„เปเบฒเปเบ™เบฐเบ™เปเบฒ (015)) เบซเบกเบฒเบเบ„เบงเบฒเบกเบงเปˆเบฒเปเบžเบฑเบเป€เบเบฑเบ”เบšเปเปˆเป„เบ”เป‰เบฎเบฑเบšเบเบฒเบ™เบเบญเบกเบฎเบฑเบš.

เป€เบ„เบทเปˆเบญเบ‡ virtual BPF เปเบฅเบฐ bytecode เป„เบ”เป‰เบ–เบทเบเบชเบฐเป€เบซเบ™เบตเป‚เบ”เบ Steve McCann เปเบฅเบฐ Van Jacobson เปƒเบ™เบ—เป‰เบฒเบเบ›เบต 1992 เป€เบกเบทเปˆเบญเป€เบญเบเบฐเบชเบฒเบ™เบ‚เบญเบ‡เบžเบงเบเป€เบ‚เบปเบฒเบ–เบทเบเบ•เบตเบžเบดเบก. BSD Packet Filter: เบชเบฐเบ–เบฒเบ›เบฑเบ”เบ•เบฐเบเบฐเบเปเบฒเปƒเบซเบกเปˆเบชเปเบฒเบฅเบฑเบšเบเบฒเบ™เบˆเบฑเบš Packet เบฅเบฐเบ”เบฑเบšเบœเบนเป‰เปƒเบŠเป‰, เป€เบ•เบฑเบเป‚เบ™เป‚เบฅเบขเบตเบ™เบตเป‰เป„เบ”เป‰เบ–เบทเบเบ™เปเบฒเบชเบฐเป€เบซเบ™เบตเบ„เบฑเป‰เบ‡เบ—เปเบฒเบญเบดเบ”เปƒเบ™เบเบญเบ‡เบ›เบฐเบŠเบธเบก Usenix เปƒเบ™เบฅเบฐเบ”เบนเบซเบ™เบฒเบงเบ‚เบญเบ‡ 1993.

เป€เบ™เบทเปˆเบญเบ‡เบˆเบฒเบเบงเปˆเบฒ BPF เป€เบ›เบฑเบ™เป€เบ„เบทเปˆเบญเบ‡ virtual, เบกเบฑเบ™เบเปเบฒเบ™เบปเบ”เบชเบฐเบžเบฒเบšเปเบงเบ”เบฅเป‰เบญเบกเบ—เบตเปˆเป‚เบ„เบ‡เบเบฒเบ™เบ”เปเบฒเป€เบ™เบตเบ™เบเบฒเบ™. เบ™เบญเบเป€เบซเบ™เบทเบญเป„เบ›เบˆเบฒเบ bytecode, เบกเบฑเบ™เบเบฑเบ‡เบเปเบฒเบ™เบปเบ”เบฎเบนเบšเปเบšเบšเบซเบ™เปˆเบงเบเบ„เบงเบฒเบกเบˆเปเบฒ batch (เบ„เปเบฒเปเบ™เบฐเบ™เปเบฒเบเบฒเบ™เป‚เบซเบผเบ”เป„เบ”เป‰เบ–เบทเบเบ™เปเบฒเปƒเบŠเป‰ implicitly เบเบฑเบš batch), เบฅเบปเบ‡เบ—เบฐเบšเบฝเบ™ (A เปเบฅเบฐ X; accumulator เปเบฅเบฐเบ”เบฑเบ”เบชเบฐเบ™เบต), เบเบฒเบ™เป€เบเบฑเบšเบฎเบฑเบเบชเบฒเบซเบ™เปˆเบงเบเบ„เบงเบฒเบกเบˆเปเบฒ scratch, เปเบฅเบฐเบ•เบปเบงเบ•เป‰เบฒเบ™เป‚เบ„เบ‡เบเบฒเบ™ implicit. เบซเบ™เป‰เบฒเบชเบปเบ™เปƒเบˆ, BPF bytecode เป„เบ”เป‰เบ–เบทเบเบชเป‰เบฒเบ‡เปเบšเบšเบˆเปเบฒเบฅเบญเบ‡เบซเบผเบฑเบ‡เบˆเบฒเบ Motorola 6502 ISA. เบ”เบฑเปˆเบ‡เบ—เบตเปˆ Steve McCann เบˆเบทเปˆเป„เบงเป‰เปƒเบ™เบฅเบฒเบง เบšเบปเบ”เบฅเบฒเบเบ‡เบฒเบ™เบเบญเบ‡เบ›เบฐเบŠเบธเบก เบขเบนเปˆเบ—เบตเปˆ Sharkfest '11, เบฅเบฒเบงเบกเบตเบ„เบงเบฒเบกเบ„เบธเป‰เบ™เป€เบ„เบตเบเบเบฑเบšเบเบฒเบ™เบเปเปˆเบชเป‰เบฒเบ‡ 6502 เบˆเบฒเบเบเบฒเบ™เบ‚เบฝเบ™เป‚เบ›เบฅเปเบเบฅเบกเปƒเบ™เป‚เบฎเบ‡เบฎเบฝเบ™เบกเบฑเบ”เบ—เบฐเบเบปเบกเปƒเบ™ Apple II, เปเบฅเบฐเบ„เบงเบฒเบกเบฎเบนเป‰เบ™เบตเป‰เบกเบตเบญเบดเบ”เบ—เบดเบžเบปเบ™เบ•เปเปˆเบเบฒเบ™เป€เบฎเบฑเบ”เบงเบฝเบเบ‚เบญเบ‡เบฅเบฒเบงเปƒเบ™เบเบฒเบ™เบญเบญเบเปเบšเบš BPF bytecode.

เบเบฒเบ™เบชเบฐเบซเบ™เบฑเบšเบชเบฐเบซเบ™เบนเบ™ BPF เปเบกเปˆเบ™เบ–เบทเบเบ›เบฐเบ•เบดเบšเบฑเบ”เปƒเบ™ Linux kernel เปƒเบ™เบฎเบธเปˆเบ™ v2.5 เปเบฅเบฐเบชเบนเบ‡เบเบงเปˆเบฒ, เป€เบžเบตเปˆเบกเป‚เบ”เบเบชเปˆเบงเบ™เปƒเบซเบเปˆเปเบกเปˆเบ™เบ„เบงเบฒเบกเบžเบฐเบเบฒเบเบฒเบกเบ‚เบญเบ‡ Jay Schullist. เบฅเบฐเบซเบฑเบ” BPF เบเบฑเบ‡เบ„เบปเบ‡เบšเปเปˆเบ›เปˆเบฝเบ™เปเบ›เบ‡เบˆเบปเบ™เบเปˆเบงเบฒ 2011, เป€เบกเบทเปˆเบญ Eric Dumaset เป„เบ”เป‰เบญเบญเบเปเบšเบšเบ•เบปเบงเปเบ›เบžเบฒเบชเบฒ BPF เบ„เบทเบ™เปƒเปเปˆเป€เบžเบทเปˆเบญเป€เบฎเบฑเบ”เบงเบฝเบเปƒเบ™เบฎเบนเบšเปเบšเบš JIT (เปเบซเบผเปˆเบ‡เบ‚เปเป‰เบกเบนเบ™: JIT เบชเปเบฒเบฅเบฑเบšเบ•เบปเบงเบเบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”). เบซเบผเบฑเบ‡เบˆเบฒเบเบ™เบฑเป‰เบ™, kernel, เปเบ—เบ™เบ—เบตเปˆเบˆเบฐเบ•เบตเบ„เบงเบฒเบกเบซเบกเบฒเบ BPF bytecode, เบชเบฒเบกเบฒเบ”เบ›เปˆเบฝเบ™เป‚เบ›เบผเปเบเบผเบก BPF เป‚เบ”เบเบเบปเบ‡เบเบฑเบšเบชเบฐเบ–เบฒเบ›เบฑเบ”เบ•เบฐเบเบฐเบเปเบฒเป€เบ›เบปเป‰เบฒเบซเบกเบฒเบ: x86, ARM, MIPS, เปเบฅเบฐเบญเบทเปˆเบ™เป†.

เบ•เปเปˆเบกเบฒ, เปƒเบ™เบ›เบต 2014, Alexey Starovoitov เป„เบ”เป‰เบชเบฐเป€เบซเบ™เบตเบเบปเบ™เป„เบ JIT เปƒเบซเบกเปˆเบชเปเบฒเบฅเบฑเบš BPF. เปƒเบ™เบ„เบงเบฒเบกเป€เบ›เบฑเบ™เบˆเบดเบ‡, JIT เปƒเบซเบกเปˆเบ™เบตเป‰เป„เบ”เป‰เบเบฒเบเป€เบ›เบฑเบ™เบชเบฐเบ–เบฒเบ›เบฑเบ”เบ•เบฐเบเบฐเบเปเบฒ BPF เปƒเบซเบกเปˆเปเบฅเบฐเบ–เบทเบเป€เบญเบตเป‰เบ™เบงเปˆเบฒ eBPF. เบ‚เป‰เบฒเบžเบฐเป€เบˆเบปเป‰เบฒเบ„เบดเบ”เบงเปˆเบฒ VMs เบ—เบฑเบ‡เบชเบญเบ‡เบขเบนเปˆเบฎเปˆเบงเบกเบเบฑเบ™เบชเปเบฒเบฅเบฑเบšเบšเบฒเบ‡เป€เบงเบฅเบฒ, เปเบ•เปˆเบ›เบฐเบˆเบธเบšเบฑเบ™เบเบฒเบ™เบเบฑเปˆเบ™เบ•เบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”เบ–เบทเบเบ›เบฐเบ•เบดเบšเบฑเบ”เป‚เบ”เบเบญเบตเบ‡เปƒเบชเปˆ eBPF. เปƒเบ™เบ„เบงเบฒเบกเป€เบ›เบฑเบ™เบˆเบดเบ‡, เปƒเบ™เบซเบผเบฒเบเป†เบ•เบปเบงเบขเปˆเบฒเบ‡เบ‚เบญเบ‡เป€เบญเบเบฐเบชเบฒเบ™เบ—เบตเปˆเบ—เบฑเบ™เบชเบฐเป„เบซเบก, BPF เปเบกเปˆเบ™เป€เบ‚เบปเป‰เบฒเปƒเบˆเบงเปˆเบฒ eBPF, เปเบฅเบฐ BPF เบ„เบฅเบฒเบชเบชเบดเบเปเบกเปˆเบ™เป€เบ›เบฑเบ™เบ—เบตเปˆเบฎเบนเป‰เบˆเบฑเบเปƒเบ™เบกเบทเป‰เบ™เบตเป‰เบงเปˆเบฒ cBPF.

eBPF เบ‚เบฐเบซเบเบฒเบเป€เบ„เบทเปˆเบญเบ‡ virtual BPF เบ„เบฅเบฒเบชเบชเบดเบเปƒเบ™เบซเบผเบฒเบเบงเบดเบ—เบต:

  • เบญเบตเบ‡เปƒเบชเปˆเบชเบฐเบ–เบฒเบ›เบฑเบ”เบ•เบฐเบเบฐเบเปเบฒ 64-bit เบ—เบตเปˆเบ—เบฑเบ™เบชเบฐเป„เบซเบก. eBPF เปƒเบŠเป‰เบเบฒเบ™เบฅเบปเบ‡เบ—เบฐเบšเบฝเบ™ 64-bit เปเบฅเบฐเป€เบžเบตเปˆเบกเบˆเปเบฒเบ™เบงเบ™เบเบฒเบ™เบฅเบปเบ‡เบ—เบฐเบšเบฝเบ™เบ—เบตเปˆเบกเบตเบขเบนเปˆเบˆเบฒเบ 2 (accumulator เปเบฅเบฐ X) เป€เบ›เบฑเบ™ 10. eBPF เบเบฑเบ‡เบชเบฐเบซเบ™เบญเบ‡ opcodes เป€เบžเบตเปˆเบกเป€เบ•เบตเบก (BPF_MOV, BPF_JNE, BPF_CALL ... ).
  • เปเบเบเบญเบญเบเบˆเบฒเบเบฅเบฐเบšเบปเบšเบเปˆเบญเบเบŠเบฑเป‰เบ™เบ‚เปเป‰เบกเบนเบ™เป€เบ„เบทเบญเบ‚เปˆเบฒเบ. BPF เป„เบ”เป‰เบ–เบทเบเบœเบนเบเบกเบฑเบ”เบเบฑเบšเบ•เบปเบงเปเบšเบšเบ‚เปเป‰เบกเบนเบ™ batch. เป€เบ™เบทเปˆเบญเบ‡เบˆเบฒเบเบกเบฑเบ™เบ–เบทเบเบ™เปเบฒเปƒเบŠเป‰เบชเปเบฒเบฅเบฑเบšเบเบฒเบ™เบเบฑเปˆเบ™เบ•เบญเบ‡เปเบžเบฑเบเป€เบเบฑเบ”, เบฅเบฐเบซเบฑเบ”เบ‚เบญเบ‡เบกเบฑเบ™เบขเบนเปˆเปƒเบ™เบฅเบฐเบšเบปเบšเบเปˆเบญเบเบ—เบตเปˆเบชเบฐเบซเบ™เบญเบ‡เบเบฒเบ™เบชเบทเปˆเบชเบฒเบ™เป€เบ„เบทเบญเบ‚เปˆเบฒเบ. เบขเปˆเบฒเบ‡เปƒเบ”เบเปเบ•เบฒเบก, เป€เบ„เบทเปˆเบญเบ‡ virtual eBPF เบšเปเปˆเป„เบ”เป‰เบ•เบดเบ”เบเบฑเบšเบ•เบปเบงเปเบšเบšเบ‚เปเป‰เบกเบนเบ™เบญเบตเบเบ•เปเปˆเป„เบ›เปเบฅเบฐเบชเบฒเบกเบฒเบ”เบ–เบทเบเบ™เปเบฒเปƒเบŠเป‰เป€เบžเบทเปˆเบญเบˆเบธเบ”เบ›เบฐเบชเบปเบ‡เปƒเบ”เบเปเปˆเบ•เบฒเบก. เบ”เบฑเปˆเบ‡เบ™เบฑเป‰เบ™, เปƒเบ™เบ›เบฑเบ”เบˆเบธเบšเบฑเบ™เป‚เบ„เบ‡เบเบฒเบ™ eBPF เบชเบฒเบกเบฒเบ”เป€เบŠเบทเปˆเบญเบกเบ•เปเปˆเบเบฑเบš tracepoint เบซเบผเบท kprobe. เบ™เบตเป‰เป€เบ›เบตเบ”เบ—เบฒเบ‡เป„เบ›เบชเบนเปˆเป€เบ„เบทเปˆเบญเบ‡เบกเบท eBPF, เบเบฒเบ™เบงเบดเป€เบ„เบฒเบฐเบ›เบฐเบชเบดเบ”เบ—เบดเบžเบฒเบš, เปเบฅเบฐเบซเบผเบฒเบเป†เบเปเบฅเบฐเบ™เบตเบเบฒเบ™เบ™เปเบฒเปƒเบŠเป‰เปƒเบ™เบชเบฐเบžเบฒเบšเบเบฒเบ™เบ‚เบญเบ‡เบฅเบฐเบšเบปเบšเบเปˆเบญเบ kernel เบญเบทเปˆเบ™เป†. เปƒเบ™เบ›เบฑเบ”เบˆเบธเบšเบฑเบ™เบฅเบฐเบซเบฑเบ” eBPF เปเบกเปˆเบ™เบขเบนเปˆเปƒเบ™เป€เบชเบฑเป‰เบ™เบ—เบฒเบ‡เบ‚เบญเบ‡เบ•เบปเบ™เป€เบญเบ‡: kernel / bpf.
  • เบšเปˆเบญเบ™เป€เบเบฑเบšเบ‚เปเป‰เบกเบนเบ™เบ—เบปเปˆเบงเป‚เบฅเบเป€เบญเบตเป‰เบ™เบงเปˆเบฒเปเบœเบ™เบ—เบตเปˆ. เปเบœเบ™โ€‹เบ—เบตเปˆโ€‹เป€เบ›เบฑเบ™โ€‹เบšเปˆเบญเบ™โ€‹เป€เบเบฑเบšโ€‹เบ‚เปเป‰โ€‹เบกเบนเบ™โ€‹เบ—เบตเปˆโ€‹เบกเบตโ€‹เบ„เบธเบ™โ€‹เบ„เปˆเบฒโ€‹เบ—เบตเปˆโ€‹เป€เบฎเบฑเบ”โ€‹เปƒเบซเป‰โ€‹เบเบฒเบ™โ€‹เปเบฅเบโ€‹เบ›เปˆเบฝเบ™โ€‹เบ‚เปเป‰โ€‹เบกเบนเบ™โ€‹เบฅเบฐโ€‹เบซเบงเปˆเบฒเบ‡โ€‹เบžเบทเป‰เบ™โ€‹เบ—เบตเปˆโ€‹เบœเบนเป‰โ€‹เปƒเบŠเป‰โ€‹เปเบฅเบฐโ€‹เบŠเปˆเบญเบ‡ kernelโ€‹. eBPF เบชเบฐเปœเบญเบ‡เปเบœเบ™เบ—เบตเปˆเบซเบผเบฒเบเบ›เบฐเป€เบžเบ”.
  • เบซเบ™เป‰เบฒเบ—เบตเปˆเบฎเบญเบ‡. เป‚เบ”เบเบชเบฐเป€เบžเบฒเบฐ, เป€เบžเบทเปˆเบญเบ‚เบฝเบ™เบŠเบธเบ”เปƒเบซเบกเปˆ, เบ„เบดเบ”เป„เบฅเปˆ checksum, เบซเบผเบท clone เบŠเบธเบ”. เบŸเบฑเบ‡เบŠเบฑเบ™เป€เบซเบผเบปเปˆเบฒเบ™เบตเป‰เบ”เปเบฒเป€เบ™เบตเบ™เบเบฒเบ™เบžเบฒเบเปƒเบ™ kernel เปเบฅเบฐเบšเปเปˆเปเบกเปˆเบ™เป‚เบ„เบ‡เบเบฒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰. เบ™เบญเบเบ™เบฑเป‰เบ™เบ—เปˆเบฒเบ™เบเบฑเบ‡เบชเบฒเบกเบฒเบ”เป‚เบ—เบซเบฒเบฅเบฐเบšเบปเบšเบˆเบฒเบเป‚เบ„เบ‡เบเบฒเบ™ eBPF.
  • เบชเบดเป‰เบ™เบชเบธเบ”เบเบฒเบ™เป‚เบ—. เบ‚เบฐเบซเบ™เบฒเบ”เบ‚เบญเบ‡เป‚เบ›เบฅเปเบเบฅเบกเปƒเบ™ eBPF เบ–เบทเบเบˆเปเบฒเบเบฑเบ”เบขเบนเปˆเบ—เบตเปˆ 4096 bytes. เบ„เบธเบ™เบ™เบฐเบชเบปเบกเบšเบฑเบ”เบเบฒเบ™เป‚เบ—เบซเบฒเบ‡เบญเบฐเบ™เบธเบเบฒเบ”เปƒเบซเป‰เป‚เบ„เบ‡เบเบฒเบ™ eBPF เป‚เบญเบ™เบเบฒเบ™เบ„เบงเบšเบ„เบธเบกเป„เบ›เบเบฑเบ‡เป‚เบ„เบ‡เบเบฒเบ™ eBPF เปƒเบซเบกเปˆเปเบฅเบฐเบ”เบฑเปˆเบ‡เบ™เบฑเป‰เบ™เบˆเบถเปˆเบ‡ bypass เบ‚เปเป‰เบˆเปเบฒเบเบฑเบ”เบ™เบตเป‰ (เป€เบ–เบดเบ‡ 32 เป‚เบ„เบ‡เบเบฒเบ™เบชเบฒเบกเบฒเบ”เป€เบŠเบทเปˆเบญเบกเบ•เปเปˆเบ”เป‰เบงเบเบงเบดเบ—เบตเบ™เบตเป‰).

eBPF: เบ•เบปเบงเบขเปˆเบฒเบ‡

เบกเบตเบ•เบปเบงเบขเปˆเบฒเบ‡เบˆเปเบฒเบ™เบงเบ™เบซเบ™เบถเปˆเบ‡เบชเปเบฒเบฅเบฑเบš eBPF เปƒเบ™เปเบซเบผเปˆเบ‡ Linux kernel. เบžเบงเบเป€เบ‚เบปเบฒเป€เบˆเบปเป‰เบฒเบกเบตเบขเบนเปˆเปƒเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡ / bpf /. เป€เบžเบทเปˆเบญเบฅเบงเบšเบฅเบงเบกเบ•เบปเบงเบขเปˆเบฒเบ‡เป€เบซเบผเบปเปˆเบฒเบ™เบตเป‰, เบžเบฝเบ‡เปเบ•เปˆเปƒเบชเปˆ:

$ sudo make samples/bpf/

เบ‚เป‰เบญเบเบˆเบฐเบšเปเปˆเบ‚เบฝเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡เปƒเบซเบกเปˆเบชเปเบฒเบฅเบฑเบš eBPF เบ•เบปเบงเป€เบญเบ‡, เปเบ•เปˆเบˆเบฐเปƒเบŠเป‰เบซเบ™เบถเปˆเบ‡เปƒเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡เบ—เบตเปˆเบกเบตเบขเบนเปˆเปƒเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡ / bpf /. เบ‚เป‰เบญเบเบˆเบฐเป€เบšเบดเปˆเบ‡เบšเบฒเบ‡เบชเปˆเบงเบ™เบ‚เบญเบ‡เบฅเบฐเบซเบฑเบ”เปเบฅเบฐเบญเบฐเบ—เบดเบšเบฒเบเบงเปˆเบฒเบกเบฑเบ™เป€เบฎเบฑเบ”เบงเบฝเบเปเบ™เบงเปƒเบ”. เบ•เบปเบงเบขเปˆเบฒเบ‡, เบ‚เป‰เบญเบเป€เบฅเบทเบญเบเป‚เบ„เบ‡เบเบฒเบ™ tracex4.

เป‚เบ”เบเบ—เบปเปˆเบงเป„เบ›, เปเบ•เปˆเบฅเบฐเบ•เบปเบงเบขเปˆเบฒเบ‡เปƒเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡ / bpf / เบ›เบฐเบเบญเบšเบ”เป‰เบงเบเบชเบญเบ‡เป„เบŸเบฅเปŒ. เปƒเบ™โ€‹เบเปโ€‹เบฅเบฐโ€‹เบ™เบตโ€‹เบ™เบตเป‰:

  • tracex4_kern.c, เบกเบตเบฅเบฐเบซเบฑเบ”เปเบซเบผเปˆเบ‡เบ—เบตเปˆเบˆเบฐเบ–เบทเบเบ›เบฐเบ•เบดเบšเบฑเบ”เบขเบนเปˆเปƒเบ™ kernel เป€เบ›เบฑเบ™ eBPF bytecode.
  • tracex4_user.c, เบกเบตเป‚เบ„เบ‡เบเบฒเบ™เบˆเบฒเบเบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰.

เปƒเบ™เบเปเบฅเบฐเบ™เบตเบ™เบตเป‰, เบžเบงเบเป€เบฎเบปเบฒเบˆเปเบฒเป€เบ›เบฑเบ™เบ•เป‰เบญเบ‡เบฅเบงเบšเบฅเบงเบก tracex4_kern.c เบเบฑเบš eBPF bytecode. เปƒเบ™เบ›เบฑเบ”เบˆเบธเบšเบฑเบ™เบขเบนเปˆเปƒเบ™ gcc เบšเปเปˆเบกเบต backend เบชเปเบฒเบฅเบฑเบš eBPF. เป‚เบŠเบเบ”เบต, clang เบชเบฒเบกเบฒเบ”เบญเบญเบ eBPF bytecode. Makefile เบเบฒเบ™เบ™เปเบฒเปƒเบŠเป‰ clang เบชเปเบฒเบฅเบฑเบšเบเบฒเบ™เบฅเบงเบšเบฅเบงเบก tracex4_kern.c เป„เบ›เบซเบฒเป„เบŸเบฅเปŒเบงเบฑเบ”เบ–เบธ.

เบ‚เป‰เบฒเบžเบฐเป€เบˆเบปเป‰เบฒเป„เบ”เป‰เบเปˆเบฒเบงเป€เบ–เบดเบ‡เบ‚เป‰เบฒเบ‡เป€เบ—เบดเบ‡เบงเปˆเบฒเบซเบ™เบถเปˆเบ‡เปƒเบ™เบฅเบฑเบเบชเบฐเบ™เบฐเบ—เบตเปˆเบซเบ™เป‰เบฒเบชเบปเบ™เปƒเบˆเบ—เบตเปˆเบชเบธเบ”เบ‚เบญเบ‡ eBPF เปเบกเปˆเบ™เปเบœเบ™เบ—เบตเปˆ. tracex4_kern เบเปเบฒเบ™เบปเบ”เปเบœเบ™เบ—เบตเปˆเบซเบ™เบถเปˆเบ‡:

struct pair {
    u64 val;
    u64 ip;
};  

struct bpf_map_def SEC("maps") my_map = {
    .type = BPF_MAP_TYPE_HASH,
    .key_size = sizeof(long),
    .value_size = sizeof(struct pair),
    .max_entries = 1000000,
};

BPF_MAP_TYPE_HASH เปเบกเปˆเบ™เบซเบ™เบถเปˆเบ‡เปƒเบ™เบซเบผเบฒเบเบ›เบฐเป€เบžเบ”เบ‚เบญเบ‡เบšเบฑเบ”เบ—เบตเปˆเบชเบฐเป€เบซเบ™เบตเป‚เบ”เบ eBPF. เปƒเบ™เบเปเบฅเบฐเบ™เบตเบ™เบตเป‰, เบกเบฑเบ™เป€เบ›เบฑเบ™เบžเบฝเบ‡เปเบ•เปˆ hash. เบ—เปˆเบฒเบ™เบญเบฒเบ”เบˆเบฐเป„เบ”เป‰เบชเบฑเบ‡เป€เบเบ”เป€เบซเบฑเบ™เบเบฒเบ™เป‚เบ„เบชเบฐเบ™เบฒ SEC("maps"). SEC เปเบกเปˆเบ™เบกเบฐเบซเบฒเบžเบฒเบเบ—เบตเปˆเปƒเบŠเป‰เป€เบžเบทเปˆเบญเบชเป‰เบฒเบ‡เบžเบฒเบเบชเปˆเบงเบ™เปƒเปเปˆเบ‚เบญเบ‡เป„เบŸเบฅเปŒเบ„เบนเปˆ. เปƒเบ™เบ„เบงเบฒเบกเป€เบ›เบฑเบ™เบˆเบดเบ‡, เปƒเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡ tracex4_kern เบชเบญเบ‡โ€‹เบžเบฒเบโ€‹เบชเปˆเบงเบ™โ€‹เป€เบžเบตเปˆเบกโ€‹เป€เบ•เบตเบกโ€‹เป„เบ”เป‰โ€‹เบ–เบทเบโ€‹เบเปเบฒโ€‹เบ™เบปเบ”โ€‹:

SEC("kprobe/kmem_cache_free")
int bpf_prog1(struct pt_regs *ctx)
{   
    long ptr = PT_REGS_PARM2(ctx);

    bpf_map_delete_elem(&my_map, &ptr); 
    return 0;
}
    
SEC("kretprobe/kmem_cache_alloc_node") 
int bpf_prog2(struct pt_regs *ctx)
{
    long ptr = PT_REGS_RC(ctx);
    long ip = 0;

    // ะฟะพะปัƒั‡ะฐะตะผ ip-ะฐะดั€ะตั ะฒั‹ะทั‹ะฒะฐัŽั‰ะตะน ัั‚ะพั€ะพะฝั‹ kmem_cache_alloc_node() 
    BPF_KRETPROBE_READ_RET_IP(ip, ctx);

    struct pair v = {
        .val = bpf_ktime_get_ns(),
        .ip = ip,
    };
    
    bpf_map_update_elem(&my_map, &ptr, &v, BPF_ANY);
    return 0;
}   

เบชเบญเบ‡เบŸเบฑเบ‡เบŠเบฑเบ™เบ™เบตเป‰เบญเบฐเบ™เบธเบเบฒเบ”เปƒเบซเป‰เบ—เปˆเบฒเบ™เบฅเบถเบšเบฅเบฒเบเบเบฒเบ™เบญเบญเบเบˆเบฒเบเปเบœเบ™เบ—เบตเปˆ (kprobe/kmem_cache_free) เปเบฅเบฐโ€‹เป€เบžเบตเปˆเบกโ€‹เบเบฒเบ™โ€‹เป€เบ‚เบปเป‰เบฒโ€‹เปƒเบซเบกเปˆโ€‹เปƒเบ™โ€‹เปเบœเบ™โ€‹เบ—เบตเปˆ (kretprobe/kmem_cache_alloc_node). เบŠเบทเปˆเบŸเบฑเบ‡เบŠเบฑเบ™เบ—เบฑเบ‡เปเบปเบ”เบ—เบตเปˆเบ‚เบฝเบ™เบ”เป‰เบงเบเบ•เบปเบงเบžเบดเบกเปƒเบซเบเปˆเปเบกเปˆเบ™เบเบปเบ‡เบเบฑเบš macros เบ—เบตเปˆเป„เบ”เป‰เบเบณเบ™เบปเบ”เป„เบงเป‰เปƒเบ™ bpf_helpers.h.

เบ–เป‰เบฒเบ‚เป‰เบญเบเบ–เบดเป‰เบกเบžเบฒเบเบชเปˆเบงเบ™เบ‚เบญเบ‡เป„เบŸเบฅเปŒเบงเบฑเบ”เบ–เบธ, เบ‚เป‰เบญเบเบ„เบงเบ™เบˆเบฐเป€เบซเบฑเบ™เบงเปˆเบฒเบžเบฒเบเบชเปˆเบงเบ™เปƒเบซเบกเปˆเป€เบซเบผเบปเปˆเบฒเบ™เบตเป‰เบ–เบทเบเบเปเบฒเบ™เบปเบ”เป„เบงเป‰เปเบฅเป‰เบง:

$ objdump -h tracex4_kern.o

tracex4_kern.o: file format elf64-little

Sections:
Idx Name Size VMA LMA File off Algn
0 .text 00000000 0000000000000000 0000000000000000 00000040 2**2
CONTENTS, ALLOC, LOAD, READONLY, CODE
1 kprobe/kmem_cache_free 00000048 0000000000000000 0000000000000000 00000040 2**3
CONTENTS, ALLOC, LOAD, RELOC, READONLY, CODE
2 kretprobe/kmem_cache_alloc_node 000000c0 0000000000000000 0000000000000000 00000088 2**3
CONTENTS, ALLOC, LOAD, RELOC, READONLY, CODE
3 maps 0000001c 0000000000000000 0000000000000000 00000148 2**2
CONTENTS, ALLOC, LOAD, DATA
4 license 00000004 0000000000000000 0000000000000000 00000164 2**0
CONTENTS, ALLOC, LOAD, DATA
5 version 00000004 0000000000000000 0000000000000000 00000168 2**2
CONTENTS, ALLOC, LOAD, DATA
6 .eh_frame 00000050 0000000000000000 0000000000000000 00000170 2**3
CONTENTS, ALLOC, LOAD, RELOC, READONLY, DATA

เบเบฑเบ‡เบกเบต tracex4_user.c, เป‚เบ„เบ‡โ€‹เบเบฒเบ™โ€‹เบ•เบปเป‰เบ™โ€‹เบ•เปโ€‹. เป‚เบ”เบเบžเบทเป‰เบ™เบ–เบฒเบ™เปเบฅเป‰เบง, เป‚เบ„เบ‡เบเบฒเบ™เบ™เบตเป‰เบŸเบฑเบ‡เป€เบซเบ”เบเบฒเบ™ kmem_cache_alloc_node. เป€เบกเบทเปˆเบญเป€เบซเบ”เบเบฒเบ™เบ”เบฑเปˆเบ‡เบเปˆเบฒเบงเป€เบเบตเบ”เบ‚เบทเป‰เบ™, เบฅเบฐเบซเบฑเบ” eBPF เบ—เบตเปˆเบชเบญเบ”เบ„เป‰เบญเบ‡เบเบฑเบ™เบˆเบฐเบ–เบทเบเบ›เบฐเบ•เบดเบšเบฑเบ”. เบฅเบฐเบซเบฑเบ”เบšเบฑเบ™เบ—เบถเบเบ„เบธเบ™เบฅเบฑเบเบชเบฐเบ™เบฐ IP เบ‚เบญเบ‡เบงเบฑเบ”เบ–เบธเป€เบ‚เบปเป‰เบฒเป„เบ›เปƒเบ™เปเบœเบ™เบ—เบตเปˆ, เปเบฅเบฐเบˆเบฒเบเบ™เบฑเป‰เบ™เบงเบฑเบ”เบ–เบธเบˆเบฐเบ–เบทเบ looped เบœเปˆเบฒเบ™เป‚เบ„เบ‡เบเบฒเบ™เบ•เบปเป‰เบ™เบ•เป. เบ•เบปเบงเบขเปˆเบฒเบ‡:

$ sudo ./tracex4
obj 0xffff8d6430f60a00 is 2sec old was allocated at ip ffffffff9891ad90
obj 0xffff8d6062ca5e00 is 23sec old was allocated at ip ffffffff98090e8f
obj 0xffff8d5f80161780 is 6sec old was allocated at ip ffffffff98090e8f

เป‚เบ„เบ‡เบเบฒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰เปเบฅเบฐเป‚เบ„เบ‡เบเบฒเบ™ eBPF เบกเบตเบ„เบงเบฒเบกเบเปˆเบฝเบงเบ‚เป‰เบญเบ‡เปเบ™เบงเปƒเบ”? เบเปˆเบฝเบงเบเบฑเบšเบเบฒเบ™เป€เบฅเบตเปˆเบกเบ•เบปเป‰เบ™ tracex4_user.c เป‚เบซเบผเบ”เป„เบŸเบฅเปŒเบงเบฑเบ”เบ–เบธ tracex4_kern.o เบเบฒเบ™โ€‹เบ™เปเบฒโ€‹เปƒเบŠเป‰โ€‹เบซเบ™เป‰เบฒโ€‹เบ—เบตเปˆโ€‹ load_bpf_file.

int main(int ac, char **argv)
{
    struct rlimit r = {RLIM_INFINITY, RLIM_INFINITY};
    char filename[256];
    int i;

    snprintf(filename, sizeof(filename), "%s_kern.o", argv[0]);

    if (setrlimit(RLIMIT_MEMLOCK, &r)) {
        perror("setrlimit(RLIMIT_MEMLOCK, RLIM_INFINITY)");
        return 1;
    }

    if (load_bpf_file(filename)) {
        printf("%s", bpf_log_buf);
        return 1;
    }

    for (i = 0; ; i++) {
        print_old_objects(map_fd[1]);
        sleep(1);
    }

    return 0;
}

เปƒเบ™เบ‚เบฐเบ™เบฐเบ—เบตเปˆเป€เบฎเบฑเบ” load_bpf_file probes เบ—เบตเปˆเบเปเบฒเบ™เบปเบ”เป„เบงเป‰เปƒเบ™เป„เบŸเบฅเปŒ eBPF เป„เบ”เป‰เบ–เบทเบเป€เบžเบตเปˆเบกเปƒเบชเปˆ /sys/kernel/debug/tracing/kprobe_events. เปƒเบ™เบ›เบฑเบ”เบˆเบธเบšเบฑเบ™เบžเบงเบเป€เบฎเบปเบฒเบŸเบฑเบ‡เป€เบซเบ”เบเบฒเบ™เป€เบซเบผเบปเปˆเบฒเบ™เบตเป‰เปเบฅเบฐเป‚เบ„เบ‡เบเบฒเบ™เบ‚เบญเบ‡เบžเบงเบเป€เบฎเบปเบฒเบชเบฒเบกเบฒเบ”เป€เบฎเบฑเบ”เบšเบฒเบ‡เบชเบดเปˆเบ‡เบšเบฒเบ‡เบขเปˆเบฒเบ‡เปƒเบ™เป€เบงเบฅเบฒเบ—เบตเปˆเบžเบงเบเป€เบ‚เบปเบฒเป€เบเบตเบ”เบ‚เบถเป‰เบ™.

$ sudo cat /sys/kernel/debug/tracing/kprobe_events
p:kprobes/kmem_cache_free kmem_cache_free
r:kprobes/kmem_cache_alloc_node kmem_cache_alloc_node

เบ—เบธเบเป‚เบ„เบ‡เบเบฒเบ™เบญเบทเปˆเบ™เป†เปƒเบ™เบ•เบปเบงเบขเปˆเบฒเบ‡ / bpf / เปเบกเปˆเบ™เป‚เบ„เบ‡เบชเป‰เบฒเบ‡เบ—เบตเปˆเบ„เป‰เบฒเบเบ„เบทเบเบฑเบ™. เบžเบงเบเบกเบฑเบ™เบกเบตเบชเบญเบ‡เป„เบŸเบฅเปŒเบชเบฐเป€เปเบต:

  • XXX_kern.c: เป‚เบ„เบ‡เบเบฒเบ™ eBPF.
  • XXX_user.c: เป‚เบ„เบ‡โ€‹เบเบฒเบ™โ€‹เบ•เบปเป‰เบ™โ€‹เบ•เปโ€‹.

เป‚เบ›เบฃเปเบเบฃเบก eBPF เบเบณเบ™เบปเบ”เปเบœเบ™เบ—เบตเปˆ เปเบฅเบฐเปœเป‰เบฒเบ—เบตเปˆเบ—เบตเปˆเบเปˆเบฝเบงเบ‚เป‰เบญเบ‡เบเบฑเบšเบžเบฒเบเบชเปˆเบงเบ™เปƒเบ”เปœเบถเปˆเบ‡. เป€เบกเบทเปˆเบญ kernel เบญเบญเบเป€เบซเบ”เบเบฒเบ™เบ‚เบญเบ‡เบ›เบฐเป€เบžเบ”เบชเบฐเป€เบžเบฒเบฐเปƒเบ”เบซเบ™เบถเปˆเบ‡ (เบ•เบปเบงเบขเปˆเบฒเบ‡, tracepoint), เบซเบ™เป‰เบฒเบ—เบตเปˆเบœเบนเบเบกเบฑเบ”เป„เบ”เป‰เบ–เบทเบเบ›เบฐเบ•เบดเบšเบฑเบ”. เบšเบฑเบ”เบชเบฐเบซเบ™เบญเบ‡เบเบฒเบ™เบชเบทเปˆเบชเบฒเบ™เบฅเบฐเบซเบงเปˆเบฒเบ‡เป‚เบ„เบ‡เบเบฒเบ™ kernel เปเบฅเบฐเป‚เบ„เบ‡เบเบฒเบ™เบžเบทเป‰เบ™เบ—เบตเปˆเบœเบนเป‰เปƒเบŠเป‰.

เบชเบฐเบซเบฅเบธเบš

เบšเบปเบ”เบ„เบงเบฒเบกเบ™เบตเป‰เป„เบ”เป‰เบ›เบถเบเบชเบฒเบซเบฒเบฅเบทเบเปˆเบฝเบงเบเบฑเบš BPF เปเบฅเบฐ eBPF เปƒเบ™เป€เบ‡เบทเปˆเบญเบ™เป„เบ‚เบ—เบปเปˆเบงเป„เบ›. เบ‚เป‰เบญเบเบฎเบนเป‰เบงเปˆเบฒเบกเบตเบ‚เปเป‰เบกเบนเบ™เปเบฅเบฐเบŠเบฑเบšเบžเบฐเบเบฒเบเบญเบ™เบซเบผเบฒเบเบขเปˆเบฒเบ‡เบเปˆเบฝเบงเบเบฑเบš eBPF เปƒเบ™เบกเบทเป‰เบ™เบตเป‰, เบ”เบฑเปˆเบ‡เบ™เบฑเป‰เบ™เบ‚เป‰เบญเบเบˆเบฐเปเบ™เบฐเบ™เปเบฒเบŠเบฑเบšเบžเบฐเบเบฒเบเบญเบ™เป€เบžเบตเปˆเบกเป€เบ•เบตเบกเบˆเปเบฒเบ™เบงเบ™เบซเบ™เป‰เบญเบเบชเปเบฒเบฅเบฑเบšเบเบฒเบ™เบชเบถเบเบชเบฒเบ•เบทเปˆเบกเบญเบตเบ.

เบ‚เป‰เบญเบเบ‚เปเปเบ™เบฐเบ™เปเบฒเปƒเบซเป‰เบญเปˆเบฒเบ™:

เปเบซเบผเปˆเบ‡เบ‚เปเป‰เบกเบนเบ™: www.habr.com

เป€เบžเบตเปˆเบกเบ„เบงเบฒเบกเบ„เบดเบ”เป€เบซเบฑเบ™