Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
#include <u.h>
2
#include <libc.h>
3
#include <bio.h>
4
#include "authcmdlib.h"
5
 
6
/*
7
 * compute the key verification checksum
8
 */
9
void
10
checksum(char key[], char csum[]) {
11
	uchar buf[8];
12
 
13
	memset(buf, 0, 8);
14
	encrypt(key, buf, 8);
15
	sprint(csum, "C %.2ux%.2ux%.2ux%.2ux", buf[0], buf[1], buf[2], buf[3]);
16
}
17
 
18
/*
19
 * compute the proper response.  We encrypt the ascii of
20
 * challenge number, with trailing binary zero fill.
21
 * This process was derived empirically.
22
 * this was copied from inet's guard.
23
 */
24
char *
25
netresp(char *key, long chal, char *answer)
26
{
27
	uchar buf[8];
28
 
29
	memset(buf, 0, 8);
30
	snprint((char *)buf, sizeof buf, "%lud", chal);
31
	if(encrypt(key, buf, 8) < 0)
32
		error("can't encrypt response");
33
	chal = (buf[0]<<24)+(buf[1]<<16)+(buf[2]<<8)+buf[3];
34
	sprint(answer, "%.8lux", chal);
35
 
36
	return answer;
37
}
38
 
39
char *
40
netdecimal(char *answer)
41
{
42
	int i;
43
 
44
	for(i = 0; answer[i]; i++)
45
		switch(answer[i]){
46
		case 'a': case 'b': case 'c':
47
			answer[i] = '2';
48
			break;
49
		case 'd': case 'e': case 'f':
50
			answer[i] = '3';
51
			break;
52
		}
53
	return answer;
54
}
55
 
56
int
57
netcheck(void *key, long chal, char *response)
58
{
59
	char answer[32], *p;
60
	int i;
61
 
62
	if(smartcheck(key, chal, response))
63
		return 1;
64
 
65
	if(p = strchr(response, '\n'))
66
		*p = '\0';
67
	netresp(key, chal, answer);
68
 
69
	/*
70
	 * check for hex response -- securenet mode 1 or 5
71
	 */
72
	for(i = 0; response[i]; i++)
73
		if(response[i] >= 'A' && response[i] <= 'Z')
74
			response[i] -= 'A' - 'a';
75
	if(strcmp(answer, response) == 0)
76
		return 1;
77
 
78
	/*
79
	 * check for decimal response -- securenet mode 0 or 4
80
	 */
81
	return strcmp(netdecimal(answer), response) == 0;
82
}
83
 
84
int
85
smartcheck(void *key, long chal, char *response)
86
{
87
	uchar buf[2*8];
88
	int i, c, cslo, cshi;
89
 
90
	snprint((char*)buf, sizeof buf, "%lud        ", chal);
91
	cslo = 0x52;
92
	cshi = cslo;
93
	for(i = 0; i < 8; i++){
94
		c = buf[i];
95
		if(c >= '0' && c <= '9')
96
			c -= '0';
97
		cslo += c;
98
		if(cslo > 0xff)
99
			cslo -= 0xff;
100
		cshi += cslo;
101
		if(cshi > 0xff)
102
			cshi -= 0xff;
103
		buf[i] = c | (cshi & 0xf0);
104
	}
105
 
106
	encrypt(key, buf, 8);
107
	for(i = 0; i < 8; i++)
108
		if(response[i] != buf[i] % 10 + '0')
109
			return 0;
110
	return 1;
111
}