使用iOS原生API实现异步SSL通信

前言

通常SSL连接可以使用OpenSSL库来实现,但OpenSSL库体积比较大,完整动态库大小在2M左右。由于项目希望尽量控制iOS端应用包的大小,因此尝试使用iOS原生API实现SSL连接的功能。

另外,工程中已经存在异步网络IO的框架,因此希望直接在当前的IO框架上实现SSL功能,而不是再引入另一个IO框架。

总结

总的来说,iOS下实现SSL通信能力非常简单,iOS提供的API在使用上和OpenSSL有异曲同工之处,并且比OpenSSL绑定BIO的方法更加合理

主要API列表

所有API都通过头文件<Security/Security.h>引入

只需要数个API就可以实现SSL的读写能力,这里先全部列举出来

  1. SSLCreateContext 创建SSL上下文
  2. SSLSetIOFuncs 设置IO读写回调函数
  3. SSLSetConnection 设置回调函数中使用的自定义参数
  4. SSLHandshake 发起SSL握手过程
  5. SSLRead 读取数据
  6. SSLWrite 写入数据
初始化SSL上下文
  1. 创建SSL上下文句柄 ctx = SSLCreateContext(NULL, kSSLClientSide, kSSLStreamType)

  2. 设置读写回调 SSLSetIOFuncs(ctx, SSLReadCallback, SSLWriteCallback)

  3. 设置其他选项,可以给SSL上下文设置其他额外选项,需要在调用SSLHandshake之前完成,具体可参考apple的文档。

SSL握手/数据发送/数据接收

完成SSL上下文的初始化以后就可以开始握手流程,握手、发送、接收的处理流程区别不大,本文以握手流程为例进行说明。

  1. 调用SSLHandshake方法,在返回前SSLReadCallback或SSLWriteCallback会被立即调用,SSL组件通过这两个回调获取相应的通信数据从而与实际的网络socket和网络框架解耦。
  2. SSLReadCallback会告诉我们SSL组件需要读取多少字节数据,如果我们可以立即从socket或缓冲区(取决于实现)返回相应大小的数据,那么返回noErr,否则返回errSSLWouldBlock。
  3. SSLWriteCallback会把发送数据的缓冲区与其大小通过参数传给我们,如果发送可以立即完成(比如成功写到了socket缓存中),那么返回noErr,否则返回errSSLWouldBlock。
  4. 当我们在回调函数中返回errSSLWouldBlock后,SSLHandshake也会返回errSSLWouldBlack。这时我们需要判断是读操作未完成或是写操作未完成,然后开始同步或异步的从socket中获取数据。
  5. 成功获取数据后,我们需要回到步骤1,再次调用SSLHandshake,直到SSLHandshake返回noErr或返回其他错误

使用伪代码说明流程

void handshake()
{
    err = SSLHandshake();
    if (err == noErr) {
        //handshake successfully done
    }
    else if (err == errSSLWouldBlock) {
        handlePendingIO(onFinished() {
            handshake() //call SSLHandshake again
        });
    }
    else {
        handleError();
    }
}

void handlePendingIO() 
{
    if (haveDataToWrite()) {
        asyncWriteDataToSocket();
    }
    else (haveDataToRead()) {
        asyncReadDataFromSocket();
    }
    else {
        handleError();
    }
}
代码示例

https://github.com/misora-cc/ssl-ios

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值