DSA算法和DSA指令概述
- DSA算法是美国国家标准的数字签名算法,只具备数字签名的功能不具备密钥交换的功能
- 生成DSA参数然后生成DSA密钥,DSA参数决定了DSA密钥的长度
- 三个指令
- 首先是dsaparam指令,该指令主要用来生成DSA密钥参数,并提供了一些格式转换、C代码生成等其他类似于dhparam指令的功能。一组DSA参数可以用来生成多个不同的DSA密钥,而不是仅仅对应于一个DSA密钥。
- gendsa指令用来从现有的DSA参数中生成DSA密钥,使用相同的DSA参数可以生成不同的DSA密钥,不过这需要rand选项指定的随机数种子文件配合。
- 同样,为了提供一些可能需要的DSA密钥管理功能,如格式转换、保护口令更改等,OpenSSL提供了dsa指令
- 为什么生成DSA密钥参数跟生成DSA密钥区分开来呢?首先,因为要使用一个DSA密钥,必须预先共享其参数p、q和g;其次,因为生成一组DSA密钥参数所耗费的时间比较多,而一组DSA密钥参数可以用来生成许多组DSA密钥,所以分开来就可以避免每次生成一对DSA密钥都要重新生成DSA密钥参数,耗费大量的时间。
- OpenSSL没有提供类似rsautl指令的专门DSA算法使用指令,但是可以在dgst指令中使用DSA算法和密钥进行数字签名和验证的操作。这基本上满足了DSA算法使用的要求。
生成和管理 DSA密钥参数
-
dsaparam 用于生成和管理DSA密钥参数,其功能和参数类似dhparam,使用dsaparam 生成的密钥参数不仅仅可以用于生成不同的DSA密钥,还可以用于生成DH密钥参数
- (2)输入和输出格式选项inform和outform inform和outform选项指定了输入DSA密钥参数和输出DSA密钥参数或者DSA密钥的编码格式,目前支持的格式有PEM和DER两种,默认的是PEM格式。
- (3)输入和输出文件选项in和out in选项指定了输入文件名,一般来说,如果使用了in选项,表示是从已有的DSA密钥参数中生成新的DSA密钥或者对密钥参数进行格式转换等管理操作。如果要生成新的DSA密钥参数或者利用新生成的密钥参数生成DSA密钥,那么一般不需要使用in选项。
- out选项指定了输出文件名,输出的信息可能是DSA密钥参数、DSA密钥和text选项给出的明文解析信息。输出的DSA密钥参数和DSA密钥的编码格式由outform选项指定。如果输出的是DSA密钥,那么其形式是DSA私钥的形式,但是包含了DSA公钥参数。
- (4)engine选项 如果使用了有效的Engine设备并提供该选项,而且在生成DSA密钥参数的过程中执行的操作或者函数在Engine中支持,比如大数操作、随机数生成及信息摘要函数等,那么就会采用Engine设备而不是OpenSSL默认的算法库的函数进行实际的操作和运算。同样,engine_id是一个简短的描述型字符串,由Engine接口决定。
- (5)C语言代码输出选项某些时候,我们可能需要将DSA密钥参数写入到C语言的代码中去,OpenSSL提供了从一组DSA密钥参数转换成代码的方法,就是在dsaparam指令中使用C选项。下面是使用dsaparam指令的C选项生成的一段DSA密钥参数的C语言代码。
- (6)直接生成DSA密钥选项genkey 虽然dsaparam指令通常用来生成DSA密钥参数,但是如果你想直接生成一个DSA密钥而不是DSA密钥参数,那么可以使用genkey选项。该选项使得输出到out选项指定的输出文件的是一个PEM编码或者DER编码的DSA私钥。但是,该私钥是没有进行加密的,如果要安全地存放,必须使用下面将要介绍的dsa指令进行加密保存。使用该选项后,输出的虽然只是一个DSA私钥,但是私钥结构里面已经包含了DSA公钥的参数,所以,如果要得到相应的DSA公钥,那么只要从这个DSA私钥里面提取相应的参数就可以了,dsa指令可以帮助你从一个DSA私钥得到相应的DSA公钥。
- (7)DSA密钥参数长度选项numbits DSA密钥参数决定了用其产生的DSA密钥的长度,一般来说,512位的DSA密钥只能提供很短期的安全性能,所以一般建议使用1024位的DSA密钥。
- (8)其他选项rand选项跟其他指令同名选项一样,指定了一个随机数种子文件,默认情况下指令也会从其他可能的途径自动获取。text选项告诉指令输出DSA密钥参数的明文解析
-
使用了text选项的 DSA 密钥参数输出结果
- noout选项告诉指令不用输出DSA密钥参数或者DSA密钥到out选项指定的文件或者标准输出设备中(通常是指令行界面)。一般来说,在你想测试和查看DSA密钥参数的时候,为了避免还要到相应的目录中去删除一个无意义的文件的时候会使用这个选项。
生成DSA密钥
- (1)gendsa指令格式 DSA密钥是在DSA密钥参数的基础上产生的,一对DSA密钥可以包含三个部分:DSA密钥参数(p、q和g)、DSA私钥和DSA公钥。DSA密钥参数是公开的,甚至可以为一组网络用户所共享,即这组网络用户使用相同的DSA密钥参数产生各自的DSA密钥对。内部使用随机数控制不同的用户密钥不是完全一样的
- dsaparam指令为我们生成了DSA密钥参数,紧接着我们就要使用OpenSSL提供的gendsa指令生成真正要使用的DSA密钥对。虽然说是密钥对,但是gendsa指令只输出DSA私钥,这是因为DSA私钥里面已经包含了DSA公钥的所有参数,所以如果需要使用相应的DSA公钥,那么可以通过DSA私钥来获得。dsa指令提供了从DSA私钥输出相应DSA公钥的功能。
- gendsa指令的格式如下:
- (2)输出文件选项out out选项指定了保存生成的DSA密钥的文件,如果没有使用out选项,那么DSA密钥将会输出到标准输出设备,一般就是当前指令行界面。
- 输出密钥的编码格式OpenSSL没有提供可以选择的余地,只能是PEM编码。
- (3)输出DSA私钥保护口令passout 如果输出的DSA私钥是保存在文件里面,那么对私钥进行加密保护就显得非常必要。跟其他密钥保护的方式一样,OpenSSL提供了基于口令的加密保护方式。passout指定了获取加密口令的源和方法,口令可以从指令参数、文件、环境变量等获得。pasout选项只有在指定了DSA私钥使用加密选项之后才会有效,否则该选项将被简单忽略。
- (4)密钥加密算法选项对DSA私钥进行保护的重要性我们已经反复强调多次,现在就不用说为什么了。加密算法选项指定了使用什么对称加密算法来对DSA私钥进行加密,可选的算法有6种:DES、DES3、IDEA、128位AES、192位AES和256位AES。这些算法使用的加密密钥和初始变量都经过特定的算法从提供的口令中获取。如果使用了上述加密算法选项之一但却没有使用pasout选项指定加密口令,那么指令会在指令行界面提示用户输入口令。如果没有使用上述任意一种加密算法,那么对DSA密钥将不会进行加密,这当然很危险!
- (5)engine选项engine选项似乎紧紧跟随每一个OpenSSL指令,在这里也不例外。在gendsa指令里使用engine选项指定有效的Engine之后,受影响最显著的地方就是加密密钥的算法,也就是说,如果加密的密钥算法在指定的Engine接口中支持,那么指令就会调用Engine设备对DSA密钥进行加密。其次,产生随机数的操作也可能会在Engine设备中进行,只要Engine接口支持这些相应的操作。
- (6)DSA密钥参数选项该选项指定用于生成DSA密钥的DSA密钥参数文件,DSA密钥的长度就取决于文件里面的DSA密钥参数。遗憾的是对于该文件的格式你没有选择,只有输入PEM编码的DSA密钥参数才能够正确运行gendsa指令。如果你拥有的是一个DER编码的DSA密钥参数,那么请使用dsaparam指令先将其转换成PEM编码的DSA密钥参数。
- (7)随机数选项生成DSA密钥的过程同样需要随机数的参与,既然有随机数参与,我们就需要随机数种子文件,rand选项一直就充当这样的功能。当然,如果你不提供该文件,那么指令也会想办法从其他可能的途径获取随机数种子。在使用了Engine的情况下,甚至硬件设备有可能自己能够支持产生随机数种子的操作。
管理DSA密钥
- 考虑到用户后期对先前生成的DSA密钥的要求的变化,提供dsa指令
- dsa指令格式
- (2)输入和输出格式选项inform和outform inform和outform选项分别指定了输入DSA密钥和输出DSA密钥的编码格式,目前支持的格式包括PEM编码和DER编码两种。
- (3)输入和输出密钥类型选项pubin和pubout默认情况下,输入和输出的密钥都应该是DSA私钥,但是,有时候我们可能需要从一个输入的DSA私钥里面获取一个相应的DSA公钥发送给签名验证方,那么就可以选择pubout选项来输出一个DSA公钥。在某些情况下,我们甚至可能输入一个DSA公钥,对它的信息进行解释或者进行格式转换。因为DSA公钥不需要加密,所以如果使用了pubin或者pubout选项,相应的passin和passout选项指定的口令也会被忽略,输出的公钥不会被加密。
- (4)输入和输出文件选项in和out in指定了输入DSA密钥的保存文件,默认情况下输入的文件应该保存一个PEM编码或者DER编码的DSA私钥。如果使用了pubin选项,则指令认为输入文件保存的是一个没有加密的DSA公钥。密钥的编码格式默认是PEM,如果是DER格式,则需要使用inform选项指定。
- out选项指定了输出DSA密钥的保存文件,如果输入的是DSA私钥,默认情况下输出的也是DSA私钥,但是如果使用了pubout选项,则输出的将是一个DSA公钥。如果输入是一个DSA公钥,那么输出也是一个DSA公钥。输出公钥的时候不会对密钥进行加密操作。默认情况下输出的密钥编码格式是PEM,如果需要输出密钥编码格式为DER的密钥,那么可以使用outform选项指定。
- 如果使用了text和modulus选项,还会在out指定的文件中输入明文解析信息。使用了noout选项将不会输出编码密钥数据。
- (5)输入和输出口令选项passin和passout pasin选项指定了解密DSA私钥需要的口令的方式和源,口令可以从多种渠道获取。如果输入了DSA私钥而没有使用pasin选项,那么指令会从指令行界面提示输入解密密钥数据需要的口令。如果使用了pubin选项,那么passin选项会被忽略。pasout选项指定加密输出的DSA私钥需要的口令的方式和源。如果选择了加密算法但是没有使用pasout选项,那么指令会从指令行界面提示用户输入保护密钥的口令。如果输入的是DSA公钥(使用pubin选项)或者输出的是DSA公钥(使用pubout选项),那么pasout选项就会被忽略。
- (6)加密算法选项dsa指令提供了更加丰富的密钥加密算法,理论上,所有OpenSSL支持的对称加密算法都可以在这里用于加密DSA私钥。使用的方式是直接输入该对称加密算法的合法名称。
- (7)engine选项 engine选项指定使用Engine设备中支持的对称加密算法替代OpenSSL算法库中的加密算法对DSA私钥进行加密或者解密。例如,如果Engine设备支持DES3算法,而且你指定了使用DES3算法对DSA密钥进行加密,那么指令就会调用Engine设备中相应的DES3算法对DSA私钥进行加密。
- (8)解析信息输出选项使用text选项会输出DSA密钥各项参数的明文解析信息,包括DSA密钥的三个基本参数、公钥参数和私钥参数。使用modulus选项会输出DSA公钥的参数信息。而使用noout选项则指令不会输出编码的密钥数据。