前几天项目用到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. Call me evilxr

    我是Evilxr,博客新开第一天:希望自己能坚持下去!之前友友推荐的是oschina,使用了一段时间发现oschina经常抽风,再者自己平时也有关注一些博客觉得cnblogs也不错,开博的初衷是想记录 ...

  2. Python requests 为pfsense 添加Routes

    # !/usr/bin/python 2 # -*- coding: utf-8 -*- __author__ = "Evilxr" import requests ips = o ...

  3. java通过反射取得一个类的完整结构

    首先我们在person包中新建一个Person.java: package person; import sex.Sex; public class Person{ private String na ...

  4. bzoj1188 [HNOI2007]分裂游戏 博弈论 sg函数的应用

    1188: [HNOI2007]分裂游戏 Time Limit: 10 Sec  Memory Limit: 162 MBSubmit: 973  Solved: 599[Submit][Status ...

  5. js控制 固定框架内图片 按比例显示 以及 占满框架 居中显示

    js控制 固定框架内图片 等比例显示 以及 占满框架 纵横居中显示 通过设置 js函数 fitDiv里面var fit的值就好 function fitDiv (obj) { var target_w ...

  6. 在实现和使用上与select和poll有很大差异

    在看此课程的读者,希望先阅读关于函数基础内容 函数定义与函数作用域 的章节,因为此课程或多或少会涉及函数基础的内容,而基础内容,本人放在 函数定义函数作用域 章节. 本文直接赘述函数参数与闭包,若涉及 ...

  7. [linux]解决vsftpd 读取目录列表失败的问题

    使用第三方FTP软件filezilla进行登陆,出现如下错误:状态:    正在连接 192.168.1.6:21...状态:    连接建立,等待欢迎消息...响应:    220 (vsFTPd ...

  8. nginx(tengine)的一些小优化(持续更新)

    1.nginx日志切割脚本 需求来源:nginx本身并没有日志切割的功能,由访问产生的大日志很难进行分析. 实现目的:每天对nginx日志进行切割,并备份至指定文件夹. 简要指令: mv /usr/l ...

  9. Web API数据传输加密

    http://www.cnblogs.com/wuhuacong/p/4620300.html Web API应用架构设计分析(2) 在上篇随笔<Web API应用架构设计分析(1)>, ...

  10. win10怎么取消登录密码

    win10安装后每次登录都需要输入密码,挺烦的,查了下,原来windows10无密码登录设置挺方便. 1. 按下win+x组合键,如下图所示 2. 在弹出菜单选择运行,如下图所示 或者直接按win+r ...