前几天项目用到sm4加密解密,加密为十六进制字符串,再将十六进制字符串解密。网上百度了下,sm4是密钥长度和加密明文加密密文都为16个字节十六进制数据,网上的sm4 c语言算法很容易搜到,笔者刚开始没怎么理解,以为只能对16字节数据进行加密,并且不论是多少字节的数据加密出来都是16字节的。后来看了下源码,应该是加密的数据应该是16字节或者16的整数倍个字节的数据,若不够16倍数字节应该补0x00数据,最后加密出来的数据和输入数据的长度应该一致,即

密文长度=明文长度 

而且密钥长度一致,是16字节的。c的代码里面输入输出都是十六进制数据,需要将字符串转为char类型数组,并且保证长度是16整数倍

+(unsigned char*)hexEnc:(NSString*)strInput{
NSData* data = [strInput dataUsingEncoding:NSUTF8StringEncoding];
NSUInteger length = data.length;
NSUInteger plusLength;
if(length % 16 == 0){
plusLength = 0;
}
else{
plusLength = 16 - length % 16;
}
NSMutableString* new_str = [[NSMutableString alloc] initWithString:strInput];
for (int i =0;i < plusLength;i++) {
[new_str appendString:@" "];
}
NSUInteger new_length = length+plusLength;
Uchar *input = (Uchar*)malloc(sizeof(Uchar)*new_length);
Uchar *output = (Uchar*)malloc(sizeof(Uchar)*new_length);
Uchar key[16] = KEY;
const char *utfChar = [new_str UTF8String];
memset(input, 0, new_length);
memcpy(input, utfChar, new_length); sm4_context ctx;
unsigned long i; sm4_setkey_enc(&ctx,key);
sm4_crypt_ecb(&ctx,1,new_length,input,output); for(i=0;i<new_length;i++)
printf("%02x ", output[i]);
printf("\n"); unsigned char* c_str = Hex2Str(output,new_length);
printf("%s\n", c_str); free(input);
free(output);
return c_str;
}

  

解密时密文是十六进制字符串,需要将字符串先转为int类型数组,再作解密操作,具体代码  
+(unsigned char*)hexDec:(NSString*)strInput{
int inputCharSize = strInput.length/2;
Uchar* input = (Uchar*)malloc(sizeof(Uchar)*inputCharSize);
Uchar* output = (Uchar*)malloc(sizeof(Uchar)*inputCharSize);
for (int i = 0; i<inputCharSize; i++) {
NSString* str = [strInput substringWithRange:NSMakeRange(i*2, 2)];
NSString* gw = [str substringWithRange:NSMakeRange(0, 1)]
;
NSString* dw = [str substringWithRange:NSMakeRange(1, 1)];
int n_gw = [HexToStr str2Int:gw];
int n_dw = [HexToStr str2Int:dw];
int result = n_gw * 16 + n_dw;
input[i] = result;
}
Uchar key[16] = KEY; sm4_context ctx;
sm4_setkey_dec(&ctx,key);
sm4_crypt_ecb(&ctx,0,inputCharSize,input,output);
int kgPos = 0;
for(int i=0;i<inputCharSize;i++){
printf("%02x ", output[i]);
if (output[i] == 32) {
kgPos = i;
output[i] = '\0';
}
}
printf("\n");
free(input);
// free(output);
return output;
}

  

demo地址:https://github.com/dinner/sm4

  





sm4加密 解密(oc)的更多相关文章

  1. SM4加密算法实现Java和C#相互加密解密

    SM4加密算法实现Java和C#相互加密解密 近期由于项目需要使用SM4对数据进行加密,然后传给Java后台,Java后台使用的也是SM4的加密算法但是就是解密不正确,经过一步步调试发现Java中好多 ...

  2. Cryptopp iOS 使用 RSA加密解密和签名验证签名

    Cryptopp 是一个c++写的功能完善的密码学工具,类似于openssl 官网:https://www.cryptopp.com 以下主要演示Cryptopp 在iOS上的RSA加密解密签名与验证 ...

  3. 手摸手带你认识https涉及的知识,并实现https加密解密,加签解签

    目录 http访问流程 https访问流程 证书 加密/解密 加签/验签 Java实现https 拓展 @ 看完整的代码,直接去完整代码实现,看实现完后会遇到的坑,直接去测试过程中的问题,包括经过代理 ...

  4. Python常用加密解密算法

    MD5加密 简介 这是一种使用非常广泛的加密方式,不可逆的,常见16位和32位一般都是md5 实现 import hashlib data = '你好' print(hashlib.md5(data. ...

  5. PHP的学习--RSA加密解密

    PHP服务端与客户端交互或者提供开放API时,通常需要对敏感的数据进行加密,这时候rsa非对称加密就能派上用处了. 举个通俗易懂的例子,假设我们再登录一个网站,发送账号和密码,请求被拦截了. 密码没加 ...

  6. 兼容javascript和C#的RSA加密解密算法,对web提交的数据进行加密传输

    Web应用中往往涉及到敏感的数据,由于HTTP协议以明文的形式与服务器进行交互,因此可以通过截获请求的数据包进行分析来盗取有用的信息.虽然https可以对传输的数据进行加密,但是必须要申请证书(一般都 ...

  7. .NET和JAVA中BYTE的区别以及JAVA中“DES/CBC/PKCS5PADDING” 加密解密在.NET中的实现

    场景:java 作为客户端调用已有的一个.net写的server的webservice,输入string,返回字节数组. 问题:返回的值不是自己想要的,跟.net客户端直接调用总是有差距 分析:平台不 ...

  8. php使用openssl进行Rsa长数据加密(117)解密(128) 和 DES 加密解密

    PHP使用openssl进行Rsa加密,如果要加密的明文太长则会出错,解决方法:加密的时候117个字符加密一次,然后把所有的密文拼接成一个密文:解密的时候需要128个字符解密一下,然后拼接成数据. 加 ...

  9. c#和js互通的AES加密解密

    一.使用场景 在使用前后端分离的框架中常常会进行传输数据相互加密解密以确保数据的安全性,如web Api返回加密数据客户端或web端进行解密,或者客户端或web端进行加密提交数据服务端解密数据等等. ...

随机推荐

  1. memory corruption

    今天遇到了一个比较弱的问题,但是涉及到一些东西,所以记录一下. 问题表现为,系统BOSD,在析构函数进行free的时候,有的时候是在使用buffer的过程中就BSOD. 之前是怀疑因为分配的是page ...

  2. 前端学习 第二弹: JavaScript中的一些函数与对象(1)

    前端学习 第二弹: JavaScript中的一些函数与对象(1) 1.apply与call函数 每个函数都包含两个非继承而来的方法:apply()和call(). 他们的用途相同,都是在特定的作用域中 ...

  3. MsXml创建和解析XML示例

    一.MsXml创建XML文档示例 // XmlCreationDemo.cpp #include <stdlib.h> #include <stdio.h> // 引入MSXM ...

  4. 转-springAOP基于XML配置文件方式

    springAOP基于XML配置文件方式 时间 2014-03-28 20:11:12  CSDN博客 原文  http://blog.csdn.net/yantingmei/article/deta ...

  5. AngularJS之directive

    AngularJS之directive AngularJS是什么就不多舌了,这里简单介绍下directive.内容基本上是读书笔记,所以如果你看过<AngularJS up and runnin ...

  6. [Maven] - Eclipse "maven compiler plugin" 冲突解决

    刚安装最新的Maven 3.2.5,在eclipse中使用maven的Run As->Maven Install,总会提示: Failed to execute goal org.apache. ...

  7. C#:调用webservice时提示对操作的回复消息正文进行反序列化时出错

    主要原因webservice返回值的长度超过readerQuotas中的了maxStringContentLength值,造成返回值截断,不完整,反序列化时出错. <readerQuotas m ...

  8. MSSQL 多行合并为一行

    select ptl_a01, ptl_piitem, ( ) as ptl_count, STUFF((SELECT ','+ltrim(ptl_pdid) FROM PRODUCT_TRACEAB ...

  9. Python的第七天

    面向对象编程: 编程范式 编程是程序员用特定的语法+数据结构+算法组成的代码来告诉计算机如何执行任务的过程,一个程序是程序员为了得到一个任务结果而编写的一组指令的集合,正所谓条条大路通罗马,实现一个任 ...

  10. 关于MySql 关键字与字段名冲突 的问题

    我在用mysql创建数据表时,其中一个表怎么创建都提示失败,最终我把语句翻来覆去折腾了许多遍之后发现原来我的一个字段值的名称为order的字段出了问题,把它去了就好了,最后结论就是设置字段值名称时不要 ...