AES/CBC/PKCS5Padding加解密

33 篇文章 0 订阅

aes/cbc/pkcs5padding/128加解密示例:

<?php
class AesEncrypt{
    //自定义key
    protected $key;    

    //cipher算法类型
    protected $cipher  = 'rijndael-128';

    //mode模型
    protected $mode = 'cbc';

    public function __construct($key){
        $this->key = $key;
    }

    //aes加密
    public function aesEncrypt($data){
        //随机生成16位iv,初始向量
        $iv = self::aesRandom(16,'1234567890abcdefghijklmnopqrstuvwxyz');

        //pkcs5padding
        //获取加密算法分组大小
        $block = mcrypt_get_block_size($this->cipher, $this->mode);

        //方式一  计算补码长度,chr-返回相对应于 ascii 所指定的单个字符
        //$pad = chr($block - (strlen($data)%$block));
        //str_pad-使用另一个字符串填充字符串为指定长度
        //$pad = str_pad($data, ceil(strlen($data)/16.0)*16, $pad);

        //方式二  获取补码长度
        $pad = $block-(strlen($data)%$block);
        //str_repeat-重复一个字符串chr($pad),$pad次
        $pad = $data.str_repeat(chr($pad), $pad);

        //mcrypt_module_open - 打开算法和模式对应的模块
        $td = mcrypt_module_open($this->cipher, '', $this->mode, '');
        //mcrypt_generic_init-初始化加密所需的缓冲区
        mcrypt_generic_init($td , $this->key , $iv);
        //mcrypt_generic- 加密数据,使用前必须调用mcrypt_generic_init
        $encrypt = mcrypt_generic($td, $pad);
        //mcrypt_generic_deinit — 对加密模块进行清理工作,它会清理缓冲区,但是并不关闭模块
        mcrypt_generic_deinit($td);
        //mcrypt_module_close — 关闭加密模块
        mcrypt_module_close($td);

        //iv拼密串之后base64
        return base64_encode($iv.$encrypt);
    }

    //aes解密
    public function aesDecrypt($data){
        $data = base64_decode($data) ;//base64
        //前16位为iv
        $iv = substr($data, 0, 16); 
        //16位后未密串
        $data = substr($data, 16);
        //mcrypt_module_open - 打开算法和模式对应的模块
        $td = mcrypt_module_open($this->cipher, '', $this->mode, '');
        //mcrypt_generic_init-初始化加密所需的缓冲区
        mcrypt_generic_init($td , $this->key , $iv);
        //mdecrypt_generic — 解密数据,使用前必须调用mcrypt_generic_init
        $decrypt = mdecrypt_generic($td, $data);
        //mcrypt_generic_deinit — 对加密模块进行清理工作
        mcrypt_generic_deinit($td);
        //mcrypt_module_close — 关闭加密模块
        mcrypt_module_close($td);

        //Remove the padding
        //ord-返回字符的 ASCII 码值
        $pad = ord($decrypt[($len = strlen($decrypt))-1]);
        //返回补码开始索引位置
        $beforePad = strlen($decrypt) - $pad;
        //判断是否补码过
        $decrypt = substr($decrypt, $beforePad) == str_repeat(substr($decrypt, -1), $pad) ? substr($decrypt, 0, $len - $pad) : $decrypt;

        return $decrypt;
    }

    //随机生成16位iv
    public function aesRandom($length, $chars = 'ABCDEFGHJKLMNPQRSTUVWXYZ23456789')
    {
        $hash = '';
        $max = strlen($chars) - 1;
        for($i = 0; $i < $length; $i++)
        {
        $hash .= $chars[mt_rand(0, $max)];
        }
        return $hash;
    }

    //修改cipher
    public function setCipher($cipher){
        $this->cipher = $cipher;
    }

    //修改mode
    public function setMode($mode){
        $this->mode = $mode;
    }

}
//初始化类
$aes = new aesEncrypt('I4fe6xmsndfrGK4g');
$str = 'xiaoming';
//加密
$res = $aes->aesEncrypt($str);
echo $res."<br/>";
//解密
$res2 = $aes->aesDecrypt($res);
echo $res2."<br/>";

$resstr = 'rTnAY7a6vnHkUqfICRxgtiXBYXcP2f+A+zxy4ONsg3w=';
$res3 = $aes->aesDecrypt($resstr);
echo $res3."<br/>";

示例结果:

aesEncrypt: MWY5bzBvOXdidWUxMnU4N/f8ANDZUw3cSza+QCnIquI=
aesDecrypt: xiaoming
aesDecrypt: xiaoming

url后带加密参数获取问题
示例:
http://test.local?token=rTnAY7a6vnHkUqfICRxgtiXBYXcP2f+A+zxy4ONsg3w=
获取以上url后所带参数token
浏览器会将一些特殊字符自动转码,所以获取时需注意转换
1)urldecode
urldecode后将+号转换成空格,需要替换

$token = Input::get('token');
$token = urldecode($token);
echo $token.'<br>';
$token = str_replace(' ','+',$token);
echo $token;

示例结果:

rTnAY7a6vnHkUqfICRxgtiXBYXcP2f A zxy4ONsg3w=
rTnAY7a6vnHkUqfICRxgtiXBYXcP2f+A+zxy4ONsg3w=

2)rawurldecode

$token = Input::get('token');
echo rawurldecode($str);

示例结果:

rTnAY7a6vnHkUqfICRxgtiXBYXcP2f+A+zxy4ONsg3w=
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值