在阅读了罗斯·安德森(Ross Anderson)的书《安全工程》的第一部分,并阐明了Wikipedia上的某些主题之后,我遇到了Client Nonce(cnonce)的想法。罗斯在他的书中从未提及过它,我正努力了解它在用户身份验证中的作用。服务器向客户端提供一个随机数(使用一次的数字),客户端必须使用该随机数来哈希其响应,然后服务器使用提供的随机数对期望的响应进行哈希处理,并且如果客户端的哈希值与客户端的哈希值匹配服务器,然后服务器可以验证请求是否有效且新鲜。这就是所有验证的内容;有效而新鲜。
我为客户随机数找到的解释不那么直接和可疑。用于摘要访问身份验证的Wikipedia页面以及此处Stack Overflow上的一些响应似乎表明,使用客户端随机数可以避免选择明文攻击。我对这个想法有几个问题:

如果一个人可以嗅探和插入数据包,那么最大的漏洞就是中间人攻击,即席即席也不能克服,因此使得两者都毫无意义。
假设攻击者一秒钟不想进行中间人攻击并想恢复身份验证详细信息,那么Cnonce如何提供额外的保护?如果攻击者拦截通信并以其自己的随机数答复请求,则来自客户端的响应将是随机数,数据和随机数的哈希值,以及未加密形式的随机数。现在,攻击者可以访问随机数,nonce和哈希。攻击者现在可以使用nonce和nonce哈希其rainbow表并找到匹配项。因此,该保护提供了零附加保护。

那么保护的目的是什么?
我假设方程式的某些部分我不了解,但是我还没有找到关于该部分是什么的解释。
EDIT一些答案表明,客户可以提供一个随机数,它将为客户服务。相同的目的。但是,这打破了挑战-响应模型,这意味着什么?

#1 楼

随机数是一个实体在协议中选择的唯一值,用于保护该实体免受巨大的“重播”攻击。

例如,考虑一个密码基于身份的身份验证协议,如下所示:


服务器向客户端发送“挑战”(假定为随机值c)
客户端应通过发送h(c | | p)其中h是安全哈希函数(例如SHA-256),p是用户密码,“ ||”表示级联
服务器在其自己的数据库中查找密码,重新计算预期的客户端响应,并查看其是否与客户端发送的密码匹配

密码是适合人脑的秘密值;这样,它们就不会非常复杂,并且有可能构建一个大的字典,其中将包含用户密码的可能性很高。 “大”是指“可以在几周内用一个中等规模的集群来枚举”。在当前的讨论中,我们认为攻击者只需花几周的时间就能破解一个密码。这是我们要实现的安全级别。

想象一个被动的攻击者:攻击者窃听但不更改消息。他看到了c和h(c || p),因此他可以使用其群集枚举潜在的密码,直到找到匹配项。这对他来说将是昂贵的。如果攻击者想攻击两个密码,那么他必须做两次该工作。攻击者希望使用预先计算的表(“彩虹表”只是一种具有优化存储的预先计算的表)在两个攻击实例之间进行一些成本分摊;但是构建彩虹表仍然需要枚举完整的字典并对每个哈希进行哈希处理密码)。但是,随机质询击败了攻击者:由于每个实例都涉及一个新质询,因此即使使用相同的密码,每个会话的哈希函数输入也会有所不同。因此,攻击者无法构建有用的预先计算表,尤其是Rainbow表。

现在假定攻击者已处于活动状态。他将不只是观察消息,而是会主动更改消息,删除某些消息,复制其他消息或插入自己的消息。攻击者现在可以拦截来自客户端的连接尝试。攻击者选择并发送自己的质询(c'),然后等待客户端响应(h(c'|| p))。请注意,没有联系真正的服务器。攻击者只是在客户端响应后立即突然断开连接,以模拟良性网络错误。在这种攻击模型中,攻击者取得了很大的进步:他仍然具有挑战c'和相应的响应,但是挑战是攻击者认为合适的值。攻击者将要做的始终是应对相同的挑战c'。每次使用相同的挑战,攻击者就可以执行预先计算:他可以构建使用特殊“挑战”的预先计算表(即Rainbow表)。现在,攻击者可以攻击几个不同的密码,而无需为每个密码承担字典枚举的费用。

客户现时避免了此问题。协议变为:


服务器发送随机质询c

客户端选择随机数n(每次均应不同)
客户端发送n | | h(c || n || p)

服务器重新计算h(c || n || p)(使用数据库中的p),并查看此值是否与客户端发送的值匹配

由于客户端在每个会话的哈希函数输入中包含一个新的随机值(“ nonce”),因此即使攻击者可以选择挑战,哈希函数输入也会每次都不同。这将破坏预先计算的(彩虹)表并恢复我们预期的安全级别。同一系统中的两个不同的用户将具有不同的名称。但是,用户在更改密码时将保留其姓名;并且两个不同的用户在两个不同的系统上可能具有相同的名称(例如,每个类Unix系统都有一个“ root”用户)。因此,用户名不是一个很好的随机数(但总比根本没有客户端随机数更好)。

总而言之,客户端随机数用于保护客户端免受重放攻击( “服务器”实际上是攻击者,他将向他希望攻击的每个客户端发送相同的挑战)。如果质询是在包含强服务器身份验证(例如SSL)的通道上执行的,则不需要这样做。密码认证密钥交换是高级协议,可确保客户端和服务器之间基于密码的相互认证,而无需先验信任(SSL客户端认证SSL服务器证书时称为“根证书”),并防止主动和被动攻击者(包括对单个密码的“两周集群”攻击,因此,它比上面的协议(随机数或无随机数)严格更好。

评论


哇。谢谢!我希望我可以再次投票。

–user2014
2011年4月11日下午13:14

在摘要身份验证中,服务器发送一个随机数,然后客户端将该相同的随机数发回。在我看来,客户端随机数仅在服务器采用客户端说的随机数是表面价值而不是服务器本身生成的价值时才真正有用。如果HTTP连接保持活动状态,在我看来,服务器可以知道它刚发送的现时是什么。

– paynes_bay
2011年7月10日23:30

@paynes_bay使用HTTP时,无状态通常是理想的属性,尤其是出于可伸缩性和高可用性的原因。不将随机数发送回服务器将使摘要身份验证处于有状态。

– Evgeniy Berezovsky
2012年10月2日,下午1:37

出于好奇-服务器跟踪和记录客户端现时是否是客户端现时的重要组成部分,以便在客户端重现也被重用时拒绝身份验证?

–怒不可遏
16年5月31日在19:54

明确地说:客户端随机数尤其适用于攻击者是服务器的情况,对吗?否则,即使我在安全通道上,某人/拦截器仍然可以简单地再次转发请求(重播),而无需解密。但是对于此类攻击,我们使用其他机制,例如请求计数器(每个随机数)等。

–zgulser
19/12/24在10:36

#2 楼

让我尝试回答您的问题:“假设攻击者一秒钟不想进行中间人攻击并希望恢复身份验证详细信息,那么Cnonce如何提供附加信息?保护?”

通常,客户端不仅会在请求中包含随机数,还会在整个请求(包括随机数)上签名。这意味着即使攻击者在客户端和服务器之间截获了一条消息:


重播攻击也不会起作用(因为服务器正在跟踪客户端的随机数)。 >攻击者不能只使用新的客户端随机数生成新消息,因为它不知道如何正确签名新消​​息(即,它缺少客户端机密或私钥)。


评论


客户产生的随机数不会打破挑战-响应模型吗?这有什么作用?可以确认该消息以前没有被查看过,但不是新鲜的。换句话说,它使系统可以进行定时攻击,其中攻击者拦截客户端响应,拒绝服务并重新使用响应。

–匿名
2011年4月10日在9:06

客户端可以包括到期时间。如果服务器在(已签名)消息中包含的到期后接收到该消息,则将其与签名无效一样对待。

– yfeldblum
2011年4月11日,下午2:21

@Justice引入了同步时间等问题。服务器如何知道客户端的时间?这很容易欺骗。

–user2014
2011年4月11日在2:23

伪造者不能伪造过期时间,因为该过期时间是正在签名的消息的一部分。在HTTP中,不需要时钟同步,因为客户端总是从服务器获取时钟时间。尽管客户端可以根据自己的时钟来计算持续时间,但客户端将始终将该持续时间添加到服务器的时钟时间中以获得另一个时钟时间。

– yfeldblum
2011年4月11日上午11:11

@Justice我刚刚意识到使用服务器时间并通过客户端时间对其进行修改实际上只是实现服务器随机数的另一种方法。因此,实际上,以这种方式使用时间只是在使用服务器随机数。

–user2014
2011年4月13日在6:54

#3 楼

我认为一个好主意是阅读有关Oauth之类的nonce值的用法。简而言之,当使用OAuth的应用向支持OAuth的服务发出请求时,该请求必须包含一堆字段,其中两个是时间戳记和随机数。该表格的目的很明显:它可以指示发送消息的时间范围,以便服务器可以更好地猜测消息是否陈旧。显然,后者是一堆随机字符/字节。然后,将具有签名附加到请求(无论是查询参数还是HTTP标头)并发送到服务器。请求的实际主体不会被散列。

OAuth服务器应跟踪给定客户端的N个随机数的前一组,以确保它们不会被重用。鉴于消息的主体可以更改(本质上对哈希没有影响),因此必须进行其他更改(例如,随机数)以确保请求是唯一的,这一点很重要。鉴于HTTP的开放/纯文本性质,这非常重要。

这是否有助于阐明其目的? (希望如此:))。

评论


OAuth不会通过让消费者创建随机数来打破质询响应模型吗?这样不好吗?用户可以确认该消息以前没有被查看过,但不能确认它是新鲜的。换句话说,它使系统可以进行定时攻击,其中攻击者拦截客户端响应,拒绝服务并重新使用响应。

–匿名
2011年4月10日在9:02

#4 楼

根据RFC 2617,cnoncenc参数可防止选择的明文攻击。

如果Eve更改了服务器发送给客户端的随机数,Eve获得了什么?夏娃无法从h(password || nonce)生成h(password || fake_nonce),从理论上讲,服务器似乎也不应该接受h(password || fake_nonce),因为服务器应该知道发出的是现时是什么,没有知道是什么现时。

评论


如果您要提一个问题,它可能应该放在一个单独的问题中,而不是在此处回答。

– D.W.
2011年7月11日下午0:24

这里几乎是相同的问题。我想知道客户现时的用途是什么。 RFC2617提供了一个答案,但是这个答案对我来说没有多大意义。托马斯·波宁(Thomas Pornin)也提供了答案,但根据我对他的回答的回答,他的回答对我来说也没有多大意义。

– paynes_bay
2011年7月11日,在1:27

@paynes_bay欢迎来到该网站!请阅读常见问题解答-答案是为了回答问题。如果您要澄清其他答案,可以使用注释。如果您想获得原始问题未涵盖的其他信息,请询问另一个!

–AVID♦
2011年7月11日在22:48