梁玉英
(广东理工学院信息工程系,广东 肇庆 526100)
ECC(Elliptic Curves Cryptography),椭圆曲线密码编码学,该算法由华盛顿大学NealKoblitz和IBM的VictorM iller在1985年提出应用在加密技术上,根据是有限域上的椭圆曲线上的点群中的离散对数问题ECDLP。在公钥密码体制中,ECC算法是目前已知的公钥体制中对每比特所提供加密强度最高的一种加密机制。很多软件的序列号通常都采用该算法,它在软件注册保护方面起到很大的作用[1]。
在欧美发达国家的一些公司,以及不少的密码学研究小组都已实现了椭圆曲线密码体制,最有名的ECC密码技术公司是加拿大的Certicom。中国也有一些密码学者做了相关的ECC加密研究,有不少的厂商已经开发基于椭圆曲线的产品。国内外对于ECC算法的研究也是方兴未艾。
目前,C++、VB和Java都能解决数据加密的设计与实现,其中Java是一款面向对象的程序设计语言,在2014至2017年的世界编程语言排行榜中,Java一直排名第一,由此可见Java语言应用的广泛性[2]。它具有跨平台性、安全性、多线程和简单易用性,它提供了密钥管理、认证、加密、数字签名和存取控制功能,利用Java程序设计语言能较好地实现对文件、数据的加密。
ECC是基于椭圆曲线离散对数问题的各种公钥密码体制,它是利用有限域上椭圆曲线的有限点群代替基于离散对数问题密码体制中有限循环群所得到的一类密码体制。在有限域Fp中定义一个椭圆曲线,常用y2=x3+ax+b;[3]
(1)Fp中只有p个元素,p为素数;
(2)Fp中,a+b≡c(mod p),a×b≡c(mod p),a/b≡c(mod p);
(3)4a3+27b2≠0 (mod p),a,b是小于p的非负整数;
(4)x,y属于0到p-1间的证书,曲线标记为Ep(a,b);
阶:椭圆曲线上一点P,存在正整数n,使得nP=O∞,则n为P的阶,若n不存在,则P是无限阶的,有限域上定义的椭圆曲线上所有点的阶都存在[4]。
椭圆曲线难解性为:其中Q,G为Ep(a,b)上的点,k为小于n的整数,n是点G的阶,给定k和G,计算Q容易,但是给定Q和G,求k就很难了。因此,设Q为公钥,k为私钥,G为基点[5]。
ECC算法的依据就是利用定义在椭圆曲线点群上的离散对数问题的难解性。要对明文信息m加密,首先必须把要发送的明文信息m编码形成(x,y)的点Pm,并对点Pm进行加密,然后对密文进行解密。注意,不能简单地将信息编码成点x坐标或y坐标,因为并不是所有的坐标都在Ep(a,b)[6]。具体的加密过程如下:
首先,用户A选定一个大的整数p及椭圆曲线的参数a和b。由此可以定义出点的椭圆群Ep(a,b)。其次,在Ep(a,b)中挑选基点G=(xG,yG),G的阶为一个非常大的数n。
接着用户A选定一个私钥k,并生成公钥K=kG;若A将Ep(a,b)和k,G发送给用户B,B收到后将明文编码到Ep(a,b)上一点M,并产生一个随机数r;然后B计算点C1=M+rK,C2=rG,B将C1,C2传给A,A计算C1-kC2=M+rkG-krG=M,A对M解码得到明文。
攻击者只能得到Ep(a,b),G,K,C1,C2,没有k就无法得到M。
签名验证的过程如下:
用户A选定一条椭圆曲线Ep(a,b),并取曲线上一点作为基点G;A选择一个私钥k,并生成公钥K=kG;A产生一个随机数 r,计算 R(x,y)=rG;A 计算 Hash=SHA(M),M'=M(modp);A计算S=(Hash+M'k)/r(modp);B获得S和M',Ep(a,b),K,R(x,y);B计算Hash=SHA(M),M'=M(modp);B计算R'=(Hash*G+M'*K)/S=(Hash*G+M'*kG)*r/(Hash+M'k)=rG=R(x,y),若R'=R,则验签成功。
从上述的研究看,椭圆曲线离散对数问题比有限域上的离散对数问题更难以处理[7]。
(1)密钥长度短,占用带宽少:ECC加密算法的密钥长度是256位,占用的存储空间少,CPU开销低,带宽的占用也自然比较少。随着移动网络技术的发展,ECC算法为移动互联网提供了更可靠、更安全的环境。
(2)性能更好,安全性更高:安全性能一般通过算法的抗击强度来反映,ECC加密算法需要较短的密钥长度来提供更好的安全性,相对其他的公钥算法,ECC算法能更好地防止攻击。采用256位的ECC密钥与3072位RSA密钥的加密强度水平相同,目前公钥加密应用广泛的RSA密钥长度是2048位,则210位ECC与2048位的RSA具有相同的安全强度。ECC算法采用更低的计算能力代价得到了更高的安全性[8]。
(3)延长硬件使用寿命:ECC算法由于提供了更高的安全性,可以更好地保护投资的基础设施。ECC的密钥长度增加度一般按128位增长,而RSA则是倍数增长,采用ECC加密算法将延长计算机硬件的使用寿命。经国外有关权威机构测试,在Apache和IIS服务器采用ECC算法,Web服务器响应时间比RSA快十几倍[9]。
在jak 1.5后的版本中加入了ECC算法,采用ECC算法对文件加密的算法如下:
Java语言的安全性高,安全的类主要在java.security包中,实现ECC算法还需要导入包java.math、java.util、javax.crypto、sun.security。基于Java语言的数字签名密钥生成、数字签名和验证设计实现如下:
(1)密钥对的生成实现
密钥对的生成实现算法如下:
声明公有的静态字符串常量ALGORITHM="ECC";
声明公有的静态字符串常量PUBLIC_KEY="ECCPublicKey";
声明公有的静态字符串常量PRIVATE_KEY="ECCPrivateKey";
用私钥解密:byte[]keyBytes=decryptBASE64(key);
取得私钥,创建一个PKCS8EncodedKeySpec对象pkcs8KeySpec,使用PKCS#8标准作为密钥规范管理的编码格式来表示私钥;
创建一个KeyFactory对象keyFactory;
用ECPrivateKdy类创建对象priKey,用ECPrivateKey-Spec类创建对象ecPrivateKeySpec;
对数据解密priKey.getParams();
Cipher类为加密和解密提供密码功能,它构成了Java Cryptographic Extension框架的核心。创建Cipher对象cipher,调用init函数进行初始化数据。
(2)用公钥加密
BASE64是用来将非ASCII字符的数据转换成ASCII字符的一种方法,BASE64虽然不是安全领域下的加密解密算法,但它适合在http、m ime协议下快速传输数据,常见于邮件、http加密。
取得公钥byte[]keyBytes=decryptBASE64(private Key);
X509EncodedKeySpec类继承EncodedKeySpec类,以编码格式来表示公钥,实例化X509EncodedKeySpec对象x509KeySpec;
利用KeyFactory类生成密钥对象keyFactory;
创建EC公钥对象pubKey;
利用函数generatePublic(x509KeySpec)生成相应的密钥规范公钥对象;
利用ECPublicKeySpec类创建带关联参数的椭圆曲线公用密钥ecPublicKeySpec;
利用函数pubKey.getParams()对数据加密;
创建Cipher类的加密/解密对象cipher。
(3)取得私钥
声明Key接口变量key;
利用keyMap.get(PRIVATE_KEY)取得私钥;
返回encryptBASE64(key.getEncoded());
(4)取得公钥
声明Key接口变量key;
利用keyMap.get(PUBLIC_KEY)取得私钥;返回encryptBASE64(key.getEncoded());
本文研究基于java语言的ECC算法的加密技术,应用了Java系统中的安全类,采用对称密钥封装方法得到密文。研究得出,采用该方法进行对文件加密,抗攻击性好,加密性能好,具有较高的应用价值,可以应用在电子商务和电子政务等Web应用中得。但如果想要获得ECC算法实现,需要调用硬件完成加密和解密,涉及Java Card领域、PKCS#13。上述的加密/解密算法使用CPU进行,由于比较耗费资源,效率较低。