php加密解密函数authcode的用法详细解析


Posted in PHP onOctober 28, 2013

核心提示:康盛的 authcode 函数可以说对中国的PHP界作出了重大贡献。包括康盛自己的产品,以及大部分中国使用PHP的公司都用这个函数进行加密,authcode 是使用异或运算进行加密和解密。
 
康盛的 authcode 函数可以说对中国的PHP界作出了重大贡献。包括康盛自己的产品,以及大部分中国使用PHP的公司都用这个函数进行加密,authcode 是使用异或运算进行加密和解密。
  
原理如下,假如:
 
加密
 
明文:1010 1001
 
密匙:1110 0011
 
密文:0100 1010
 
得出密文0100 1010,解密之需和密匙异或下就可以了
 
解密
 
密文:0100 1010
 
密匙:1110 0011
 
明文:1010 1001
 
并没有什么高深的算法,密匙重要性很高,所以,关键在于怎么生成密匙。
 
那我们一起看下康盛的authcode怎么做的吧

// 参数解释  
 // $string: 明文 或 密文  
 // $operation:DECODE表示解密,其它表示加密  
 // $key: 密匙  
 // $expiry:密文有效期  
 function authcode($string, $operation = 'DECODE', $key = '', $expiry = 0) {  
   // 动态密匙长度,相同的明文会生成不同密文就是依靠动态密匙  
   $ckey_length = 4;  
     
   // 密匙  
   $key = md5($key ? $key : $GLOBALS['discuz_auth_key']);  
     
   // 密匙a会参与加解密  
   $keya = md5(substr($key, 0, 16));  
   // 密匙b会用来做数据完整性验证  
   $keyb = md5(substr($key, 16, 16));  
   // 密匙c用于变化生成的密文  
   $keyc = $ckey_length ? ($operation == 'DECODE' ? substr($string, 0, $ckey_length): 
substr(md5(microtime()), -$ckey_length)) : '';  
   // 参与运算的密匙  
   $cryptkey = $keya.md5($keya.$keyc);  
   $key_length = strlen($cryptkey);  
   // 明文,前10位用来保存时间戳,解密时验证数据有效性,10到26位用来保存$keyb(密匙b),解密时会通过这个密匙验证数据完整性  
   // 如果是解码的话,会从第$ckey_length位开始,因为密文前$ckey_length位保存 动态密匙,以保证解密正确  
   $string = $operation == 'DECODE' ? base64_decode(substr($string, $ckey_length)) : 
sprintf('%010d', $expiry ? $expiry + time() : 0).substr(md5($string.$keyb), 0, 16).$string;  
   $string_length = strlen($string);  
   $result = '';  
   $box = range(0, 255);  
   $rndkey = array();  
   // 产生密匙簿  
   for($i = 0; $i <= 255; $i++) {  
     $rndkey[$i] = ord($cryptkey[$i % $key_length]);  
   }  
   // 用固定的算法,打乱密匙簿,增加随机性,好像很复杂,实际上对并不会增加密文的强度  
   for($j = $i = 0; $i < 256; $i++) {  
     $j = ($j + $box[$i] + $rndkey[$i]) % 256;  
     $tmp = $box[$i];  
     $box[$i] = $box[$j];  
     $box[$j] = $tmp;  
   }  
   // 核心加解密部分  
   for($a = $j = $i = 0; $i < $string_length; $i++) {  
     $a = ($a + 1) % 256;  
     $j = ($j + $box[$a]) % 256;  
     $tmp = $box[$a];  
     $box[$a] = $box[$j];  
     $box[$j] = $tmp;  
     // 从密匙簿得出密匙进行异或,再转成字符  
     $result .= chr(ord($string[$i]) ^ ($box[($box[$a] + $box[$j]) % 256]));  
   }  
   if($operation == 'DECODE') {  
     // substr($result, 0, 10) == 0 验证数据有效性  
     // substr($result, 0, 10) - time() > 0 验证数据有效性  
     // substr($result, 10, 16) == substr(md5(substr($result, 26).$keyb), 0, 16) 验证数据完整性  
     // 验证数据有效性,请看未加密明文的格式  
     if((substr($result, 0, 10) == 0 || substr($result, 0, 10) - time() > 0) && 
substr($result, 10, 16) == substr(md5(substr($result, 26).$keyb), 0, 16)) {  
       return substr($result, 26);  
     } else {  
       return '';  
     }  
   } else {  
     // 把动态密匙保存在密文里,这也是为什么同样的明文,生产不同密文后能解密的原因  
     // 因为加密后的密文可能是一些特殊字符,复制过程可能会丢失,所以用base64编码  
     return $keyc.str_replace('=', '', base64_encode($result));  
   }  
 }
PHP 相关文章推荐
文件系统基本操作类
Nov 23 PHP
php radio 单选框获取与保持值的实现代码
May 15 PHP
php 如何获取数组第一个值
Aug 06 PHP
php设置允许大文件上传示例代码
Mar 10 PHP
php基于base64解码图片与加密图片还原实例
Nov 03 PHP
PHP移动文件指针ftell()、fseek()、rewind()函数总结
Nov 18 PHP
php实现用于删除整个目录的递归函数
Mar 16 PHP
php5.4传引用时报错问题分析
Jan 22 PHP
PHP简单判断字符串是否包含另一个字符串的方法
Mar 25 PHP
php获取网站根目录物理路径的几种方法(推荐)
Mar 04 PHP
微信公众平台开发教程④ ThinkPHP框架下微信支付功能图文详解
Apr 10 PHP
PHP实现简单日历类编写
Aug 28 PHP
php 模拟post_验证页面的返回状态(实例讲解)
Oct 28 #PHP
php操作mysqli(示例代码)
Oct 28 #PHP
php session_start()出错原因分析及解决方法
Oct 28 #PHP
php 强制下载文件实现代码
Oct 28 #PHP
php获取qq用户昵称和在线状态(实例分析)
Oct 27 #PHP
php获取数组长度的方法(有实例)
Oct 27 #PHP
使用淘宝IP库获取用户ip地理位置
Oct 27 #PHP
You might like
全国FM电台频率大全 - 30 宁夏回族自治区
2020/03/11 无线电
php抓即时股票信息
2006/10/09 PHP
PHP新手上路(八)
2006/10/09 PHP
PHP中空字符串介绍0、null、empty和false之间的关系
2012/09/25 PHP
PHP5.5在windows安装使用memcached服务端的方法
2014/04/16 PHP
ThinkPHP中关联查询实例
2014/12/02 PHP
PHP自毁程序(慎用)
2015/07/09 PHP
laravel 去掉index.php伪静态的操作方法
2019/10/12 PHP
让iframe框架网页在任何浏览器下自动伸缩
2006/08/18 Javascript
Javascript 判断 object 的特定类转载
2007/02/01 Javascript
Jquery Ajax方法传值到action的方法
2014/05/11 Javascript
jQuery实现连续动画效果实例分析
2015/10/09 Javascript
jQuery form插件之ajaxForm()和ajaxSubmit()的可选参数项对象
2016/01/23 Javascript
原生JS实现几个常用DOM操作API实例
2017/01/19 Javascript
详解Vue中过度动画效果应用
2017/05/25 Javascript
在React中如何优雅的处理事件响应详解
2017/07/24 Javascript
微信小程序授权获取用户详细信息openid的实例详解
2017/09/20 Javascript
基于jsbarcode 生成条形码并将生成的条码保存至本地+源码
2020/04/27 Javascript
JavaScript array常用方法代码实例详解
2020/09/02 Javascript
Vue.extend 登录注册模态框的实现
2020/12/29 Vue.js
Python中的测试模块unittest和doctest的使用教程
2015/04/14 Python
离线安装Pyecharts的步骤以及依赖包流程
2020/04/23 Python
python 实现倒排索引的方法
2018/12/25 Python
Python经典五人分鱼实例讲解
2021/01/04 Python
html5将图片转换成base64的实例代码
2016/09/21 HTML / CSS
金融事务专业求职信
2014/04/25 职场文书
2014年党支部学习材料
2014/05/19 职场文书
海洋科学专业求职信
2014/08/10 职场文书
领导班子整改方案
2014/10/25 职场文书
地道战观后感400字
2015/06/04 职场文书
发票退票证明
2015/06/24 职场文书
2015年乡镇组织委员工作总结
2015/10/23 职场文书
2019年度行政文员工作计划范本!
2019/07/04 职场文书
2019年妇科护士的自我鉴定(3篇)
2019/09/26 职场文书
JS数组方法some、every和find的使用详情
2021/10/05 Javascript
python基础之错误和异常处理
2021/10/24 Python