iOS-AES算法总结
AESCipher.h
#import <Foundation/Foundation.h> @interface AESCipher : NSObject /**
加密算法 @param dictionary 待加密字典
@param key 密钥
@return 加密后字符串
*/
+ (NSString *)encryptAES:(NSDictionary *)dictionary key:(NSString *)key; /**
解密算法 @param content 待解密字符串
@param key 密钥
@return 解密后字典
*/
+ (NSDictionary *)decryptAES:(NSString *)content key:(NSString *)key; @end
AESCiphser.m
注意:需要注意的是AES加密算法中的这几个设置参数一定要和服务器端一致,否则会有各种错误
1)密钥长度(Key Size)
2)加密模式(Cipher Mode)
3)填充方式(Padding)
4)初始向量(Initialization Vector)
#import "AESCipher.h"
#import <CommonCrypto/CommonCryptor.h> /** 初始向量*/
NSString *const kInitVector = @"16-Bytes--String";
/** 密钥长度:AES-128*/
size_t const kKeySize = kCCKeySizeAES128; @implementation AESCipher #pragma mark - 加密算法 + (NSString *)encryptAES:(NSDictionary *)dictionary key:(NSString *)key { // NSDictionary -> NSString
NSString *content = [self convertToJsonData:dictionary]; // 待加密数据: NSString -> NSData
NSData *contentData = [content dataUsingEncoding:NSUTF8StringEncoding];
NSUInteger dataLength = contentData.length; // 密钥长度:kCCKeySizeAES128
char keyPtr[kKeySize + ]; // 为结束符'\\0' +1
memset(keyPtr, , sizeof(keyPtr));
[key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding]; // 密文长度 <= 明文长度 + BlockSize(填充数据)
size_t encryptSize = dataLength + kCCBlockSizeAES128;
void *encryptedBytes = malloc(encryptSize);
size_t actualOutSize = ; NSData *initVector = [kInitVector dataUsingEncoding:NSUTF8StringEncoding]; // 设置加密参数
// 系统默认使用 CBC 加密模式,然后指明使用 PKCS7Padding 补码方式(填充方式)
CCCryptorStatus cryptStatus = CCCrypt(kCCEncrypt,
kCCAlgorithmAES,
kCCOptionPKCS7Padding,
keyPtr,
kKeySize,
initVector.bytes,
contentData.bytes,
dataLength,
encryptedBytes,
encryptSize,
&actualOutSize); if (cryptStatus == kCCSuccess) {
// 加密结果编码方式: base64 编码
return [[NSData dataWithBytesNoCopy:encryptedBytes length:actualOutSize] base64EncodedStringWithOptions:NSDataBase64EncodingEndLineWithLineFeed];
}
free(encryptedBytes);
return nil;
} #pragma mark - 解密算法 + (NSDictionary *)decryptAES:(NSString *)content key:(NSString *)key {
// 把 base64 String 转换成 Data
NSData *contentData = [[NSData alloc] initWithBase64EncodedString:content options:NSDataBase64DecodingIgnoreUnknownCharacters];
NSUInteger dataLength = contentData.length; char keyPtr[kKeySize + ];
memset(keyPtr, , sizeof(keyPtr));
[key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding]; size_t decryptSize = dataLength + kCCBlockSizeAES128;
void *decryptedBytes = malloc(decryptSize);
size_t actualOutSize = ; NSData *initVector = [kInitVector dataUsingEncoding:NSUTF8StringEncoding]; CCCryptorStatus cryptStatus = CCCrypt(kCCDecrypt,
kCCAlgorithmAES,
kCCOptionPKCS7Padding,
keyPtr,
kKeySize,
initVector.bytes,
contentData.bytes,
dataLength,
decryptedBytes,
decryptSize,
&actualOutSize); if (cryptStatus == kCCSuccess) {
NSString *content = [[NSString alloc] initWithData:[NSData dataWithBytesNoCopy:decryptedBytes length:actualOutSize] encoding:NSUTF8StringEncoding];
return [self dictionaryWithJsonString:content];
}
free(decryptedBytes);
return nil;
} #pragma mark - NSDictionary <-> NSString // NSDictionary 转换为 NSString
+ (NSString *)convertToJsonData:(NSDictionary *)dictionary {
NSError *error;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dictionary options:NSJSONWritingPrettyPrinted error:&error];
NSString *jsonString;
if (!jsonData) {
NSLog(@"%@",error);
}else{
jsonString = [[NSString alloc]initWithData:jsonData encoding:NSUTF8StringEncoding];
}
NSMutableString *mutStr = [NSMutableString stringWithString:jsonString];
NSRange range = {,jsonString.length};
//去掉字符串中的空格
[mutStr replaceOccurrencesOfString:@" " withString:@"" options:NSLiteralSearch range:range];
NSRange range2 = {,mutStr.length};
//去掉字符串中的换行符
[mutStr replaceOccurrencesOfString:@"\n" withString:@"" options:NSLiteralSearch range:range2];
return mutStr;
} // NSString 转换为 NSDictionary
+ (NSDictionary *)dictionaryWithJsonString:(NSString *)content {
if (content == nil) {
return nil;
} NSData *jsonData = [content dataUsingEncoding:NSUTF8StringEncoding];
NSError *err;
NSDictionary *dic = [NSJSONSerialization JSONObjectWithData:jsonData
options:NSJSONReadingMutableContainers
error:&err];
if(err)
{
NSLog(@"json解析失败:%@",err);
return nil;
}
return dic;
} @end
加密方法的调用(key--密钥,一定要确保是16位的,且和服务端一致)
NSDictionary *dictionary = @{
@"key":@"value"
};
NSString *key = @"";
NSString *cipherString = [AESCipher encryptAES:dictionary key:key];
解密方法的调用
NSDictionary *dictionary = [AESCipher decryptAES:cipherString key:key];
iOS-AES算法总结的更多相关文章
- AES算法简介
AES算法简介 一. AES的结构 1.总体结构 明文分组的长度为128位即16字节,密钥长度可以为16,24或者32字节(128,192,256位).根据密钥的长度,算法被称为AES-128,AES ...
- 使用python进行加密解密AES算法
使用python进行加密解密AES算法-代码分享-PYTHON开发者社区-pythoner.org 使用python进行加密解密AES算法 TY 发布于 2011-09-26 21:36:53,分类: ...
- C#与Java互通AES算法加密解密
/// <summary>AES加密</summary> /// <param name="text">明文</param> /// ...
- AES算法,DES算法,RSA算法JAVA实现
1 AES算法 1.1 算法描述 1.1.1 设计思想 Rijndael密码的设计力求满足以下3条标准: ① 抵抗所有已知的攻击. ② 在多个平台上速度快,编码紧凑. ③ 设计 ...
- ORACLE 字段AES算法加密、解密
ORACLE 字段AES算法加密.解密(解决中文乱码问题)2014年02月12日 17:13:37 华智互联 阅读数:97971.加解密函数入口 CREATE OR REPLACE FUNCTION ...
- #微码分享#AES算法的C++包装类
AES为Advanced Encryption Standard的缩写,中文名:高级加密标准,在密码学中又称Rijndael加密法,是美国联邦政府采用的一种区块加密标准,用来替代DES.基于std:: ...
- 利用AES算法加密数据
准备工作: 模块安装问题: 首先在python中安装Crypto这个包 但是在安装模块后在使用过程中他会报错 下面是解决方法: pip3 install pycrypto 安装会报错 https:// ...
- Delphi与JAVA互加解密AES算法
搞了半天终于把这个对应的参数搞上了,话不多说,先干上代码: package com.bss.util; import java.io.UnsupportedEncodingException; imp ...
- .NET与Java互通AES算法加密解密
/// <summary>AES加密</summary> /// <param name="text">明文</param> /// ...
- 分组密码(四)AES算法① — 密码学复习(七)
介绍完S-PN型结构之后,下面介绍AES算法.由于内容比较多所以将其分为两篇来介绍,本篇主要讲AES的历史时间节点.产生背景.与DES的对比.算法框图(粗略)以及一些数学基础. 7.1 AES的历史时 ...
随机推荐
- 十.iSCSI网络磁盘
默认端口:3260 • Internet SCSI,网际SCSI接口 – 一种基于C/S架构的虚拟磁盘技术 – 服务器提供磁盘空间,客户机连接并当成本地磁盘使用 • backstore,后端存储 ...
- Android工程的合并
http://www.xuanyusong.com/archives/3395 1.游戏包名( 类似 com.xx.xxx ) Android应用程序只能有一个包名,如果两个游戏包名一样,那么后者安装 ...
- VTK 简单点云数据显示绘制
基于vtkPolyData,绘制时除了输入点坐标,还需要通过setVerts指定点绘制信息. simplePoints.txt的内容为简单的 xyz,如: 20 20 20 20 20 30 20 2 ...
- php rsa 非对称加解密类
<?php header("Content-Type: text/html;charset=utf-8"); /* 生成公钥.私钥对,私钥加密的内容能通过公钥解密(反过来亦可 ...
- mysqlslap压力测试时出现"Can't connect to MySQL server"
mysqlslap -utest -h 192.168.1.12 -p'test' --concurrency=100 --iterations=500 --create-schema='my_db' ...
- shell 脚本同时对远程多台机器执行命令
脚本1:需要机器之间免密 ssh-copy-id [-i [identity_file]] [user@]machine #!/bin/bash # ------------------------- ...
- fdisk创立主分区过程
[root@localhost ~]# fdisk /dev/sdb …省略部分输出… Command (m for help): p #显示当前硬盘的分区列表 Disk /dev/sdb: 21.5 ...
- mybatis bind标签
开门见山的说,平时写模糊查询,一直用${name},例如: select * from table where name like '%${name}%' 后来知道了,这样写可能会引发sql注入,于是 ...
- Keil MDK 5代码补全功能设置
这段时间在用Keil5编程,经常会遇到在程序文件头部定义一个全局变量.在后面的编程过程中,经常会要用到这个变量,如果每次再打这个变量名会特别麻烦和浪费时间,我就想着Keil5有没有像vs软件一样的代码 ...
- 使用requirejs+vue 打造 无需编译发布便捷修改调整的模块开发方案 (一)
前言 不知道大家有没有这种感觉,现在流行的很多前端技术,基本上都基于webpack编译,当然不是说这种方案不好,在标准的开发流程运行中,这种方式其实也挺不错,管理方便,代码统一. 痛点:项目不是单独针 ...