什么是计时攻击?Spring Boot 中该怎样防御?
松哥最近在研究 Spring Security 源码,发现了很多好玩的代码,抽空写几篇文章和小伙伴们分享一下。 很多人吐槽 Spring Security 比 Shiro 重量级,这个重量级不是凭空来的,重量有重量的好处,就是它提供了更为强大的防护功能。 比如松哥最近看到的一段代码: protected final UserDetails retrieveUser(String username, UsernamePasswordAuthenticationToken authentication) throws AuthenticationException { prepareTimingAttackProtection(); try { UserDetails loadedUser = this.getUserDetailsService().loadUserByUsername(username); if (loadedUser == null) { throw new InternalAuthenticationServiceException( "UserDetailsService returned null, which is an interface contract violation"); } return loadedUser; } catch (UsernameNotFoundException ex) { mitigateAgainstTimingAttack(authentication); throw ex; } catch (InternalAuthenticationServiceException ex) { throw ex; } catch (Exception ex) { throw new InternalAuthenticationServiceException(ex.getMessage(), ex); } } 这段代码位于 DaoAuthenticationProvider 类中,为了方便大家理解,我来简单说下这段代码的上下文环境。 当用户提交用户名密码登录之后,Spring Security 需要根据用户提交的用户名去数据库中查询用户。 查到用户对象之后,再去比对从数据库中查到的用户密码和用户提交的密码之间的差异。 而上面这段代码就是 Spring Security 根据用户登录时传入的用户名去数据库中查询用户,并将查到的用户返回。方法中还有一个 authentication 参数,这个参数里边保存了用户登录时传入的用户名/密码信息。 那么这段代码有什么神奇之处呢? 我们来一行一行分析。 (编辑:ASP站长网) |