⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 radlogin.c

📁 DES算法的C源码 benchmark.c des.c descalc.c descert.c descycle.c getopt.c getpass.c main.c misc.c
💻 C
字号:
/*
 * Secure packet radio login command. The system first prompts for the
 * user's name. It then generates and sends a unique "challenge" (a 64-bit
 * hexadecimal integer) based on the time of day. The user encrypts
 * this value using the Data Encryption Standard and his private key and
 * type it back to the system. The system also encrypts the challenge
 * with the user's key and compares the two. If they match, he's in.
 *
 * 18 December 1986 Phil Karn, KA9Q
 *
 * mods:
 *   870318 Bdale, N3EUA     Add code to run user's .login commands.
 *   870317 Bdale, N3EUA     Hacked to remove putenv() by calling execle()
 *                           instead of execl().
 */
#include <stdio.h>
#include <strings.h>
#include <pwd.h>
#include <utmp.h>
#define	KEYFILE	"/etc/rkeys"	/* This file must be read-protected */
main(argc,argv)
int argc;
char *argv[];
{
	struct passwd *pp,*getpwnam();
	unsigned long t;
	FILE *fp;
	char name[64];
	char key[8];
	char work[8];
	char answer[8];
	char fbuf[64];
	char ibuf[64];
	char home[64];
	char login[64];
	char shell[64];
	char user[64];
	char *keyp;
	char *cp,*tty,*ttyname();
	int i,ikey[8];
	struct utmp utmp;
	char *ep[5];               /* we'll build an environment here */

	if((fp = fopen(KEYFILE,"r")) == NULL){
		printf("Can't open key file\n");
		exit(1);
	}
	/* Get user's name and look it up in the database */
	printf("Enter login name: ");
	fgets(ibuf,sizeof(ibuf),stdin);
	if((cp = index(ibuf,'\n')) != NULL)
		*cp = '\0';
	strncpy(name,ibuf,sizeof(name));
	for(;;){
		fgets(fbuf,sizeof(fbuf),fp);
		if(feof(fp)){
			printf("No key for login name\n");
			exit(2);
		}
		if((cp = index(fbuf,'\n')) != NULL)
			*cp = '\0';
		if(strncmp(name,fbuf,strlen(name)) == 0)
			break;
	}
	fclose(fp);
	/* Find the user's DES key */
	if((keyp = index(fbuf,' ')) == NULL){
		printf("Missing key field\n");
		exit(3);
	}
	keyp++;
	/* Initialize DES with the user's key */
	sscanf(keyp,"%2x%2x%2x%2x%2x%2x%2x%2x",
	 &ikey[0], &ikey[1], &ikey[2], &ikey[3], &ikey[4], &ikey[5],
	 &ikey[6], &ikey[7]);

	for(i=0;i<8;i++)
		key[i] = ikey[i];

	desinit(0);
	setkey(key);

	/* Generate and send the challenge */
	time(&t);
	printf("Challenge: %016x\n",t);

	/* Encrypt it locally... */
	for(i=0;i<4;i++)
		work[i] = 0;
	work[4] = t >> 24;
	work[5] = t >> 16;
	work[6] = t >> 8;
	work[7] = t;
	endes(work);
	
	/* ...and see if the user can do the same */
	printf("Response:  ");
	for(i=0;i<8;i++){
		scanf("%2x",&t);
		answer[i] = t;
	}
	printf("\n");     /* I like it better with a blank line here - bdale */
	/* Compare the ciphertexts. If they match, he's in */
	for(i=0; i < 8; i++){
		if(work[i] != answer[i]){
			printf("Wrong response\n");
			exit(4);
		}
	}
	if((pp = getpwnam(name)) == NULL){
		printf("login name \"%s\" not in /etc/passwd\n",name);
		exit(4);
	}
	if((fp = fopen(UTMP_FILE,"r+")) == NULL){
		printf("can't open utmp\n");
		exit(4);
	}
	tty = ttyname(0);
	if((cp = rindex(tty,'/')) != NULL)
		tty = cp + 1;
	while(fread((char *)&utmp,sizeof(struct utmp),1,fp),!feof(fp)){
		if(strncmp(utmp.ut_line,tty,8) == 0){
			strncpy(utmp.ut_name,name,8);
			fseek(fp,(long)-sizeof(struct utmp),1);
			fwrite((char *)&utmp,sizeof(struct utmp),1,fp);
			break;
		}
	}
	fclose(fp);
	chdir(pp->pw_dir);
	setregid(pp->pw_gid,pp->pw_gid);
	setreuid(pp->pw_uid,pp->pw_uid);
	if(pp->pw_shell == NULL || *pp->pw_shell == '\0')
		pp->pw_shell = "/bin/ksh";
	sprintf(home,"HOME=%s",pp->pw_dir);
	sprintf(shell,"SHELL=%s",pp->pw_shell);
	sprintf(user,"USER=%s",name);
	sprintf(login,"%s/.login",pp->pw_dir);
	ep[0] = home;
	ep[1] = shell;
	ep[2] = user;
	ep[3] = (char *) NULL;
	execle(pp->pw_shell,"-",0,ep);
	printf("Exec failed\n");
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -