-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathdocker-seccomp-bpf.html
242 lines (214 loc) · 24.1 KB
/
docker-seccomp-bpf.html
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" /><meta name="generator" content="Docutils 0.17.1: http://docutils.sourceforge.net/" />
<title>容器——seccomp-bpf — Feng's blog 1.0 documentation</title>
<link rel="stylesheet" type="text/css" href="_static/pygments.css" />
<link rel="stylesheet" type="text/css" href="_static/alabaster.css" />
<script data-url_root="./" id="documentation_options" src="_static/documentation_options.js"></script>
<script src="_static/jquery.js"></script>
<script src="_static/underscore.js"></script>
<script src="_static/doctools.js"></script>
<script src="_static/custom.js"></script>
<link rel="index" title="Index" href="genindex.html" />
<link rel="search" title="Search" href="search.html" />
<link rel="next" title="容器——Network Namespace 和桥接网络模式" href="docker-network.html" />
<link rel="prev" title="Go 语言实现——数据结构" href="golang-internals-variable.html" />
<link rel="stylesheet" href="_static/custom.css" type="text/css" />
<meta name="viewport" content="width=device-width, initial-scale=0.9, maximum-scale=0.9" />
</head><body>
<div class="document">
<div class="documentwrapper">
<div class="bodywrapper">
<div class="body" role="main">
<section id="rong-qi-seccomp-bpf">
<h1>容器——seccomp-bpf<a class="headerlink" href="#rong-qi-seccomp-bpf" title="Permalink to this headline">¶</a></h1>
<section id="bpf">
<h2>BPF<a class="headerlink" href="#bpf" title="Permalink to this headline">¶</a></h2>
<p>BPF 本来指的是 Berkeley Packet Filter,如其字面义,是用在网络包的过滤这个场景上的,最早应用在 tcpdump 上,tcpdump 会将过滤表达式转换成 BPF 字节码然后调用内核的接口让其执行这段字节码程序来过滤网络包。</p>
<div class="highlight-console notranslate"><div class="highlight"><pre><span></span><span class="gp"># </span>tcpdump -p -ni eth0 -d <span class="s2">"ip and src 1.1.1.1"</span>
<span class="gp gp-VirtualEnv">(000)</span> <span class="go">ldh [12]</span>
<span class="gp gp-VirtualEnv">(001)</span> <span class="go">jeq #0x800 jt 2 jf 5</span>
<span class="gp gp-VirtualEnv">(002)</span> <span class="go">ld [26]</span>
<span class="gp gp-VirtualEnv">(003)</span> <span class="go">jeq #0x1010101 jt 4 jf 5</span>
<span class="gp gp-VirtualEnv">(004)</span> <span class="go">ret #262144</span>
<span class="gp gp-VirtualEnv">(005)</span> <span class="go">ret #0</span>
</pre></div>
</div>
<p>这段程序的意思翻译过来如下:</p>
<ul class="simple">
<li><p>(000)加载 ethernet packet 第 12 个字节开始的 2 个字节(ethernet frame 的类型字段)。</p></li>
<li><p>(001)检查加载的值是否为 0x800 (是否为 IP 包),是的话跳到 002 执行,否则 005。</p></li>
<li><p>(002)加载 ethernet packat 第 26 个字节开始的 4 个字节(IP 包的原地址字段)。</p></li>
<li><p>(003)检查加载的值是否为 0x1010101(IP 是否为 1.1.1.1),是的话跳到 004 执行,否则 005。</p></li>
<li><p>(004)返回包匹配。</p></li>
<li><p>(005)返回包不匹配。</p></li>
</ul>
<p>上面打印出得是翻译过的给人看字节码,我们也可以打印出给机器读的字节码:</p>
<div class="highlight-console notranslate"><div class="highlight"><pre><span></span><span class="gp"># </span>tcpdump -p -ni eth0 -ddd <span class="s2">"ip and src 1.1.1.1"</span>
<span class="go">6</span>
<span class="go">40 0 0 12</span>
<span class="go">21 0 3 2048</span>
<span class="go">32 0 0 26</span>
<span class="go">21 0 1 16843009</span>
<span class="go">6 0 0 262144</span>
<span class="go">6 0 0 0</span>
</pre></div>
</div>
<p>tcpdump 然后使用类似下面程序的方式将 bpf 程序提交给内核去执行,后面内核只会将匹配 bpf 程序的包发送给 tcpdump。</p>
<div class="highlight-c notranslate"><div class="highlight"><pre><span></span><span class="cp">#include</span><span class="w"> </span><span class="cpf"><sys/socket.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><sys/types.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><arpa/inet.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><linux/if_ether.h></span><span class="cp"></span>
<span class="cm">/* BPF 字节码结构体</span>
<span class="cm"> struct sock_filter {</span>
<span class="cm"> __u16 code; 字节码</span>
<span class="cm"> __u8 jt; 成功跳转</span>
<span class="cm"> __u8 jf; 失败跳转</span>
<span class="cm"> __u32 k; 根据字节码不同意义不一样</span>
<span class="cm"> };</span>
<span class="cm">*/</span><span class="w"></span>
<span class="k">struct</span> <span class="nc">sock_filter</span><span class="w"> </span><span class="n">code</span><span class="p">[]</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="p">{</span><span class="mi">40</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">12</span><span class="p">},</span><span class="w"></span>
<span class="w"> </span><span class="p">{</span><span class="mi">21</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">3</span><span class="p">,</span><span class="w"> </span><span class="mi">2048</span><span class="p">},</span><span class="w"></span>
<span class="w"> </span><span class="p">{</span><span class="mi">32</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">26</span><span class="p">},</span><span class="w"></span>
<span class="w"> </span><span class="p">{</span><span class="mi">21</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">1</span><span class="p">,</span><span class="w"> </span><span class="mi">16843009</span><span class="p">},</span><span class="w"></span>
<span class="w"> </span><span class="p">{</span><span class="mi">6</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">262144</span><span class="p">},</span><span class="w"></span>
<span class="w"> </span><span class="p">{</span><span class="mi">6</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">},</span><span class="w"></span>
<span class="p">};</span><span class="w"></span>
<span class="cm">/* BPF 程序元信息</span>
<span class="cm"> struct sock_fprog {</span>
<span class="cm"> unsigned short len;</span>
<span class="cm"> struct sock_filter __user *filter;</span>
<span class="cm"> };</span>
<span class="cm">*/</span><span class="w"></span>
<span class="k">struct</span> <span class="nc">sock_fprog</span><span class="w"> </span><span class="n">bpf</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="p">.</span><span class="n">len</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">ARRAY_SIZE</span><span class="p">(</span><span class="n">code</span><span class="p">),</span><span class="w"></span>
<span class="w"> </span><span class="p">.</span><span class="n">filter</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">code</span><span class="p">,</span><span class="w"></span>
<span class="p">};</span><span class="w"></span>
<span class="n">sock</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">socket</span><span class="p">(</span><span class="n">PF_PACKET</span><span class="p">,</span><span class="w"> </span><span class="n">SOCK_RAW</span><span class="p">,</span><span class="w"> </span><span class="n">htons</span><span class="p">(</span><span class="n">ETH_P_ALL</span><span class="p">));</span><span class="w"></span>
<span class="n">ret</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">setsockopt</span><span class="p">(</span><span class="n">sock</span><span class="p">,</span><span class="w"> </span><span class="n">SOL_SOCKET</span><span class="p">,</span><span class="w"> </span><span class="n">SO_ATTACH_FILTER</span><span class="p">,</span><span class="w"> </span><span class="o">&</span><span class="n">bpf</span><span class="p">,</span><span class="w"> </span><span class="k">sizeof</span><span class="p">(</span><span class="n">bpf</span><span class="p">));</span><span class="w"></span>
</pre></div>
</div>
</section>
<section id="seccomp-bpf">
<h2>seccomp-bpf<a class="headerlink" href="#seccomp-bpf" title="Permalink to this headline">¶</a></h2>
<p>目前 bpf 在 Linux 上已经应用在方方面面各种场景下, seccomp-bpf 就是 bpf 在 seccomp 上的应用。容器使用 seccomp-bpf + capability 来限制一个容器进程可以调用的系统调用。</p>
<div class="highlight-c notranslate"><div class="highlight"><pre><span></span><span class="cp">#include</span><span class="w"> </span><span class="cpf"><errno.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><linux/audit.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><linux/bpf.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><linux/filter.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><linux/seccomp.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><linux/unistd.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><stddef.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><stdio.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><sys/prctl.h></span><span class="cp"></span>
<span class="cp">#include</span><span class="w"> </span><span class="cpf"><unistd.h></span><span class="cp"></span>
<span class="kt">int</span><span class="w"> </span><span class="nf">main</span><span class="p">()</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="n">printf</span><span class="p">(</span><span class="s">"hey there!</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span><span class="w"></span>
<span class="w"> </span><span class="k">struct</span> <span class="nc">sock_filter</span><span class="w"> </span><span class="n">filter</span><span class="p">[]</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="n">BPF_STMT</span><span class="p">(</span><span class="n">BPF_LD</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_W</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_ABS</span><span class="p">,</span><span class="w"> </span><span class="p">(</span><span class="n">offsetof</span><span class="p">(</span><span class="k">struct</span> <span class="nc">seccomp_data</span><span class="p">,</span><span class="w"> </span><span class="n">arch</span><span class="p">))),</span><span class="w"></span>
<span class="w"> </span><span class="n">BPF_JUMP</span><span class="p">(</span><span class="n">BPF_JMP</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_JEQ</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_K</span><span class="p">,</span><span class="w"> </span><span class="n">AUDIT_ARCH_X86_64</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">3</span><span class="p">),</span><span class="w"></span>
<span class="w"> </span><span class="n">BPF_STMT</span><span class="p">(</span><span class="n">BPF_LD</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_W</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_ABS</span><span class="p">,</span><span class="w"> </span><span class="p">(</span><span class="n">offsetof</span><span class="p">(</span><span class="k">struct</span> <span class="nc">seccomp_data</span><span class="p">,</span><span class="w"> </span><span class="n">nr</span><span class="p">))),</span><span class="w"></span>
<span class="w"> </span><span class="n">BPF_JUMP</span><span class="p">(</span><span class="n">BPF_JMP</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_JEQ</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_K</span><span class="p">,</span><span class="w"> </span><span class="n">__NR_write</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">1</span><span class="p">),</span><span class="w"></span>
<span class="w"> </span><span class="n">BPF_STMT</span><span class="p">(</span><span class="n">BPF_RET</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_K</span><span class="p">,</span><span class="w"> </span><span class="n">SECCOMP_RET_ERRNO</span><span class="w"> </span><span class="o">|</span><span class="w"> </span><span class="p">(</span><span class="n">EPERM</span><span class="w"> </span><span class="o">&</span><span class="w"> </span><span class="n">SECCOMP_RET_DATA</span><span class="p">)),</span><span class="w"></span>
<span class="w"> </span><span class="n">BPF_STMT</span><span class="p">(</span><span class="n">BPF_RET</span><span class="w"> </span><span class="o">+</span><span class="w"> </span><span class="n">BPF_K</span><span class="p">,</span><span class="w"> </span><span class="n">SECCOMP_RET_ALLOW</span><span class="p">),</span><span class="w"></span>
<span class="w"> </span><span class="p">};</span><span class="w"></span>
<span class="w"> </span><span class="k">struct</span> <span class="nc">sock_fprog</span><span class="w"> </span><span class="n">prog</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="p">.</span><span class="n">len</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="p">(</span><span class="kt">unsigned</span><span class="w"> </span><span class="kt">short</span><span class="p">)(</span><span class="k">sizeof</span><span class="p">(</span><span class="n">filter</span><span class="p">)</span><span class="w"> </span><span class="o">/</span><span class="w"> </span><span class="k">sizeof</span><span class="p">(</span><span class="n">filter</span><span class="p">[</span><span class="mi">0</span><span class="p">])),</span><span class="w"></span>
<span class="w"> </span><span class="p">.</span><span class="n">filter</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">filter</span><span class="p">,</span><span class="w"></span>
<span class="w"> </span><span class="p">};</span><span class="w"></span>
<span class="w"> </span><span class="c1">// 让 seccomp-bpf 程序生效后即使后面程序执行了 execve 也能继续生效</span>
<span class="w"> </span><span class="c1">// https://www.kernel.org/doc/Documentation/prctl/no_new_privs.txt</span>
<span class="w"> </span><span class="k">if</span><span class="w"> </span><span class="p">(</span><span class="n">prctl</span><span class="p">(</span><span class="n">PR_SET_NO_NEW_PRIVS</span><span class="p">,</span><span class="w"> </span><span class="mi">1</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">,</span><span class="w"> </span><span class="mi">0</span><span class="p">))</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="n">perror</span><span class="p">(</span><span class="s">"prctl(NO_NEW_PRIVS)"</span><span class="p">);</span><span class="w"></span>
<span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="mi">1</span><span class="p">;</span><span class="w"></span>
<span class="w"> </span><span class="p">}</span><span class="w"></span>
<span class="w"> </span><span class="c1">// 设置 seccomp-bpf</span>
<span class="w"> </span><span class="k">if</span><span class="w"> </span><span class="p">(</span><span class="n">prctl</span><span class="p">(</span><span class="n">PR_SET_SECCOMP</span><span class="p">,</span><span class="w"> </span><span class="mi">2</span><span class="p">,</span><span class="w"> </span><span class="o">&</span><span class="n">prog</span><span class="p">))</span><span class="w"> </span><span class="p">{</span><span class="w"></span>
<span class="w"> </span><span class="n">perror</span><span class="p">(</span><span class="s">"prctl(PR_SET_SECCOMP)"</span><span class="p">);</span><span class="w"></span>
<span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="mi">1</span><span class="p">;</span><span class="w"></span>
<span class="w"> </span><span class="p">}</span><span class="w"></span>
<span class="w"> </span><span class="n">printf</span><span class="p">(</span><span class="s">"it will not definitely print this here</span><span class="se">\n</span><span class="s">"</span><span class="p">);</span><span class="w"></span>
<span class="w"> </span><span class="k">return</span><span class="w"> </span><span class="mi">0</span><span class="p">;</span><span class="w"></span>
<span class="p">}</span><span class="w"></span>
</pre></div>
</div>
<p>上面的 bpf 程序使用各种宏来写的,翻译成 human readable 的格式就是:</p>
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="p">(</span><span class="mi">001</span><span class="p">)</span> <span class="n">ldh</span> <span class="n">seccomp_data</span><span class="o">.</span><span class="n">arch</span>
<span class="p">(</span><span class="mi">002</span><span class="p">)</span> <span class="n">jeq</span> <span class="n">AUDIT_ARCH_X86_64</span> <span class="n">jt</span> <span class="mi">3</span> <span class="n">jf</span> <span class="mi">6</span>
<span class="p">(</span><span class="mi">003</span><span class="p">)</span> <span class="n">ldh</span> <span class="n">seccomp_data</span><span class="o">.</span><span class="n">nr</span>
<span class="p">(</span><span class="mi">004</span><span class="p">)</span> <span class="n">jeq</span> <span class="n">__NR_write</span> <span class="n">jt</span> <span class="mi">5</span> <span class="n">jf</span> <span class="mi">6</span>
<span class="p">(</span><span class="mi">005</span><span class="p">)</span> <span class="n">ret</span> <span class="n">SECCOMP_RET_ERRNO</span> <span class="o">|</span> <span class="p">(</span><span class="n">EPERM</span> <span class="o">&</span> <span class="n">SECCOMP_RET_DATA</span><span class="p">)</span>
<span class="p">(</span><span class="mi">006</span><span class="p">)</span> <span class="n">ret</span> <span class="n">SECCOMP_RET_ALLOW</span>
</pre></div>
</div>
<p>运行程序只会打印出第一个 <code class="docutils literal notranslate"><span class="pre">hey</span> <span class="pre">there!</span></code> ,最后 printf 的 <code class="docutils literal notranslate"><span class="pre">it</span> <span class="pre">will</span> <span class="pre">not</span> <span class="pre">...</span></code> 打印不出来,因为 printf 最后调用系统调用 write 的时候会返回错误 EPERM。strace 可以看到结果如下:</p>
<div class="highlight-default notranslate"><div class="highlight"><pre><span></span><span class="n">write</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="s2">"it will not definitely print thi"</span><span class="o">...</span><span class="p">,</span> <span class="mi">39</span><span class="p">)</span> <span class="o">=</span> <span class="o">-</span><span class="mi">1</span> <span class="n">EPERM</span> <span class="p">(</span><span class="n">Operation</span> <span class="ow">not</span> <span class="n">permitted</span><span class="p">)</span>
</pre></div>
</div>
<p>参考:</p>
<ul class="simple">
<li><p><a class="reference external" href="https://blog.cloudflare.com/bpf-the-forgotten-bytecode/">https://blog.cloudflare.com/bpf-the-forgotten-bytecode/</a></p></li>
<li><p><a class="reference external" href="https://www.kernel.org/doc/Documentation/networking/filter.txt">https://www.kernel.org/doc/Documentation/networking/filter.txt</a></p></li>
<li><p><a class="reference external" href="https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/include/uapi/linux/filter.h?h=v3.16.84">https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/tree/include/uapi/linux/filter.h?h=v3.16.84</a></p></li>
</ul>
</section>
</section>
</div>
</div>
</div>
<div class="sphinxsidebar" role="navigation" aria-label="main navigation">
<div class="sphinxsidebarwrapper">
<h3><a href="index.html">Table of Contents</a></h3>
<ul>
<li><a class="reference internal" href="#">容器——seccomp-bpf</a><ul>
<li><a class="reference internal" href="#bpf">BPF</a></li>
<li><a class="reference internal" href="#seccomp-bpf">seccomp-bpf</a></li>
</ul>
</li>
</ul>
<div role="note" aria-label="source link">
<h3>This Page</h3>
<ul class="this-page-menu">
<li><a href="_sources/docker-seccomp-bpf.rst.txt"
rel="nofollow">Show Source</a></li>
</ul>
</div>
<div id="searchbox" style="display: none" role="search">
<h3 id="searchlabel">Quick search</h3>
<div class="searchformwrapper">
<form class="search" action="https://cn.bing.com/search" method="get">
<input type="text" name="q" aria-labelledby="searchlabel" autocomplete="off" autocorrect="off" autocapitalize="off" spellcheck="false"/>
<input type="submit" value="Go" />
</form>
</div>
</div>
<script>
$('#searchbox').show(0);
document.getElementsByClassName('search')[0].addEventListener('submit', function(event) {
event.preventDefault();
var form = event.target;
var input = form.querySelector('input[name="q"]');
var value = input.value;
var q = 'ensearch=1&q=site%3Achanfung032.github.io++' + value;
var url = form.action + '?' + q;
window.location.href = url;
});
</script>
</div>
</div>
<div class="clearer"></div>
</div>
<div class="footer">
©2017, chanfung032.
|
Powered by <a href="http://sphinx-doc.org/">Sphinx 4.1.2</a>
& <a href="https://github.com/bitprophet/alabaster">Alabaster 0.7.12</a>
|
<a href="_sources/docker-seccomp-bpf.rst.txt"
rel="nofollow">Page source</a>
</div>
</body>
</html>