免费教程_免费网赚教程_破解版软件-寂涯网络学习基地

当前位置: 主页 > 系统综合 > linux > Linux PAM 模块建立“智能卡”登录(2)

Linux PAM 模块建立“智能卡”登录(2)

时间:2011-11-09 12:34来源:未知 整理:寂涯网络 点击:


  具体的用法、约定有很多,不在这里解释了,可以 man 一下相应的函数或者看看 pam
的文档。
总体设计

  认证过程与标准的 UNIX 认证差不多,只不过密码是存储在卡上的随机数,不是通过键
盘输入的就是了。
  首先是认证标记:
 typedef struct {
    int magic;      /* 这里是'CARD',用来确认是不是一个有效的标记 */
    int magic1;     /* 这里也是'CARD',但是如果有 PIN 的话,这个标记会一起被
加密 */
    int id;   /* 一个随机数,只是个记号 */         
    char token[56]; /* 56个字节的随机数,充当密码使用 */
} token;

  如果设定了 PIN的话,magic1、id和token[56]这三个域都要使用AES 加密存储,密钥
就是 PIN的 MD5值。
     magic1、id和token[56]这几个加起来正好是64 个字节,也就是 AES blocksize的4
倍,这样就可以不要 padding 了;同时也是 SHA512 的输出的大小(下文会说到)。magic1
用来判断解密是否正确,PIN 不正确的话这里就不会是'CARD'。即使使用错误的PIN解密出
来的 magic1是'CARD',也不会通过接下来的测试。
  存储在电脑上的"shadow"文件保存在/etc/cards,对每一个用户只储存这些项:用户名,
对应的认证标记种的 id,认证标记的 hash。hash 的算法作者采用的是重复 20000 次的
SHA512,hash的内容就是上一段说的那64个字节,这样可以省去第一次的特殊处理。
  因为 SIM 卡中每一条电话号码记录是28 字节,每一条短信记录是 176 字节,所以认证
标记只能放到短信文件里(下文会说到)。
代码编写,PAM部分
 #include <stdarg.h>
#include <sys/types.h>
#include <locale.h>
#include <libintl.h>
#define _ gettext
#define PAM_SM_AUTH /* 要求有 pam_sm_authenticate的定义 */
#include <security/_pam_macros.h>
#include <security/pam_modules.h>
#include <security/pam_ext.h>
#include "common.h" /* 各种辅助函数, 会有相应的解释 */
#include "card.h" /* 智能卡的读写函数 */
#include "settings.h"
#define msg_error(args...) \
    if(!(flags & PAM_SILENT)) { \
        pam_prompt(pamh, PAM_ERROR_MSG, NULL, args); \
    }
#define msg_info(args...) \
    if(!(flags & PAM_SILENT)) { \

        pam_prompt(pamh, PAM_TEXT_INFO, NULL, args); \
    }
PAM_EXTERN int pam_sm_authenticate(pam_handle_t *pamh, int flags, int argc,
const char **argv)
/*
这个就是认证的函数了,他的返回值决定了认证是成功还是失败
pamh: 应用程序由pam_start函数获得的句柄
flags: 标志位 具体请看PAM 的文档
argc/argv: 在配置文件中指定的参数
*/
{
    int retval = PAM_AUTHINFO_UNAVAIL; /* 返回代码 */
    token tok, *ptok; /* 认证标记 */
    userinfo *uih = NULL, *u; /* 机器上存储的"shadow"文件 */ 
    const char *desired_user = NULL, *rhost = NULL;
char hash[64];
setlocale(LC_ALL, ""); /* 这3 句是 L10N 相关的 */
    bindtextdomain("pam_iccard", ".");
    textdomain("pam_iccard");

    parse_file("/etc/pam_iccard.conf", 0);
    parse_args(argc, (char**)argv, 1);
    if(on("silent")) {
       flags |= PAM_SILENT;
    }
    if(PAM_SUCCESS == pam_get_item(pamh, PAM_RHOST, (const void **)&rhost)) {

  if(rhost && strlen(rhost)) {
    /* 不支持远程登录:
    远程登录的时候(比如 ssh),认证的结果取决于那台机器上是否有智能
卡,这很显然不合理 */
            msg_error(_("pam_iccard doesn't support remote login."));
            retval = PAM_AUTH_ERR;
            goto last;

本页地址 http://www.jybase.net/linux/20111109591.html

百度搜索更多

谷歌搜索更多

顶一下
(1)
100%
踩一下
(0)
0%
------分隔线----------------------------

评价:
昵称: 验证码:点击我更换图片
推荐内容
赞助商
赞助商


关于本站免责声明视频更新google百度地图视频地图RRS订阅

如有什么问题请在本站留言,或发邮件到 hxt167#foxmail.com