c中的openssl摘要与java中的不同
以下是DigitalSigning处理程序的一部分代码c中的openssl摘要与java中的不同,java,c,openssl,digital-signature,message-digest,Java,C,Openssl,Digital Signature,Message Digest,以下是DigitalSigning处理程序的一部分代码 final String NAMESPACEURI_WSSECURITY_WSU= "http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd"; final String NAMESPACEURI_WSSECURITY_WSSE = "http://docs.oasisopen.org/wss/2004/01/oa
final String NAMESPACEURI_WSSECURITY_WSU=
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd";
final String NAMESPACEURI_WSSECURITY_WSSE =
"http://docs.oasisopen.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-
1.0.xsd";
final String NAMESPACEURI_XMLSIGNATURE_DS = "http://www.w3.org/2000/09/xmldsig#";
final String ATTRIBUTENAME_X509TOKEN =
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-x509-token-profile
-1.0#X509v3";
final String ENCODINGTYPE_BASE64 =
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-
security-1.0#Base64Binary";
SOAPHeaderElement securityElement = header
.addHeaderElement(new QName(
NAMESPACEURI_WSSECURITY_WSSE, "Security",
"wsse"));
//securityElement.setMustUnderstand(true);
securityElement.addNamespaceDeclaration("wsu",
NAMESPACEURI_WSSECURITY_WSU);
securityElement.addNamespaceDeclaration("ds",
NAMESPACEURI_XMLSIGNATURE_DS);
SOAPBody body = envelope.getBody();
String bodyIdRef = "Id-1-BD-1";
body.addAttribute(new QName(NAMESPACEURI_WSSECURITY_WSU, "Id",
"wsu"), bodyIdRef);
// Prepare security token element
SOAPElement binarySecurityTokenElement = securityElement
.addChildElement("BinarySecurityToken", "wsse");
String tokenIdRef = "Id-1-TK-1";
binarySecurityTokenElement.addAttribute(new QName(
NAMESPACEURI_WSSECURITY_WSU, "Id", "wsu"), tokenIdRef);
binarySecurityTokenElement.addAttribute(new QName("ValueType"),
ATTRIBUTENAME_X509TOKEN);
binarySecurityTokenElement.addAttribute(new QName(
"EncodingType"), ENCODINGTYPE_BASE64);
// Open keystore and insert encoded certificate
KeyStore store = KeyStore.getInstance("PKCS12"); //default is "JKS"
store.load(new FileInputStream(new File(KEYSTORE_LOC)),
KEYSTORE_STOREPASS.toCharArray());
KEYSTORE_KEYALIAS = (String)store.aliases().nextElement();
Certificate certificate = store
.getCertificate(KEYSTORE_KEYALIAS);
binarySecurityTokenElement.addTextNode(new String(Base64Coder
.encode(certificate.getEncoded())));
// Prepare digest for Signature generation
XMLSignatureFactory signFactory = XMLSignatureFactory
.getInstance("DOM");
C14NMethodParameterSpec spec1 = null;
CanonicalizationMethod c14nMethod = signFactory
.newCanonicalizationMethod(
CanonicalizationMethod.EXCLUSIVE, spec1);
DigestMethod digestMethod = signFactory.newDigestMethod(
DigestMethod.SHA256, null);
String methodNS = "http://www.w3.org/2001/04/xmldsig-more#rsa-sha256";
SignatureMethod signMethod = signFactory.newSignatureMethod(
methodNS, null);
TransformParameterSpec spec2 = null;
Transform transform = signFactory.newTransform(
CanonicalizationMethod.EXCLUSIVE, spec2);
List<Transform> transformList = Collections
.singletonList(transform);
List<Reference> referenceList = new ArrayList<Reference>();
Reference reference1 = signFactory.newReference(
"#" + bodyIdRef, digestMethod, transformList, null,
null);
referenceList.add(reference1);
SignedInfo signInfo = signFactory.newSignedInfo(c14nMethod,
signMethod, referenceList);
// Get Private key
Key privateKey = store.getKey(KEYSTORE_KEYALIAS,
KEYSTORE_KEYPASSWORD.toCharArray());
// Create <SignatureValue>
DOMSignContext dsc = new DOMSignContext(privateKey,
securityElement);
dsc.setDefaultNamespacePrefix("ds");
XMLSignature signature = signFactory.newXMLSignature(signInfo,
null);
signature.sign(dsc);
// Prepare key info element
SOAPElement signatureElement = (SOAPElement) securityElement
.getLastChild();
SOAPElement keyInfoElement = signatureElement
.addChildElement(new QName(
NAMESPACEURI_XMLSIGNATURE_DS, "KeyInfo", "ds"));
SOAPElement
securityTokenReferenceElement = keyInfoElement.addChildElement(
"SecurityTokenReference", "wsse");
SOAPElement referenceElement = securityTokenReferenceElement
.addChildElement("Reference", "wsse");
referenceElement.setAttribute("URI", "#" + tokenIdRef);
referenceElement.setAttribute("ValueType",
ATTRIBUTENAME_X509TOKEN);
最终字符串NAMESPACEURI\u WSSECURITY\u WSU=
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-wssecurity-utility-1.0.xsd";
最终字符串NAMESPACEURI\u WSSECURITY\u WSSE=
"http://docs.oasisopen.org/wss/2004/01/oasis-200401-wss-wssecurity-secext-
1.0.xsd”;
最终字符串NAMESPACEURI\u XMLSIGNATURE\u DS=”http://www.w3.org/2000/09/xmldsig#";
最终字符串ATTRIBUTENAME_X509TOKEN=
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-x509-token-profile
-1.0#X509v3”;
最终字符串编码类型_BASE64=
"http://docs.oasis-open.org/wss/2004/01/oasis-200401-wss-soap-message-
安全-1.0#Base64Binary”;
SOAPHeaderElement securityElement=标头
.addHeaderElement(新QName(
NAMESPACEURI_WSSECURITY_WSSE,“安全性”,
"证券交易所");;
//securityElement.setMustUnderstand(true);
securityElement.addNamespaceDeclaration(“wsu”,
名称空间URI(安全性);
securityElement.addNamespaceDeclaration(“ds”,
名称空间URI_XMLSIGNATURE_DS);
SOAPBody=envelope.getBody();
字符串bodyIdRef=“Id-1-BD-1”;
addAttribute(新的QName(NAMESPACEURI\u WSSECURITY\u WSU,“Id”,
“wsu”)、bodyIdRef);
//准备安全令牌元素
SOAPElement binarySecurityTokenElement=securityElement
.addChildElement(“二进制安全令牌”,“wsse”);
字符串tokenIdRef=“Id-1-TK-1”;
binarySecurityTokenElement.addAttribute(新QName(
NAMESPACEURI_WSSECURITY_WSU,“Id”,“WSU”),tokenIdRef);
binarySecurityTokenElement.addAttribute(新的QName(“ValueType”),
ATTRIBUTENAME_X509;令牌);
binarySecurityTokenElement.addAttribute(新QName(
“编码类型”),编码类型_BASE64);
//打开密钥库并插入编码证书
KeyStore store=KeyStore.getInstance(“PKCS12”)//默认值为“JKS”
load(新文件输入流(新文件(KEYSTORE_LOC)),
KEYSTORE_STOREPASS.toCharArray());
KEYSTORE_keyalis=(字符串)store.aliases().nextElement();
证书=存储
.getCertificate(密钥库\密钥别名);
binarySecurityTokenElement.addTextNode(新字符串(Base64Coder
.encode(certificate.getEncoded());
//为签名生成准备摘要
XMLSignatureFactory signFactory=XMLSignatureFactory
.getInstance(“DOM”);
C14NMethodParameterSpec spec1=null;
规范化方法c14nMethod=signFactory
.newcanonicalization方法(
规范化方法(独占,spec1);
DigestMethod DigestMethod=signFactory.newDigestMethod(
DigestMethod.SHA256,空);
字符串methodNS=”http://www.w3.org/2001/04/xmldsig-more#rsa-sha256”;
SignatureMethod signMethod=signFactory.newSignatureMethod(
methodNS,null);
TransformParameterSpec spec2=null;
Transform Transform=signFactory.newTransform(
规范化方法(独占,spec2);
列表=集合
.单音列表(转换);
List referenceList=new ArrayList();
Reference reference1=signFactory.newReference(
“#”+bodyIdRef,digestMethod,transformList,null,
无效);
referenceList.add(reference1);
SignedInfo-signInfo=signFactory.newSignedInfo(C14N方法,
符号方法(参照者);
//获取私钥
Key privateKey=store.getKey(KEYSTORE\u keyalis,
KEYSTORE_KEYPASSWORD.toCharArray());
//创造
DOMSignContext dsc=新的DOMSignContext(privateKey,
证券要素);
dsc.setDefaultNamespacePrefix(“ds”);
XMLSignature signature=signFactory.newXMLSignature(signInfo,
无效);
签名。签名(dsc);
//准备关键信息元素
SOAPElement signatureElement=(SOAPElement)securityElement
.getLastChild();
SOAPElement-keyInfoElement=signatureElement
.addChildElement(新的QName(
NAMESPACEURI_XMLSIGNATURE_DS,“KeyInfo”,“DS”);
皂素
securityTokenReferenceElement=keyInfoElement.addChildElement(
“SecurityTokenReference”、“wsse”);
SOAPElement referenceElement=securityTokenReferenceElement
.addChildElement(“参考”、“wsse”);
setAttribute(“URI”、“#”+tokenIdRef);
referenceElement.setAttribute(“ValueType”,
ATTRIBUTENAME_X509;令牌);
我为SOAP调用启用了日志记录,并提取了正在计算SHA-256格式的摘要的字符串。我使用相同的字符串来计算c中的摘要。下面是C++中的代码来计算。这两个值的结果都不同
#include <openssl/sha.h>
#include <openssl/evp.h>
#include <string>
#define std::string String
String conString = "String from logs ";
unsigned char md[SHA256_DIGEST_LENGTH];
unsigned int size = 0;
EVP_Digest(conString.c_str(), conString.size(), md, &size, EVP_sha256(),
NULL);
#包括
#包括
#包括
#定义std::string字符串
String conString=“来自日志的字符串”;
无符号字符md[SHA256_摘要_长度];
无符号整数大小=0;
执行副总裁摘要(consting.c_str(),consting.size(),md,&size,执行副总裁sha256(),
无效);
这方面的任何帮助都是有益的。谢谢,非常奇怪,但是下面计算sha256的代码片段生成了与java输出匹配的正确哈希
String sha256(const String& string)
{
unsigned char hash[SHA256_DIGEST_LENGTH];
SHA256_CTX sha256;
SHA256_Init(&sha256);
SHA256_Update(&sha256, string.c_str(), string.size());
SHA256_Final(hash, &sha256);
const char* digest = mcommons::util::base64(&hash[0], SHA256_DIGEST_LENGTH);
String conString = digest;
free((char*) digest);
return conString;
}
:)看起来java正在生成一个X509签名,这将是一个使用RSA加密的哈希。另外一个似乎是base64编码的,而另一个不是。Java代码不仅仅是计算SHA256——它是一个。这与OpenSSL代码段非常不同,OpenSSL代码段试图生成一个简单的SHA256摘要。我知道它首先将其规范化,然后计算SHA256,由于我正在从传递给digest函数的日志中提取字符串,因此摘要应该是相同的。org.jcp.xml.dsig.internal.DigesterOutputStream write FINER:预摘要输入:2012年11月28日7:51:24 PM org.jcp.xml.dsig.internal.DigesterOutputStream write FINER:c14n字符串的其他部分Nov 28,2012年11月28日下午7:51:24 org.jcp.xml.dsig.internal.dom.DOMReference digest精细:引用对象uri=#Id-1-BD-1 2012年11月28日下午7:51:24 org.jcp.xml.dsig.internal.dom.DOMReference digest