1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
|
/*
* seal.c --- seal message
*
* $Source$
* $Author$
* $Header$
*
* Copyright 1991 by the Massachusetts Institute of Technology.
* All Rights Reserved.
*
* For copying and distribution information, please see the file
* <krb5/copyright.h>.
*
*/
#include <gssapi.h>
OM_uint32 gss_seal(minor_status, context, conf_req_flag, qop_req,
input_message_buffer, conf_state, output_message_buffer)
OM_uint32 *minor_status;
gss_ctx_id_t context;
int conf_req_flag;
int qop_req;
gss_buffer_t input_message_buffer;
int *conf_state;
gss_buffer_t output_message_buffer;
{
krb5_data inbuf, outbuf;
*minor_status = 0;
inbuf.length = input_message_buffer->length;
inbuf.data = input_message_buffer->value;
if (conf_req_flag) {
int priv_flags = 0;
int eblock_size;
char *i_vector;
if (context->flags & GSS_C_SEQUENCE_FLAG)
priv_flags = KRB5_PRIV_DOSEQUENCE|KRB5_PRIV_NOTIME;
/*
* Initialize the initial vector.
*/
eblock_size =
krb5_keytype_array[context->session_key->keytype]->
system->block_length;
if (!(i_vector=malloc(eblock_size))) {
return(GSS_S_FAILURE);
}
memset(i_vector, 0, eblock_size);
if (*minor_status = krb5_mk_priv(&inbuf, ETYPE_DES_CBC_CRC,
context->session_key,
&context->my_address,
&context->his_address,
context->my_seq_num,
priv_flags,
0, /* no rcache */
i_vector,
&outbuf))
return(GSS_S_FAILURE);
if (*minor_status = gss_make_token(minor_status,
GSS_API_KRB5_TYPE,
GSS_API_KRB5_PRIV,
outbuf.length,
outbuf.data,
output_message_buffer)) {
xfree(outbuf.data);
return(GSS_S_FAILURE);
}
if (conf_state)
*conf_state = 1;
if (context->flags & GSS_C_SEQUENCE_FLAG)
context->my_seq_num++;
return(GSS_S_COMPLETE);
} else {
int safe_flags = 0;
if (context->flags & GSS_C_SEQUENCE_FLAG)
safe_flags = KRB5_SAFE_DOSEQUENCE|KRB5_SAFE_NOTIME;
if (*minor_status = krb5_mk_safe(&inbuf,
CKSUMTYPE_RSA_MD4_DES,
context->session_key,
&context->my_address,
&context->his_address,
context->my_seq_num,
safe_flags,
0, /* no rcache */
&outbuf))
return(GSS_S_FAILURE);
if (*minor_status = gss_make_token(minor_status,
GSS_API_KRB5_TYPE,
GSS_API_KRB5_SAFE,
outbuf.length,
outbuf.data,
output_message_buffer)) {
xfree(outbuf.data);
return(GSS_S_FAILURE);
}
if (conf_state)
*conf_state = 0;
if (context->flags & GSS_C_SEQUENCE_FLAG)
context->my_seq_num++;
return(GSS_S_COMPLETE);
}
}
#ifdef notdef
/*
* XXX This is done inefficiently; the token in gss_sign does not need
* to include the text of the data, just a cryptographic checksum to
* act as a checksum. Nevertheless, this is a quick and dirty way to
* get it to work. When we fix this so that it works for real, we
* will need to let gss_verify accept both, and change the servers
* first.
*/
OM_uint32 gss_sign(minor_status, context, qop_req,
input_message_buffer, output_message_buffer)
OM_uint32 *minor_status;
gss_ctx_id_t context;
int qop_req;
gss_buffer_t input_message_buffer;
gss_buffer_t output_message_buffer;
{
return(gss_seal(minor_status, context, 0, qop_req,
input_message_buffer, NULL, output_message_buffer));
}
#endif
|