CHAP算法C++实现
CHAP是一种挑战响应式协议。
CHAP全称为:Challenge Handshake Authentication Protocol。
CHAP密码 = 一个字节的标识符 + MD5(一个字节的标识符+明文密码+挑战码)

注:+号只是连接符,两个串之间没有任何多余字符;
如:
挑战码 = cce964fe4807b30ddcda0903413d1a3a560710a2
一个字节的标识符 = 0x97
明文密码 = 20151013
CHAP密码 = "97" + MD5(0x97 + 20151013 + fromHex(cce964fe4807b30ddcda0903413d1a3a560710a2))
CHAP密码 = 9721e6dda93ed253cfdcbc20bab959afed
即调用如下函数时,参数如下:
string reqChallenge = "cce964fe4807b30ddcda0903413d1a3a560710a2";
string challange = fromHex(reqChallenge.c_str(), reqChallenge.length());
string ChapPasswd;
CHAPPasswdXor("20151013", 0x97, challange, ChapPasswd);
如下是一个CHAP协议的实现算法:
#include <string>
#include "md5.h" #define RAD_PASSWORD_LEN 128
#define RAD_PSWDSEG_LEN 16
#define RAD_AUTHCATOR_LEN 16 std::string Hex(const char* cpSrcStr, int len, bool isUpper = false) {
if (cpSrcStr == NULL) {
return "";
}
std::string ret(len * 2, 0x00);
const char* hex = isUpper ? "0123456789ABCDEF" : "0123456789abcdef";
for (size_t i = 0; i < len; ++i) {
unsigned char v = static_cast<unsigned char>(cpSrcStr[i]);
ret[2*i] = hex[(v >> 4) & 0x0f];
ret[2*i+1] = hex[ v & 0x0f];
}
return ret;
} char asc_bcd(const char *aBcdStr) {
unsigned char digit; digit = (aBcdStr[0] >= 'a' ? ((aBcdStr[0]) - 'a')+10 : (aBcdStr[0] - '0'));
digit *= 16;
digit += (aBcdStr[1] >= 'a' ? ((aBcdStr[1]) - 'a')+10 : (aBcdStr[1] - '0'));
return digit;
} std::string fromHex(const char* from, size_t len) {
std::string ret(len / 2, 0x00);
for (size_t ii = 0; ii < len / 2; ii++)
ret[ii] = asc_bcd(from + ii * 2);
return ret;
} void MD5Calc(const unsigned char *input,
unsigned int inlen, unsigned char *output) {
MD5_CTX context;
MD5Init(&context);
MD5Update(&context, (unsigned char *)input, inlen);
MD5Final(output, &context);
} int CHAPPasswdXor(const char *aPasswd, unsigned char aIdentifier,
const std::string& aChallenge, std::string &aOutPasswd)
{
char localPwd[RAD_PASSWORD_LEN+1] = {0};
int pwLen = strlen(aPasswd); if (pwLen > RAD_PASSWORD_LEN) {
//LOG_INFO("%s:Password is too long.");
return -1;
} char *pwStr = localPwd;
*pwStr++ = aIdentifier;
strcpy(pwStr, aPasswd);
pwStr += pwLen;
// challenge is append if challenge is exist.
memcpy(pwStr, aChallenge.data(), aChallenge.length());
pwLen += aChallenge.length() + 1; // Encrypted.
char md5Output[RAD_AUTHCATOR_LEN+1] = {0};
MD5Calc((unsigned char *)localPwd, pwLen, (unsigned char *)md5Output); // get the CHAP password
pwStr = localPwd;
*pwStr++ = aIdentifier;
memcpy(pwStr, md5Output, RAD_AUTHCATOR_LEN);
aOutPasswd = Hex(localPwd, RAD_PSWDSEG_LEN+1);
return 0;
}
CHAP算法C++实现的更多相关文章
- PPP中的PAP和CHAP的区别
PAP PAP是简单认证,明文传送,客户端直接发送包含用户名/口令的认证请求,服务器端处理并回应. CHAP CHAP是加密认证,先由服务器端给客户端发送一个随机码 challenge,客户端根据 c ...
- CHAP认证(双向)
实验要求:掌握CHAP认证配置 拓扑如下: R1enable 进入特权模式configure terminal 进入全局模式hostname R1 设置主机名 interface s0/0/0 ...
- 路由器配置PPP协议 CHAP验证 PAP验证
路由器配置PPP协议 CHAP验证 PAP验证 来源 https://www.cnblogs.com/tcheng/p/5967485.html PAP是两次握手,明文传输用户密码进行认证:CHAP是 ...
- B树——算法导论(25)
B树 1. 简介 在之前我们学习了红黑树,今天再学习一种树--B树.它与红黑树有许多类似的地方,比如都是平衡搜索树,但它们在功能和结构上却有较大的差别. 从功能上看,B树是为磁盘或其他存储设备设计的, ...
- 分布式系列文章——Paxos算法原理与推导
Paxos算法在分布式领域具有非常重要的地位.但是Paxos算法有两个比较明显的缺点:1.难以理解 2.工程实现更难. 网上有很多讲解Paxos算法的文章,但是质量参差不齐.看了很多关于Paxos的资 ...
- 【Machine Learning】KNN算法虹膜图片识别
K-近邻算法虹膜图片识别实战 作者:白宁超 2017年1月3日18:26:33 摘要:随着机器学习和深度学习的热潮,各种图书层出不穷.然而多数是基础理论知识介绍,缺乏实现的深入理解.本系列文章是作者结 ...
- 红黑树——算法导论(15)
1. 什么是红黑树 (1) 简介 上一篇我们介绍了基本动态集合操作时间复杂度均为O(h)的二叉搜索树.但遗憾的是,只有当二叉搜索树高度较低时,这些集合操作才会较快:即当树的高度较高(甚至一种极 ...
- 散列表(hash table)——算法导论(13)
1. 引言 许多应用都需要动态集合结构,它至少需要支持Insert,search和delete字典操作.散列表(hash table)是实现字典操作的一种有效的数据结构. 2. 直接寻址表 在介绍散列 ...
- 虚拟dom与diff算法 分析
好文集合: 深入浅出React(四):虚拟DOM Diff算法解析 全面理解虚拟DOM,实现虚拟DOM
随机推荐
- c 开源代码
阅读优秀代码是提高开发人员修为的一种捷径……1. WebbenchWebbench是一个在linux下使用的非常简单的网站压测工具.它使用fork()模拟多个客户端同时访问我们设定的URL,测试网站在 ...
- iOS - Availability.h
>for 'dispatch' application inner to begin note `#include <Availability.h>` These macros ar ...
- HDU5671Matrix(矩阵行列交换)
有一个nn行mm列的矩阵(1 \leq n \leq 1000 ,1 \leq m \leq 1000 )(1≤n≤1000,1≤m≤1000),在这个矩阵上进行qq (1 \leq q \leq 1 ...
- ES6之模版字符串
ES6之模版字符串 最近在项目中使用了ES6的模版字符串,在这里加以总结. 1.之前我们也可以使用JavaScript输出模版字符串,通常是下面这样的: $("#result"). ...
- HTML之表格制作
如何制作一个表格? 如何制作一个表格呢? 观察如下代码: <!DOCTYPE html> <html lang="en"> <head> &l ...
- 未签名有元程序集 Unsigned Friend Assemblies
C#中的访问修饰符internal可以使类型在同程序集中可以被相互访问.但有时会有这样一个要求,我们希望一个程序集中的类型可以被外部的某些程序集访问,如果设置成public的话,就被所有的外部程序集访 ...
- GridView数据格式化
一.动态生成列的格式化 此种GridView中的列是动态生成的,格式化可以通过RowDataBound事件进行.如下边代码,对第十列的值进行格式化. protected void gvUserList ...
- IO多路复用及ThreadingTCPServer源码阅读
IO多路复用 socket模块是阻塞的,通过socket建立的服务端可以接收多个请求,但只能同时处理一个请求,其他请求都被阻塞.可以通过IO多路复用解决这个问题,socketserver内部使用的就是 ...
- Android学习笔记——MixLayout
该工程的功能是实现LinearLayout+TableLayout 以下代码是MainActivity.java中的代码 package com.example.mixlayout; import a ...
- string.capwords() 将每个单词首字母大写
string.capwords() 将每个单词首字母大写 代码: import string s = ' The quick brown fox jumped over the lazy dog. ' ...