-
Notifications
You must be signed in to change notification settings - Fork 4
/
360.txt
294 lines (223 loc) · 16 KB
/
360.txt
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
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
[3] [[Cookie]] 設定時の [DFN[[CODE(HTTP)@en[[[Domain]]]] [[属性]]]]は、その [[Cookie]]
の対象となる[[ドメイン名]]を指定します。 [[HTTP]] の [CODE(HTTP)@en[[[Set-Cookie:]]]] [[応答頭欄]]や
[[JavaScript]] の [CODE(JS)@en[[[document.cookie]]]] の設定時に用いられます。
* 仕様書
[REFS[
- [34] '''[CITE@en[RFC 6265 - HTTP State Management Mechanism]] ([TIME[2012-03-01 09:57:02 +09:00]] 版) <http://tools.ietf.org/html/rfc6265#section-4.1.2.3>'''
- [32] [CITE@en[RFC 6265 - HTTP State Management Mechanism]] ([TIME[2012-03-01 09:57:02 +09:00]] 版) <http://tools.ietf.org/html/rfc6265#page-9>
- [46] [CITE@en[RFC 6265 - HTTP State Management Mechanism]] ([TIME[2014-10-12 15:11:47 +09:00]] 版) <http://tools.ietf.org/html/rfc6265#section-5.2.3>
- [51] [CITE@en[RFC 6265 - HTTP State Management Mechanism]] ([TIME[2014-10-12 15:11:47 +09:00]] 版) <http://tools.ietf.org/html/rfc6265#section-5.3>
- [71] [CITE@en[RFC 7469 - Public Key Pinning Extension for HTTP]] ([TIME[2015-05-05 21:00:37 +09:00]] 版) <https://tools.ietf.org/html/rfc7469#section-4.4>
]REFS]
* 意味
[35] [CODE(HTTP)@en[[[Domain]]]] [[属性]]は、[[クッキー]]が送信されることになる[[ホスト]]を指定します。
[SRC[>>34]]
[EG[
[36] 例えば [CODE(HTTP)@en[[[Domain]]=example.com]] であれば、
[CODE[example.com]], [CODE[www.example.com]], [CODE[www.corp.example.com]]
のような[[ホスト]]に対する [[HTTP]] [[要求]]で[[クッキー]]が送信されます。 [SRC[>>34]]
]EG]
[37] [CODE(HTTP)@en[[[Domain]]]] [[属性]]がなければ、[[起源鯖]]だけに[[クッキー]]を送信するべきであることを表しています。
[SRC[>>34]]
* 構文
[FIG[
[FIGCAPTION[
[33] [[RFC 6265]] における [CODE(ABNF)@en[[[Domain]]]] [[属性]]の構文
]FIGCAPTION]
[PRE(ABNF code)[
domain-av = "Domain=" domain-value
domain-value = <[[subdomain]]>
; defined in [RFC1034], Section 3.5, as
; enhanced by [RFC1123], Section 2.1
]PRE]
]FIG]
** 先頭の [CODE[.]]
[38] [[RFC 6265]] の構文では先頭の [CODE[[[.]]]] は認められていません。また、先頭にあった場合には、
これを無視することになっています [SRC[>>34, >>46]]。
;;
[17] [[RFC 2109]] の定義では、[[ドメイン名]]の先頭は [CODE[[[.]]]] でなければならない
[SRC[>>14]] とされていました。
また、 [[RFC 2965]] の定義では、先頭が [CODE[[[.]]]] でなければ[[利用者エージェント]]が
[CODE[[[.]]]] を補う [SRC[>>16]] とされていました。
;; [45] 現実には先頭に [CODE[[[.]]]] をつけた[[ドメイン名]]も多々用いられています。
** 末尾の [CODE[.]]
[39] [[RFC 6265]] の構文では末尾の [CODE[[[.]]]] ([[末尾の点]]) は認められておらず、あった場合には[[属性]]全体が無視されることになっています
[SRC[>>34]]。
** IDN
[9] [[Cookie]] が定義されたのは [[IDN]] 導入の遥かに前であり、仕様上は [[IDN]]
の扱いが明確になっていません。
* 既定値
[40] [CODE(HTTP)@en[[[Domain]]]] [[属性]]を省略した場合、[[クッキー]]は[[起源鯖]]にのみ送られます。
[SRC[>>34]]
;; [8] [[Netscape]] の仕様では、 [CODE(HTTP)@en[[[Domain]]]] [[属性]]が指定されていない場合は [[Cookie]]
[[応答]]を生成した[[ホスト]]の名前が指定されたとみなす [SRC[>>1]] とされていました。
[[RFC 6265]] ではこれは誤った動作だけど[[利用者エージェント]]によってはそうすると述べられています
[SRC[>>34]]。
[EG[
[41] 例えば [CODE[[[example.com]]]] が [CODE(HTTP)@en[[[Domain]]]] [[属性]]無しの[[クッキー]]を発行した場合、
[CODE[example.com]] への[[要求]]にはこれを送信しますが、 [CODE[www.example.com]]
への[[要求]]ではこれを送信してはなりません。
]EG]
;; [19] [[RFC 2109]] によると[[request-host]]
[SRC[>>20]]、[[RFC 2965]] によると[[実効request-host]] [SRC[>>21]] になります。
その場合最初に [CODE(char)[[[.]]]] が付かないので、[[ドメイン一致]]するのはその[[ドメイン]]自体だけになります
[SRC[>>21]]。
[72] [[HTTPサーバー]]が [CODE(HTTP)@en[[[Host:]]]] の検査などを十分行っておらず、
任意の[[ドメイン名]]でアクセスできる状態になっていると、悪意のある者が自身の保有する [[DNS]]
[[ドメイン名]]に攻撃先の [[IPアドレス]]を割り当て、[[利用者]]をその[[ドメイン名]]に誘導することで、
攻撃先サービスの[[クッキー]]を当該[[ドメイン名]]下で発行させることができるかもしれません。
そのような攻撃を防ぐため、 [CODE(HTTP)@en[[[Domain]]]] [[属性]]は明示的に指定するべきかもしれません。
;; [73] もちろん、[[TLS]] を使ったり、 [CODE(HTTP)@en[[[Host:]]]]
の検査を行ったりすることが (他のセキュリティー上の問題を防ぐためにも) 重要なことには変わりありません。
* 文脈
[70] [[セッションクッキー]]その他[[セキュリティー]]的に重要な[[クッキー]]では、
[CODE(HTTP)@en[[[Domain]]]] [[属性]]を適切な範囲に設定する[['''べきです''']] [SRC[>>71]]。
* 構文解析
[47] [[属性値]]が[[空文字列]]の場合、動作は未定義ですが、
[[属性]]を無視する[['''べきです''']] [SRC[>>46]]。
[48] [[属性値]]の最初の文字が [CODE[[[.]]]] の場合、これは無視しなければ[['''なりません''']] [SRC[>>46]]。
;; [50] [[属性値]]が [CODE[[[.]]]] のみならこれにより[[空文字列]]になりますが、
>>47 は適用されないので無視はされません。
[49] [[小文字]]に変換しなければ[['''なりません''']] [SRC[>>46]]。
* 処理モデル
[59] [[クッキー]]の[[ドメイン]]は、 [CODE(HTTP)@en[[[Domain]]]]
[[属性]]の構文解析結果を使って次のように決定しなければ[['''なりません''']]
[SRC[>>51]]。
[FIG(steps)[
= [60] [CODE(HTTP)@en[[[Domain]]]] [[属性]]があれば、
最後の [CODE(HTTP)@en[[[Domain]]]] [[属性]]の値を[[ドメイン]]とします。
なければ、[[空文字列]]を[[ドメイン]]とします。
= [61] [[利用者エージェント]]が [[public suffix]] を拒むよう設定されており、
[[ドメイン]]が [[public suffix]] なら、
== [62] [[ドメイン]]が[[正準化要求ホスト]]と同じなら、[[ドメイン]]を[[空文字列]]とします。
== [63] そうでないなら、[[クッキー]]全体を無視してここで終わります。
= [64] [[ドメイン]]が[[空文字列]]でないなら、
== [65] [[正準化要求ホスト]]が[[ドメイン]]に[[ドメイン一致]]し''ない''なら、
[[クッキー]]全体を無視してここで終わります。
== [52] そうでないなら、
=== [53] [[クッキー]]のホストのみフラグを設定しません。
=== [54] [[クッキー]]の[[ドメイン]]を[[ドメイン]]に設定します。
= [55] そうでないなら、
== [56] [[クッキー]]のホストのみフラグを設定します。
== [57] [[クッキー]]の[[ドメイン]]を[[正準化要求ホスト]]に設定します。
]FIG]
;; [58] >>61 で [[public suffix]] が設定依存とされているのは謎ですが、
[[セキュリティー]]上、実際には有効にしなければ危険です。
([[Public Suffix List]] が [[IETF]] の標準でないといったような政治的な理由でしょうか。)
[12] [[ポート番号]]は[[クッキー]]の処理には影響しません。
;; [18] [[RFC 2965]] では別に [CODE(HTTP)@en[[[Port]]]] [[属性]]が用意されていますが、
実装されませんでした。
* 第三者クッキー
[6] [CODE(HTTP)@en[[[Domain]]]] で指定された[[ドメイン]]に属する[[ホスト]]だけがその[[ドメイン]]の
[[Cookie]] を設定することができます。 [SRC[>>1]]
[[利用者エージェント]]は [CODE(HTTP)@en[[[Domain]]]] [[属性]]の範囲外の[[起源鯖]]からの[[クッキー]]を拒否します
[SRC[>>34]]。
[EG[
[42] 例えば、 [CODE[foo.example.com]] が[[起源鯖]]の場合、 [CODE[[[Domain]]=example.com]] や
[CODE[[[Domain]]=foo.example.com]] は認められますが、 [CODE[[[Domain]]=bar.example.com]] や
[CODE[[[Domain]]=baz.foo.example.com]] の[[クッキー]]は無視されます。 [SRC[>>34]]
]EG]
;; [22] [[RFC 2109]] では、[CODE(HTTP)@en[[[Domain]]]] が途中に [CODE[[[.]]]]
を含まない場合や [CODE[[[.]]]] から始まらない場合にはその [[Cookie]]
を[RUBYB[[[蓄積]]]@en[store]]しては[['''ならない''']]とされていました
[SRC[>>23]]。
;; [25] [[RFC 2965]] では [CODE(HTTP)@en[[[Domain]]]] が途中に [CODE[[[.]]]]
を含まない場合でその値が [CODE(HTTP)@en[[[.local]]]] ではない時にその [[Cookie]]
を[RUBYB[[[蓄積]]]@en[store]]しては[['''ならない''']]とされていました [SRC[>>24]]。
;; [26] 更に、 [[RFC 2109]] では [CODE(HTTP)@en[[[Domain]]]] が [[request-host]]
と[[ドメイン一致]]しない場合、 [[RFC 2965]] では [CODE(HTTP)@en[[[Domain]]]] が
[[request-host]] の[[実効ホスト名]]と[[ドメイン一致]]しない場合に、その [[Cookie]]
を[RUBYB[[[蓄積]]]@en[store]]しては[['''ならない''']]とされていました [SRC[>>23、>>24]]。
;; [27] 加えて、[[RFC 2109]] と [[RFC 2965]] では、 [[request-host]] が [[IPアドレス]]では''なく''、
[CODE[[[.]]]] を含まない文字列 [VAR[H]] と [CODE(HTTP)@en[[[Domain]]]] の値 [VAR[D]]
を使って [CODE[[VAR[H]][VAR[D]]]] と表せる場合に、その [[Cookie]]
を[RUBYB[[[蓄積]]]@en[store]]しては[['''ならない''']]とされていました [SRC[>>23、>>24]]。
** TLD
[7] [CODE(HTTP)@en[[[Domain]]]] で設定する[[ドメイン名]]には少なくても2つか3つの [CODE(char)[[[.]]]]
が含まれていなければなりません。基本的には3つ以上で、2つでもよいのは
[CODE@en[[[.com]]]], [CODE@en[[[.edu]]]], [CODE@en[[[.net]]]], [CODE@en[[[.org]]]],
[CODE@en[[[.gov]]]], [CODE@en[[[.mil]]]], [CODE@en[[[.int]]]] の7つの [[gTLD]] だけです。
[SRC[>>1]]
[10] [[FQDN]] であることを明示する際に [CODE[foo.example.]] のように最後に [CODE[[[.]]]]
を付けることがありますが、これと >>4 の処理モデルや >>7 の制約との関係は仕様上明確にされていません。
* 歴史
** Netscape Cookie
[4] [[妥当]]な [[Cookie]] を探す際に、[[Cookie]] の [CODE(HTTP)@en[[[Domain]]]]
[[属性]]と、 [[fetch]] しようとしている [[URL]] の[[ドメイン名]]の部分とを比較します。
ここで[[末尾一致]]していれば、更に [CODE(HTTP)@en[[[Path]]]] の比較へと進みます。
[SRC[>>1]] 一致していなければその [[Cookie]] は妥当ではなく、[[HTTP]]
[[要求]]の [CODE(HTTP)@en[[[Cookie:]]]] [[頭欄]]には含まれません。
[5] ここで[DFN[[RUBYB[[[末尾一致]]]@en[tail matching]]]]とは、
[[fetch]] しようとしている[[ホスト]]の[[完全修飾ドメイン名]] ([[FQDN]])
の末尾に [CODE(HTTP)@en[[[Domain]]]] [[属性]]の値が一致することをいいます。 [SRC[>>1]]
;; 例えば、 [CODE(HTTP)@en[[[Domain]]=acme.com]] は
[CODE@en[anvil.acme.com]] や [CODE@en[shipping.crate.acme.com]] と一致します。 [SRC[>>1]]
[11] 仕様上明記されていませんが、[[ドメイン名]]は[[大文字・小文字を区別しない]]ので、
この[[一致]]の際も差異は無視されるものと思われます。
[REFS[
-[1] [[Netscape Cookie]]: [CITE[Client Side State - HTTP Cookies]]
<http://web.archive.org/web/19961125090609/http://www2.netscape.com/newsref/std/cookie_spec.html>
]REFS]
** RFC 2109 の [CODE(HTTP)@en[Set-Cookie]] の定義
[31] [[RFC 2109]], [[RFC 2965]] では、[[利用者エージェント]]には異なる[[ドメイン]]の[[ホスト]]での[[セッション]]情報の共有を可能な限り阻止する[['''べき''']]
[SRC[>>30, >>29]] とのよくわからない要件が課されていました。
*** 仕様書
- [13] [DEL[[[RFC 2109]]]] ([[廃止]]済み)
-- [14] '''[CSECTION@en[4.2.2 Set-Cookie2 Syntax]]'''
-- [20] [CSECTION@en[4.3.1 Interpreting Set-Cookie2]]
-- [23] [CSECTION@en[4.3.2 Rejecting Cookies]]
-- [30] [CSECTION@en[8.3 Unexpected Cookie Sharing]]
** RFC 2965 の [CODE(HTTP)@en[Set-Cookie2] の定義
*** 仕様書
- [15] [[RFC 2965]]
-- [16] '''[CSECTION@en[3.2.2 Set-Cookie2 Syntax]]'''
-- [21] [CSECTION@en[3.3.1 Interpreting Set-Cookie2]]
-- [24] [CSECTION@en[3.3.2 Rejecting Cookies]]
-- [29] [CSECTION@en[7.3 Unexpected Cookie Sharing]]
* 関連
[28] [[RFC 2109]]、[[RFC 2965]] では[[利用者エージェント]]が返送する時に
[CODE(HTTP)@en[[[Cookie:]]]] に [CODE(HTTP)@en[[[$Domain]]]] [[属性]]として含めることになっていました。
* メモ
[2]
[CITE[document.cookie の覚え書き - Ci.nsIZIGOROu - Mozilla 拡張機能勉強会]] ([TIME[2009-02-01 18:27:09 +09:00]] 版) <http://moz-addon.g.hatena.ne.jp/ZIGOROu/20081001/1222845305>
>現在 test.example.com で実行してるとして、
[PRE(JS example code)[
document.cookie = "Z=1";
alert(document.cookie);
document.cookie = "Z=2;domain=example.com";
alert(document.cookie);
document.cookie = "Z=3;domain=test.example.com";
alert(document.cookie);
]PRE]
は IE6, 7 の場合、最終的に "Z=3;Z=2" となるのだが、Fx3, Safari だと、"Z=1;Z=2;Z=3" となる。
>domain が省略された場合、test.example.com 相当で設定したとされるべきだと思うんだけど。
>
と思ったら、domain パラメータの挙動について見ている所が netscape の決めた奴と言う古い奴見てた事が判明。
>>
:Domain=domain:Optional. The Domain attribute specifies the domain for which the cookie is valid. An explicitly specified domain must always start with a dot.
>> RFC 2109 - 4.2.2 Set-Cookie Syntax
>つまり、指定するなら "." から開始しないとだめぽって事。
>省略した場合の挙動は、
>> Domain Defaults to the request-host. (Note that there is no dot at the beginning of request-host.)
>>RFC 2109 - 4.3.1 Interpreting Set-Cookie
>"." を先頭につけないのが正しいと。
>[DEL[まぁこれらの結果分かるのは、domain 指定がある場合、別々の物として key-value のペアが管理されますよと考えられると。]]
>[INS[この挙動、IEとそれ以外でだいぶ異なるみたいなので注意]]
[43] [CITE[252342 – fix cookie domain checks to not allow .co.uk]]
( ([TIME[2012-03-25 11:29:16 +09:00]] 版))
<https://bugzilla.mozilla.org/show_bug.cgi?id=252342>
[44] [CITE@en[draft-pettersen-dns-cookie-validate-05 - Enhanced validation of domains for HTTP State Management Cookies using DNS]]
( ([TIME[2012-03-19 18:25:41 +09:00]] 版))
<http://tools.ietf.org/html/draft-pettersen-dns-cookie-validate-05>
[66] [CITE@en[draft-pettersen-dns-cookie-validate-05 - Enhanced validation of domains for HTTP State Management Cookies using DNS]]
( ([TIME[2014-10-16 13:01:02 +09:00]] 版))
<http://tools.ietf.org/html/draft-pettersen-dns-cookie-validate-05>
[67] [CITE@en[draft-pettersen-dns-cookie-validate-05 - Enhanced validation of domains for HTTP State Management Cookies using DNS]]
( ([TIME[2014-10-16 13:01:02 +09:00]] 版))
<http://tools.ietf.org/html/draft-pettersen-dns-cookie-validate-05>
[68] [CITE@en[RFC 2964 - Use of HTTP State Management]]
( ([TIME[2014-09-07 21:45:30 +09:00]] 版))
<http://tools.ietf.org/html/rfc2964#section-3.2>
[69] [CITE[Issue 56211 - chromium - chrome.cookies fails for localhost domains - An open-source project to help move the web forward. - Google Project Hosting]]
([TIME[2015-04-20 21:13:38 +09:00]] 版)
<https://code.google.com/p/chromium/issues/detail?id=56211>