fsphinx.addnodesdocument)}( rawsourcechildren]( translations LanguagesNode)}(hhh](h pending_xref)}(hhh]docutils.nodesTextEnglish}parenthsba attributes}(ids]classes]names]dupnames]backrefs] refdomainstdreftypedoc reftarget/security/siphashmodnameN classnameN refexplicitutagnamehhh ubh)}(hhh]hChinese (Traditional)}hh2sbah}(h]h ]h"]h$]h&] refdomainh)reftypeh+ reftarget$/translations/zh_TW/security/siphashmodnameN classnameN refexplicituh1hhh ubh)}(hhh]hItalian}hhFsbah}(h]h ]h"]h$]h&] refdomainh)reftypeh+ reftarget$/translations/it_IT/security/siphashmodnameN classnameN refexplicituh1hhh ubh)}(hhh]hJapanese}hhZsbah}(h]h ]h"]h$]h&] refdomainh)reftypeh+ reftarget$/translations/ja_JP/security/siphashmodnameN classnameN refexplicituh1hhh ubh)}(hhh]hKorean}hhnsbah}(h]h ]h"]h$]h&] refdomainh)reftypeh+ reftarget$/translations/ko_KR/security/siphashmodnameN classnameN refexplicituh1hhh ubh)}(hhh]hSpanish}hhsbah}(h]h ]h"]h$]h&] refdomainh)reftypeh+ reftarget$/translations/sp_SP/security/siphashmodnameN classnameN refexplicituh1hhh ubeh}(h]h ]h"]h$]h&]current_languageChinese (Simplified)uh1h hh _documenthsourceNlineNubhcomment)}(h SPDX-License-Identifier: GPL-2.0h]h SPDX-License-Identifier: GPL-2.0}hhsbah}(h]h ]h"]h$]h&] xml:spacepreserveuh1hhhhhhQ/var/lib/git/docbuild/linux/Documentation/translations/zh_CN/security/siphash.rsthKubhnote)}(hX{此文件的目的是为让中文读者更容易阅读和理解,而不是作为一个分支。 因此, 如果您对此文件有任何意见或更新,请先尝试更新原始英文文件。 如果您发现本文档与原始文件有任何不同或者有翻译问题,请发建议或者补丁给 该文件的译者,或者请求中文文档维护者和审阅者的帮助。h]h paragraph)}(hX{此文件的目的是为让中文读者更容易阅读和理解,而不是作为一个分支。 因此, 如果您对此文件有任何意见或更新,请先尝试更新原始英文文件。 如果您发现本文档与原始文件有任何不同或者有翻译问题,请发建议或者补丁给 该文件的译者,或者请求中文文档维护者和审阅者的帮助。h]hX{此文件的目的是为让中文读者更容易阅读和理解,而不是作为一个分支。 因此, 如果您对此文件有任何意见或更新,请先尝试更新原始英文文件。 如果您发现本文档与原始文件有任何不同或者有翻译问题,请发建议或者补丁给 该文件的译者,或者请求中文文档维护者和审阅者的帮助。}(hhhhhNhNubah}(h]h ]h"]h$]h&]uh1hh5Documentation/translations/zh_CN/disclaimer-zh_CN.rsthKhhubah}(h]h ]h"]h$]h&]uh1hhhhhhhhNubh field_list)}(hhh](hfield)}(hhh](h field_name)}(hOriginalh]hOriginal}(hhhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhhhKubh field_body)}(h#Documentation/security/siphash.rst h]h)}(h"Documentation/security/siphash.rsth]h"Documentation/security/siphash.rst}(hhhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKhhubah}(h]h ]h"]h$]h&]uh1hhhubeh}(h]h ]h"]h$]h&]uh1hhhhKhhhhubh)}(hhh](h)}(h翻译h]h翻译}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhj hhhKubh)}(h-张巍 zhangwei h]h)}(h,张巍 zhangwei h](h张巍 zhangwei <}(hj hhhNhNubh reference)}(hzhangwei@cqsoftware.com.cnh]hzhangwei@cqsoftware.com.cn}(hj*hhhNhNubah}(h]h ]h"]h$]h&]refuri!mailto:zhangwei@cqsoftware.com.cnuh1j(hj ubh>}(hj hhhNhNubeh}(h]h ]h"]h$]h&]uh1hhhhKhjubah}(h]h ]h"]h$]h&]uh1hhj ubeh}(h]h ]h"]h$]h&]uh1hhhhKhhhhubeh}(h]h ]h"]h$]h&]uh1hhhhhhhhKubhsection)}(hhh](htitle)}(h1SipHash - 一种短输入伪随机函数(PRF)h]h1SipHash - 一种短输入伪随机函数(PRF)}(hj]hhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjXhhhhhK ubh)}(h.:作者: Jason A.Donenfeld h](h:作者: Jason A.Donenfeld <}(hjkhhhNhNubj))}(hjason@zx2c4.comh]hjason@zx2c4.com}(hjshhhNhNubah}(h]h ]h"]h$]h&]refurimailto:jason@zx2c4.comuh1j(hjkubh>}(hjkhhhNhNubeh}(h]h ]h"]h$]h&]uh1hhhhK hjXhhubh)}(hXLSipHash是一种加密安全的伪随机函数,即一种用于生成伪随机密钥的哈 希函数,因为其在处理短输入时表现出色,因此得名。其由密码学家 Daniel J. Bernstein和Jean-Philippe Aumasson设计。目的主要是替 代其他哈希函数,例如:jhash,md5_transform,sha1_transform等。h]hXLSipHash是一种加密安全的伪随机函数,即一种用于生成伪随机密钥的哈 希函数,因为其在处理短输入时表现出色,因此得名。其由密码学家 Daniel J. Bernstein和Jean-Philippe Aumasson设计。目的主要是替 代其他哈希函数,例如:jhash,md5_transform,sha1_transform等。}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKhjXhhubh)}(hX"SipHash采用一个完全由随机数生成的密钥,以及一个输入缓冲区或者 多个输入整数,它输出一个与随机数难以区分的整数,你可以将它作 为安全序列、安全cookies的一部分,或者对其进行掩码处理,以便在 哈希表中使用。h]hX"SipHash采用一个完全由随机数生成的密钥,以及一个输入缓冲区或者 多个输入整数,它输出一个与随机数难以区分的整数,你可以将它作 为安全序列、安全cookies的一部分,或者对其进行掩码处理,以便在 哈希表中使用。}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKhjXhhubjW)}(hhh](j\)}(h 生成密钥h]h 生成密钥}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjhhhhhKubh)}(hm密钥应来源于加密安全的随机数生成,要么使用get random bytes 要么使用get random once::h]hl密钥应来源于加密安全的随机数生成,要么使用get random bytes 要么使用get random once:}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKhjhhubh literal_block)}(h7siphash_key_t key; get_random_bytes(&key, sizeof(key));h]h7siphash_key_t key; get_random_bytes(&key, sizeof(key));}hjsbah}(h]h ]h"]h$]h&]hhuh1jhhhKhjhhubh)}(hH如果你的密钥来源不是这两个,那么你的做法是错的。h]hH如果你的密钥来源不是这两个,那么你的做法是错的。}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhK"hjhhubeh}(h]id1ah ]h"] 生成密钥ah$]h&]uh1jVhjXhhhhhKubjW)}(hhh](j\)}(h 使用函数h]h 使用函数}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjhhhhhK%ubh)}(hY这个函数有两个变种,一种是接受整数列表,另一种是接受缓冲区::h]hX这个函数有两个变种,一种是接受整数列表,另一种是接受缓冲区:}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhK'hjhhubj)}(hDu64 siphash(const void *data, size_t len, const siphash_key_t *key);h]hDu64 siphash(const void *data, size_t len, const siphash_key_t *key);}hj sbah}(h]h ]h"]h$]h&]hhuh1jhhhK)hjhhubh)}(h和::h]h和:}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhK+hjhhubj)}(hXu64 siphash_1u64(u64, const siphash_key_t *key); u64 siphash_2u64(u64, u64, const siphash_key_t *key); u64 siphash_3u64(u64, u64, u64, const siphash_key_t *key); u64 siphash_4u64(u64, u64, u64, u64, const siphash_key_t *key); u64 siphash_1u32(u32, const siphash_key_t *key); u64 siphash_2u32(u32, u32, const siphash_key_t *key); u64 siphash_3u32(u32, u32, u32, const siphash_key_t *key); u64 siphash_4u32(u32, u32, u32, u32, const siphash_key_t *key);h]hXu64 siphash_1u64(u64, const siphash_key_t *key); u64 siphash_2u64(u64, u64, const siphash_key_t *key); u64 siphash_3u64(u64, u64, u64, const siphash_key_t *key); u64 siphash_4u64(u64, u64, u64, u64, const siphash_key_t *key); u64 siphash_1u32(u32, const siphash_key_t *key); u64 siphash_2u32(u32, u32, const siphash_key_t *key); u64 siphash_3u32(u32, u32, u32, const siphash_key_t *key); u64 siphash_4u32(u32, u32, u32, u32, const siphash_key_t *key);}hj)sbah}(h]h ]h"]h$]h&]hhuh1jhhhK-hjhhubh)}(h如果向一个通用的hsiphash函数传递一个恒定长度的常量,他将 在编译的时候将常量折叠,并自动选择一个优化后的函数。h]h如果向一个通用的hsiphash函数传递一个恒定长度的常量,他将 在编译的时候将常量折叠,并自动选择一个优化后的函数。}(hj7hhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhK6hjhhubh)}(h哈希表键函数的用法::h]h哈希表键函数的用法:}(hjEhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhK9hjhhubj)}(hXstruct some_hashtable { DECLARE_HASHTABLE(hashtable, 8); siphash_key_t key; }; void init_hashtable(struct some_hashtable *table) { get_random_bytes(&table->key, sizeof(table->key)); } static inline hlist_head *some_hashtable_bucket(struct some_hashtable *table, struct interesting_input *input) { return &table->hashtable[siphash(input, sizeof(*input), &table->key) & (HASH_SIZE(table->hashtable) - 1)]; }h]hXstruct some_hashtable { DECLARE_HASHTABLE(hashtable, 8); siphash_key_t key; }; void init_hashtable(struct some_hashtable *table) { get_random_bytes(&table->key, sizeof(table->key)); } static inline hlist_head *some_hashtable_bucket(struct some_hashtable *table, struct interesting_input *input) { return &table->hashtable[siphash(input, sizeof(*input), &table->key) & (HASH_SIZE(table->hashtable) - 1)]; }}hjSsbah}(h]h ]h"]h$]h&]hhuh1jhhhK;hjhhubh)}(hK然后,你可以像往常一样对返回的哈希存储桶进行迭代。h]hK然后,你可以像往常一样对返回的哈希存储桶进行迭代。}(hjahhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKJhjhhubeh}(h]id2ah ]h"] 使用函数ah$]h&]uh1jVhjXhhhhhK%ubjW)}(hhh](j\)}(h 安全性h]h 安全性}(hjzhhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjwhhhhhKMubh)}(hSipHash有着非常高的安全性,因为其有128位的密钥。只要密钥是保密的, 即使攻击者看到多个输出,也无法猜测出函数的正确输出,因为2^128次 方个输出是非常庞大的。h]hSipHash有着非常高的安全性,因为其有128位的密钥。只要密钥是保密的, 即使攻击者看到多个输出,也无法猜测出函数的正确输出,因为2^128次 方个输出是非常庞大的。}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKOhjwhhubh)}(h'Linux实现了SipHash的“2-4”变体h]h'Linux实现了SipHash的“2-4”变体}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKShjwhhubeh}(h]id3ah ]h"] 安全性ah$]h&]uh1jVhjXhhhhhKMubjW)}(hhh](j\)}(hStruct-passing陷阱h]hStruct-passing陷阱}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjhhhhhKVubh)}(hX通常情况下,XuY函数的输出长度不够大,因此你可能需要传递一个预填充 的结构体给SipHash,在这样做时,务必确保结构体没有填充空隙,最简单 的方法就是将结构体的成员按照大小降序的方式排序,并且使用offsetofend() 函数代替sizeof()来获取结构体大小,出于性能的考虑,如果可以的话,最 好将结构体按右边界对齐,示例如下::h]hX通常情况下,XuY函数的输出长度不够大,因此你可能需要传递一个预填充 的结构体给SipHash,在这样做时,务必确保结构体没有填充空隙,最简单 的方法就是将结构体的成员按照大小降序的方式排序,并且使用offsetofend() 函数代替sizeof()来获取结构体大小,出于性能的考虑,如果可以的话,最 好将结构体按右边界对齐,示例如下:}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKXhjhhubj)}(hX.const struct { struct in6_addr saddr; u32 counter; u16 dport; } __aligned(SIPHASH_ALIGNMENT) combined = { .saddr = *(struct in6_addr *)saddr, .counter = counter, .dport = dport }; u64 h = siphash(&combined, offsetofend(typeof(combined), dport), &secret);h]hX.const struct { struct in6_addr saddr; u32 counter; u16 dport; } __aligned(SIPHASH_ALIGNMENT) combined = { .saddr = *(struct in6_addr *)saddr, .counter = counter, .dport = dport }; u64 h = siphash(&combined, offsetofend(typeof(combined), dport), &secret);}hjsbah}(h]h ]h"]h$]h&]hhuh1jhhhK^hjhhubeh}(h]struct-passingah ]h"]struct-passing陷阱ah$]h&]uh1jVhjXhhhhhKVubjW)}(hhh](j\)}(h资源h]h资源}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjhhhhhKjubh)}(he如果你有兴趣了解更多信息,请阅读SipHash论文: https://131002.net/siphash/siphash.pdfh](h?如果你有兴趣了解更多信息,请阅读SipHash论文: }(hjhhhNhNubj))}(h&https://131002.net/siphash/siphash.pdfh]h&https://131002.net/siphash/siphash.pdf}(hjhhhNhNubah}(h]h ]h"]h$]h&]refurijuh1j(hjubeh}(h]h ]h"]h$]h&]uh1hhhhKlhjhhubeh}(h]id4ah ]h"]资源ah$]h&]uh1jVhjXhhhhhKjubeh}(h] siphash-prfah ]h"]1siphash - 一种短输入伪随机函数(prf)ah$]h&]uh1jVhhhhhhhK ubh transition)}(hO-------------------------------------------------------------------------------h]h}(h]h ]h"]h$]h&]uh1jhhhKohhhhubjW)}(hhh](j\)}(h6HalfSipHash 是 SipHash 的一个较不安全的变种h]h6HalfSipHash 是 SipHash 的一个较不安全的变种}(hj.hhhNhNubah}(h]h ]h"]h$]h&]uh1j[hj+hhhhhKsubh)}(h.:作者: Jason A.Donenfeld h](h:作者: Jason A.Donenfeld <}(hj<hhhNhNubj))}(hjason@zx2c4.comh]hjason@zx2c4.com}(hjDhhhNhNubah}(h]h ]h"]h$]h&]refurimailto:jason@zx2c4.comuh1j(hj<ubh>}(hj<hhhNhNubeh}(h]h ]h"]h$]h&]uh1hhhhKuhj+hhubh)}(hX如果你认为SipHash的速度不够快,无法满足你的需求,那么你可以 使用HalfSipHash,这是一种令人担忧但是有用的选择。HalfSipHash 将SipHash的轮数从“2-4”降低到“1-3”,更令人担心的是,它使用一 个容易被穷举攻击的64位密钥(输出为32位),而不是SipHash的128位 密钥,不过,这对于要求高性能“jhash”用户来说这是比较好的选择。h]hX如果你认为SipHash的速度不够快,无法满足你的需求,那么你可以 使用HalfSipHash,这是一种令人担忧但是有用的选择。HalfSipHash 将SipHash的轮数从“2-4”降低到“1-3”,更令人担心的是,它使用一 个容易被穷举攻击的64位密钥(输出为32位),而不是SipHash的128位 密钥,不过,这对于要求高性能“jhash”用户来说这是比较好的选择。}(hj^hhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKwhj+hhubh)}(h8HalfSipHash是通过 "hsiphash" 系列函数提供的。h]hkey, sizeof(table->key)); } static inline hlist_head *some_hashtable_bucket(struct some_hashtable *table, struct interesting_input *input) { return &table->hashtable[hsiphash(input, sizeof(*input), &table->key) & (HASH_SIZE(table->hashtable) - 1)]; }h]hXstruct some_hashtable { DECLARE_HASHTABLE(hashtable, 8); hsiphash_key_t key; }; void init_hashtable(struct some_hashtable *table) { get_random_bytes(&table->key, sizeof(table->key)); } static inline hlist_head *some_hashtable_bucket(struct some_hashtable *table, struct interesting_input *input) { return &table->hashtable[hsiphash(input, sizeof(*input), &table->key) & (HASH_SIZE(table->hashtable) - 1)]; }}hjUsbah}(h]h ]h"]h$]h&]hhuh1jhhhKhjDhhubh)}(hK然后,你可以像往常一样对返回的哈希存储桶进行迭代。h]hK然后,你可以像往常一样对返回的哈希存储桶进行迭代。}(hjchhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKhjDhhubeh}(h]id7ah ]h"]哈希表键函数的用法ah$]h&]uh1jVhj+hhhhhKubjW)}(hhh](j\)}(h性能h]h性能}(hj|hhhNhNubah}(h]h ]h"]h$]h&]uh1j[hjyhhhhhKubh)}(hhsiphash()大约比jhash()慢三倍,这是因为有许多替换,不过这些都不是问题, 因为哈希表查找不是瓶颈。而且,这些牺牲是为了hsiphash()的安全性和DoS抗 性,这是值得的。h]hhsiphash()大约比jhash()慢三倍,这是因为有许多替换,不过这些都不是问题, 因为哈希表查找不是瓶颈。而且,这些牺牲是为了hsiphash()的安全性和DoS抗 性,这是值得的。}(hjhhhNhNubah}(h]h ]h"]h$]h&]uh1hhhhKhjyhhubeh}(h]id8ah ]h"]性能ah$]h&]uh1jVhj+hhhhhKubeh}(h]halfsiphash-siphashah ]h"]6halfsiphash 是 siphash 的一个较不安全的变种ah$]h&]uh1jVhhhhhhhKsubeh}(h]h ]h"]h$]h&]sourcehuh1hcurrent_sourceN current_lineNsettingsdocutils.frontendValues)}(j[N generatorN datestampN source_linkN source_urlN toc_backlinksentryfootnote_backlinksK sectnum_xformKstrip_commentsNstrip_elements_with_classesN strip_classesN report_levelK halt_levelKexit_status_levelKdebugNwarning_streamN tracebackinput_encoding utf-8-siginput_encoding_error_handlerstrictoutput_encodingutf-8output_encoding_error_handlerjerror_encodingutf-8error_encoding_error_handlerbackslashreplace language_codeenrecord_dependenciesNconfigN id_prefixhauto_id_prefixid dump_settingsNdump_internalsNdump_transformsNdump_pseudo_xmlNexpose_internalsNstrict_visitorN_disable_configN_sourceh _destinationN _config_files]7/var/lib/git/docbuild/linux/Documentation/docutils.confafile_insertion_enabled raw_enabledKline_length_limitM'pep_referencesN pep_base_urlhttps://peps.python.org/pep_file_url_templatepep-%04drfc_referencesN rfc_base_url&https://datatracker.ietf.org/doc/html/ tab_widthKtrim_footnote_reference_spacesyntax_highlightlong smart_quotessmartquotes_locales]character_level_inline_markupdoctitle_xform docinfo_xformKsectsubtitle_xform image_loadinglinkembed_stylesheetcloak_email_addressessection_self_linkenvNubreporterNindirect_targets]substitution_defs}substitution_names}refnames}refids}nameids}(jjjjjtjqjjjjjjjjjjjAj>jvjsjju nametypes}(jjjtjjjjjjAjvjuh}(jjXjjjqjjjwjjjjjj+jjj>jjsjDjjyu footnote_refs} citation_refs} autofootnotes]autofootnote_refs]symbol_footnotes]symbol_footnote_refs] footnotes] citations]autofootnote_startKsymbol_footnote_startK id_counter collectionsCounter}jKsRparse_messages]transform_messages] transformerN include_log]5Documentation/translations/zh_CN/security/siphash.rst(NNNNta decorationNhhub.