iOS RC4加密

iOS RC4加密的实现,要注意加密后生成字符串的步骤,有些要求是base64加密后输出,有些要求是字节数组转16进制字符串输出,所以要特别注意。

// rc4加密
- (NSString *)rc4Encode:(NSString *)aInput key:(NSString *)aKey {
    NSMutableArray *iS = [[NSMutableArray alloc] initWithCapacity:256];
        NSMutableArray *iK = [[NSMutableArray alloc] initWithCapacity:256];
        for (int i= 0; i<256; i++) {
            [iS addObject:[NSNumber numberWithInt:i]];
        }
        int j=1;
        for (short i=0; i<256; i++) {
            UniChar c = [aKey characterAtIndex:i%aKey.length];
            [iK addObject:[NSNumber numberWithChar:c]];
        }
        j=0;
        for (int i=0; i<256; i++) {
            int is = [[iS objectAtIndex:i] intValue];
            UniChar ik = (UniChar)[[iK objectAtIndex:i] charValue];
            j = (j + is + ik)%256;
            NSNumber *temp = [iS objectAtIndex:i];
            [iS replaceObjectAtIndex:i withObject:[iS objectAtIndex:j]];
            [iS replaceObjectAtIndex:j withObject:temp];
        }
        int i=0;
        j=0;
        Byte byteBuffer[aInput.length];
        for (short x=0; x<[aInput length]; x++) {
            i = (i+1)%256;
            int is = [[iS objectAtIndex:i] intValue];
            j = (j+is)%256;
            int is_i = [[iS objectAtIndex:i] intValue];
            int is_j = [[iS objectAtIndex:j] intValue];
            int t = (is_i+is_j) % 256;
            
            // 先交换位置,再取值
            [iS exchangeObjectAtIndex:i withObjectAtIndex:j];
            
            int iY = [[iS objectAtIndex:t] intValue];
            UniChar ch = (UniChar)[aInput characterAtIndex:x];
            UniChar ch_y = ch^iY;
            byteBuffer[x] = ch_y;
        }
    
    // 字节数组转16进制字符串输出
    NSString *resultString = [self stringFromByte:byteBuffer length:aInput.length];
    
//    NSData *adata = [[NSData alloc] initWithBytes:byteBuffer length:aInput.length];
//    NSString *string = [adata base64EncodedStringWithOptions:0]; // 以base64的加密结果输出
    return resultString;
}

//rc4解密
- (NSString *)rc4Decode:(NSString *)data key:(NSString*)secret{
    // 如果是16进制字符串
    NSData *raw = [self ByteDataFromString:data];
    
    // 如果是base64加密后字符串
//    NSData *raw = [[NSData alloc] initWithBase64EncodedString:data options:0];
    
    int cipherLength = (int)raw.length;
    UInt8 *cipher = malloc(cipherLength);
    [raw getBytes:cipher length:cipherLength];
    NSData *kData = [secret dataUsingEncoding:NSUTF8StringEncoding];
    int keyLength = (int)kData.length;
    UInt8 *kBytes = malloc(kData.length);
    [kData getBytes:kBytes length:kData.length];
    UInt8 *decipher = malloc(cipherLength + 1);
    UInt8 iS[256];
    UInt8 iK[256];
    int i;
    for (i = 0; i < 256; i++){
        iS[i] = i;
        iK[i] = kBytes[i % keyLength];
    }
    int j = 0;
    for (i = 0; i < 256; i++){
        int is = iS[i];
        int ik = iK[i];
        j = (j + is + ik)% 256;
        UInt8 temp = iS[i];
        iS[i] = iS[j];
        iS[j] = temp;
    }
    int q = 0;
    int p = 0;
    for (int x = 0; x < cipherLength; x++){
        q = (q + 1)% 256;
        p = (p + iS[q])% 256;
        int k = iS[p];
        iS[p] = iS[q];
        iS[q] = k;
        k = iS[(iS[q] + iS[p])% 256];
        decipher[x] = cipher[x] ^ k;
    }
    free(kBytes);
    decipher[cipherLength] = '\0';
    return @((char *)decipher);
}

// 字节数组转
- (NSString *)stringFromByte:(Byte *)byteBuffer length:(NSInteger)length {
    NSMutableString *hexString = [[NSMutableString alloc] init];
    for (int i = 0; i < length; i++) {
        [hexString appendString:[NSString stringWithFormat:@"%0.2hhx", byteBuffer[i]]];
    }
    return [hexString uppercaseString];
}

- (NSData *)ByteDataFromString:(NSString *)targetStr {
    NSInteger len = [targetStr length] / 2;    // Target length
    unsigned char *buf = malloc(len);
    unsigned char *whole_byte = buf;
    char byte_chars[3] = {'\0','\0','\0'};

    int i;
    for (i=0; i < [targetStr length] / 2; i++) {
        byte_chars[0] = [targetStr characterAtIndex:i*2];
        byte_chars[1] = [targetStr characterAtIndex:i*2+1];
        *whole_byte = strtol(byte_chars, NULL, 16);
        whole_byte++;
    }

    NSData *data = [NSData dataWithBytes:buf length:len];
    free( buf );
    return data;
}

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: iOS开发可以使用AVPlayer来播放加密的m3u8视频。首先,需要获取加密m3u8视频的URL地址。然后,可以使用AVAsset来创建一个播放资源对象,通过指定URL地址初始化AVURLAsset对象,如下所示: ``` NSURL *url = [NSURL URLWithString:@"加密m3u8视频的URL地址"]; AVURLAsset *asset = [AVURLAsset URLAssetWithURL:url options:nil]; ``` 接下来,可以创建一个AVPlayerItem对象,将asset设置为其参数,用于加载加密m3u8视频资源。同时,需要为AVAsset设置相应的解密密钥,以解密加密的m3u8视频,代码如下: ``` // 创建AVPlayerItem对象 AVPlayerItem *playerItem = [AVPlayerItem playerItemWithAsset:asset]; // 设置解密密钥,以解密加密m3u8视频 NSData *keyData = [NSData dataWithContentsOfURL:[NSURL URLWithString:@"密钥URL地址"]]; NSDictionary *encryptionInfo = @{AVAssetResourceLoadingRequestStreamingContentKeyRequestRequiresPersistentKey: @NO, AVAssetResourceLoadingRequestStreamingContentKeyRequestRequiresExternalization: @NO, AVAssetResourceLoadingRequestStreamingContentKeyRequestInitializationData: keyData}; [playerItem setExternalProtectionStatusDelegate:self queue:dispatch_get_main_queue()]; [playerItem setResourceLoaderDelegate:self queue:dispatch_get_main_queue()]; [playerItem setInitializationData: @[encryptionInfo] forAsset:asset]; ``` 最后,可以使用AVPlayer来播放加密的m3u8视频,代码如下: ``` AVPlayer *player = [AVPlayer playerWithPlayerItem:playerItem]; AVPlayerLayer *playerLayer = [AVPlayerLayer playerLayerWithPlayer:player]; playerLayer.frame = self.view.bounds; [self.view.layer addSublayer:playerLayer]; [player play]; ``` 通过以上步骤,就可以在iOS开发中通过AVPlayer来播放加密的m3u8视频。同时,还需要实现相关的代理方法来处理密钥请求和解密操作,以确保视频播放正常。 ### 回答2: iOS开发中,播放加密m3u8需要进行以下步骤。 首先,我们需要获取加密m3u8文件的url地址,并进行网络请求,获取到m3u8文件的内容。可以使用NSURLConnection或者NSURLSession来进行网络请求。 接下来,我们需要解析m3u8文件的内容,找到其中的加密信息。一般来说,加密信息是包含在EXT-X-KEY标签中的。可以使用正则表达式或者解析库来提取加密信息。 获取到加密信息之后,我们需要下载加密的密钥(key文件)。可以使用NSURLSession来进行密钥的网络请求,并将密钥保存到本地。 接着,我们需要将下载的加密的密钥设置到AVAssetResourceLoaderDelegate的代理方法中。通过实现AVAssetResourceLoaderDelegate的方法,我们可以对资源的请求进行拦截,并替换成解密后的数据。在这个方法中,我们需要解密每个ts文件的内容,然后将解密后的数据返回给播放器进行播放。 最后,我们将解密后的数据传递给AVPlayer,用AVPlayer来进行播放。我们可以使用AVPlayerItem和AVPlayer来创建一个播放器,然后将解密后的数据设置给AVPlayerItem,最后将AVPlayerItem设置给AVPlayer。 综上所述,播放加密m3u8文件需要进行加密信息解析、密钥下载和解密处理等步骤。通过以上步骤,我们可以在iOS开发中实现播放加密m3u8文件的功能。 ### 回答3: iOS开发中要播放加密的m3u8文件,可以借助AVFoundation框架来实现。以下是一个简单的实现步骤: 首先,需要将m3u8文件下载到本地,并解析得到m3u8文件中的密钥以及ts片段的URL。 然后,借助AVAssetResourceLoaderDelegate协议,自定义一个资源加载器,用于处理加密文件的逻辑。在该协议的代理方法中,先判断是否需要加载加密密钥,并根据m3u8文件中的密钥信息,将其加载到AVAssetResourceLoader中。 接下来,当AVPlayer需要加载排队的媒体数据时,资源加载器会被调用。在这个代理方法中,我们需要处理对ts片段的加载请求,通过AVAssetResourceLoadingDataRequest的requestRange属性可以得到要加载的范围,然后根据范围从本地缓存中读取对应的加密ts片段数据进行解密,再通过AVAssetResourceLoadingDataRequest的respond方法回传给AVPlayer。 最后,将AVPlayer与AVPlayerLayer绑定,通过AVPlayer的play方法来开始播放加密的m3u8文件。 需要注意的是,由于涉及到解密操作,所以在自定义资源加载器中,我们需要实现对ts片段数据的解密逻辑,通常使用AES等加密算法进行解密。 综上所述,通过借助AVFoundation框架的AVAssetResourceLoaderDelegate协议和自定义资源加载器,我们可以实现在iOS开发中播放加密的m3u8文件。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值