Commit | Line | Data |
---|---|---|
37941236 | 1 | /* -*-c-*- |
37941236 | 2 | * |
3 | * Cryptographic challenges | |
4 | * | |
5 | * (c) 2005 Straylight/Edgeware | |
6 | */ | |
7 | ||
e04c2d50 | 8 | /*----- Licensing notice --------------------------------------------------* |
37941236 | 9 | * |
10 | * This file is part of Trivial IP Encryption (TrIPE). | |
11 | * | |
12 | * TrIPE is free software; you can redistribute it and/or modify | |
13 | * it under the terms of the GNU General Public License as published by | |
14 | * the Free Software Foundation; either version 2 of the License, or | |
15 | * (at your option) any later version. | |
e04c2d50 | 16 | * |
37941236 | 17 | * TrIPE is distributed in the hope that it will be useful, |
18 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | |
19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
20 | * GNU General Public License for more details. | |
e04c2d50 | 21 | * |
37941236 | 22 | * You should have received a copy of the GNU General Public License |
23 | * along with TrIPE; if not, write to the Free Software Foundation, | |
24 | * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. | |
25 | */ | |
26 | ||
27 | /*----- Header files ------------------------------------------------------*/ | |
28 | ||
29 | #include "tripe.h" | |
30 | ||
31 | /*----- Static variables --------------------------------------------------*/ | |
32 | ||
33 | static gmac *mac; | |
34 | static uint32 oseq; | |
35 | static seqwin iseq; | |
36 | ||
37 | /*----- Main code ---------------------------------------------------------*/ | |
38 | ||
39 | /* --- @c_genkey@ --- * | |
40 | * | |
41 | * Arguments: --- | |
42 | * | |
43 | * Returns: --- | |
44 | * | |
45 | * Use: Generates a new challenge key. | |
46 | */ | |
47 | ||
48 | static void c_genkey(void) | |
49 | { | |
50 | if (mac && GM_CLASS(mac) == algs.m && oseq < 0x07ffffff) return; | |
51 | if (mac) GM_DESTROY(mac); | |
52 | assert(algs.mksz < sizeof(buf_t)); | |
53 | rand_get(RAND_GLOBAL, buf_t, algs.mksz); | |
54 | mac = GM_KEY(algs.m, buf_t, algs.mksz); | |
55 | oseq = 0; | |
56 | seq_reset(&iseq); | |
57 | IF_TRACING(T_CHAL, { | |
58 | trace(T_CHAL, "chal: generated new challenge key"); | |
59 | trace_block(T_CRYPTO, "chal: new key", buf_t, algs.mksz); | |
60 | }) | |
61 | } | |
62 | ||
63 | /* --- @c_new@ --- * | |
64 | * | |
65 | * Arguments: @buf *b@ = where to put the challenge | |
66 | * | |
67 | * Returns: Zero if OK, nonzero on error. | |
68 | * | |
69 | * Use: Issues a new challenge. | |
70 | */ | |
71 | ||
72 | int c_new(buf *b) | |
73 | { | |
74 | octet *p; | |
75 | ghash *h; | |
76 | ||
77 | c_genkey(); | |
78 | p = BCUR(b); | |
79 | if (buf_putu32(b, oseq++)) return (-1); | |
80 | h = GM_INIT(mac); | |
81 | GH_HASH(h, p, BCUR(b) - p); | |
82 | buf_put(b, GH_DONE(h, 0), algs.tagsz); | |
83 | GH_DESTROY(h); | |
84 | if (BBAD(b)) return (-1); | |
85 | IF_TRACING(T_CHAL, { | |
86 | trace(T_CHAL, "chal: issuing challenge %lu", (unsigned long)(oseq - 1)); | |
87 | trace_block(T_CRYPTO, "chal: challenge block", p, BCUR(b) - p); | |
88 | }) | |
89 | return (0); | |
90 | } | |
91 | ||
92 | /* --- @c_check@ --- * | |
93 | * | |
94 | * Arguments: @buf *b@ = where to find the challenge | |
95 | * | |
96 | * Returns: Zero if OK, nonzero if it didn't work. | |
97 | * | |
98 | * Use: Checks a challenge. On failure, the buffer is broken. | |
99 | */ | |
100 | ||
101 | int c_check(buf *b) | |
102 | { | |
103 | const octet *p; | |
104 | size_t sz = 4 + algs.tagsz; | |
105 | uint32 seq; | |
106 | ghash *h; | |
107 | int ok; | |
108 | ||
109 | if ((p = buf_get(b, sz)) == 0) { | |
f43df819 | 110 | a_warn("CHAL", "invalid-challenge", A_END); |
37941236 | 111 | goto fail; |
112 | } | |
113 | IF_TRACING(T_CHAL, trace_block(T_CRYPTO, "chal: check challenge", p, sz); ) | |
114 | if (!mac) { | |
f43df819 | 115 | a_warn("CHAL", "impossible-challenge", A_END); |
37941236 | 116 | goto fail; |
117 | } | |
118 | h = GM_INIT(mac); | |
119 | GH_HASH(h, p, 4); | |
120 | ok = (memcmp(GH_DONE(h, 0), p + 4, algs.tagsz) == 0); | |
121 | GH_DESTROY(h); | |
122 | if (!ok) { | |
f43df819 | 123 | a_warn("CHAL", "incorrect-tag", A_END); |
37941236 | 124 | goto fail; |
125 | } | |
126 | seq = LOAD32(p); | |
f43df819 MW |
127 | if (seq_check(&iseq, LOAD32(p), "CHAL")) |
128 | goto fail; | |
37941236 | 129 | T( trace(T_CHAL, "chal: checked challenge %lu", (unsigned long)seq); ) |
130 | return (0); | |
131 | ||
132 | fail: | |
133 | buf_break(b); | |
134 | return (-1); | |
135 | } | |
136 | ||
137 | /*----- That's all, folks -------------------------------------------------*/ |