35
35
#define MAX_KEY_LENGTH 255
36
36
#define MAX_VALUE_NAME 16383
37
37
38
+ static int
39
+ get_user_root (struct agent_connection * con , HKEY * root ){
40
+ int r = 0 ;
41
+ if (ImpersonateNamedPipeClient (con -> connection ) == FALSE)
42
+ return ERROR_INTERNAL_ERROR ;
43
+
44
+ r = RegOpenCurrentUser (KEY_ALL_ACCESS , root );
45
+
46
+ RevertToSelf ();
47
+ return r ;
48
+ }
49
+
38
50
int
39
- process_add_identity (struct sshbuf * request , struct sshbuf * response , HANDLE client ) {
51
+ process_add_identity (struct sshbuf * request , struct sshbuf * response , struct agent_connection * con ) {
40
52
struct sshkey * key = NULL ;
41
53
int r = 0 , r1 = 0 , blob_len ;
42
54
size_t comment_len , pubkey_blob_len ;
43
55
u_char * pubkey_blob = NULL ;
44
- char * thumbprint = NULL , * blob , * comment ;
45
- HKEY reg = 0 , sub = 0 ;
56
+ char * thumbprint = NULL , * comment ;
57
+ const char * blob ;
58
+ HKEY reg = 0 , sub = 0 , user_root = 0 ;
46
59
47
60
blob = sshbuf_ptr (request );
48
61
if ((r = sshkey_private_deserialize (request , & key )) != 0 )
@@ -53,39 +66,29 @@ process_add_identity(struct sshbuf* request, struct sshbuf* response, HANDLE cli
53
66
goto done ;
54
67
}
55
68
56
- if ((r = sshbuf_peek_string_direct (request , & comment , & comment_len )) != 0 )
57
- goto done ;
58
-
59
- if ((thumbprint = sshkey_fingerprint (key , SSH_FP_HASH_DEFAULT , SSH_FP_DEFAULT )) == NULL )
60
- goto done ;
61
-
62
- if ((r = RegOpenKeyEx (HKEY_LOCAL_MACHINE , SSHD_HOST_KEYS_ROOT ,
63
- 0 , KEY_WRITE , & reg )) != 0 )
64
- goto done ;
65
-
66
- if ((r = RegCreateKeyExA (reg , thumbprint , 0 , 0 , 0 , KEY_WRITE , NULL , & sub , NULL )) != 0 )
67
- goto done ;
68
-
69
- if ((r = RegSetValueEx (sub , NULL , 0 , REG_BINARY , blob , blob_len )) != 0 )
70
- goto done ;
71
-
72
- if ((r = RegSetValueEx (sub , L"pub" , 0 , REG_BINARY , pubkey_blob , pubkey_blob_len )) != 0 )
73
- goto done ;
74
-
75
- if ((r = RegSetValueEx (sub , L"type" , 0 , REG_DWORD , & key -> type , 4 )) != 0 )
76
- goto done ;
77
-
78
- if ((r = RegSetValueEx (sub , L"comment" , 0 , REG_BINARY , comment , comment_len )) != 0 )
69
+ if (((r = sshbuf_peek_string_direct (request , & comment , & comment_len )) != 0 ) ||
70
+ ((thumbprint = sshkey_fingerprint (key , SSH_FP_HASH_DEFAULT , SSH_FP_DEFAULT )) == NULL ) ||
71
+ ((r = get_user_root (con , & user_root )) != 0 ) ||
72
+ ((r = RegCreateKeyExW (user_root , SSHD_KEYS_ROOT , 0 , 0 , 0 , KEY_WRITE , NULL , & reg , NULL )) != 0 ) ||
73
+ ((r = RegCreateKeyExA (reg , thumbprint , 0 , 0 , 0 , KEY_WRITE , NULL , & sub , NULL )) != 0 ) ||
74
+ ((r = RegSetValueExW (sub , NULL , 0 , REG_BINARY , blob , blob_len )) != 0 ) ||
75
+ ((r = RegSetValueExW (sub , L"pub" , 0 , REG_BINARY , pubkey_blob , pubkey_blob_len )) != 0 ) ||
76
+ ((r = RegSetValueExW (sub , L"type" , 0 , REG_DWORD , (BYTE * )& key -> type , 4 )) != 0 ) ||
77
+ ((r = RegSetValueExW (sub , L"comment" , 0 , REG_BINARY , comment , comment_len )) != 0 ) )
79
78
goto done ;
80
79
81
80
done :
82
81
82
+ /* TODO if r failed the delete reg entries*/
83
+
83
84
r1 = sshbuf_put_u8 (response , (r == 0 ) ? SSH_AGENT_SUCCESS : SSH_AGENT_FAILURE );
84
85
85
86
if (key )
86
87
sshkey_free (key );
87
88
if (thumbprint )
88
89
free (thumbprint );
90
+ if (user_root )
91
+ RegCloseKey (user_root );
89
92
if (reg )
90
93
RegCloseKey (reg );
91
94
if (sub )
@@ -96,8 +99,8 @@ process_add_identity(struct sshbuf* request, struct sshbuf* response, HANDLE cli
96
99
}
97
100
98
101
static int sign_blob (const struct sshkey * pubkey , u_char * * sig , size_t * siglen ,
99
- const u_char * blob , size_t blen , u_int flags ) {
100
- HKEY reg = 0 , sub = 0 ;
102
+ const u_char * blob , size_t blen , u_int flags , struct agent_connection * con ) {
103
+ HKEY reg = 0 , sub = 0 , user_root = 0 ;
101
104
int r = 0 ;
102
105
struct sshkey * prikey = NULL ;
103
106
char * thumbprint = NULL , * regdata = NULL ;
@@ -113,15 +116,18 @@ static int sign_blob(const struct sshkey *pubkey, u_char ** sig, size_t *siglen,
113
116
if ((thumbprint = sshkey_fingerprint (pubkey , SSH_FP_HASH_DEFAULT , SSH_FP_DEFAULT )) == NULL )
114
117
goto done ;
115
118
116
- if ((r = RegOpenKeyEx (HKEY_LOCAL_MACHINE , SSHD_HOST_KEYS_ROOT ,
119
+ if ((r = get_user_root (con , & user_root )) != 0 )
120
+ goto done ;
121
+
122
+ if ((r = RegOpenKeyExW (user_root , SSHD_KEYS_ROOT ,
117
123
0 , STANDARD_RIGHTS_READ | KEY_QUERY_VALUE | KEY_ENUMERATE_SUB_KEYS , & reg )) != 0 )
118
124
goto done ;
119
125
120
- if ((r = RegOpenKeyEx (reg , thumbprint , 0 , 0 , 0 , STANDARD_RIGHTS_READ | KEY_QUERY_VALUE | KEY_ENUMERATE_SUB_KEYS ,
121
- NULL , & sub , NULL )) != 0 )
126
+ if ((r = RegOpenKeyExA (reg , thumbprint , 0 , STANDARD_RIGHTS_READ | KEY_QUERY_VALUE | KEY_ENUMERATE_SUB_KEYS ,
127
+ & sub )) != 0 )
122
128
goto done ;
123
129
124
- if ((RegQueryValueEx (sub , NULL , 0 , NULL , regdata , & regdatalen )) != ERROR_MORE_DATA ) {
130
+ if ((RegQueryValueExW (sub , NULL , 0 , NULL , regdata , & regdatalen )) != ERROR_MORE_DATA ) {
125
131
r = EOTHER ;
126
132
goto done ;
127
133
}
@@ -131,7 +137,7 @@ static int sign_blob(const struct sshkey *pubkey, u_char ** sig, size_t *siglen,
131
137
goto done ;
132
138
}
133
139
134
- if ((r = RegQueryValueEx (sub , NULL , 0 , NULL , regdata , & regdatalen )) != 0 )
140
+ if ((r = RegQueryValueExW (sub , NULL , 0 , NULL , regdata , & regdatalen )) != 0 )
135
141
goto done ;
136
142
137
143
if ((tmpbuf = sshbuf_from (regdata , regdatalen )) == NULL ) {
@@ -152,6 +158,8 @@ static int sign_blob(const struct sshkey *pubkey, u_char ** sig, size_t *siglen,
152
158
sshkey_free (prikey );
153
159
if (thumbprint )
154
160
free (thumbprint );
161
+ if (user_root )
162
+ RegCloseKey (user_root );
155
163
if (reg )
156
164
RegCloseKey (reg );
157
165
if (sub )
@@ -161,7 +169,7 @@ static int sign_blob(const struct sshkey *pubkey, u_char ** sig, size_t *siglen,
161
169
}
162
170
163
171
int
164
- process_sign_request (struct sshbuf * request , struct sshbuf * response , HANDLE client ) {
172
+ process_sign_request (struct sshbuf * request , struct sshbuf * response , struct agent_connection * con ) {
165
173
u_char * blob , * data , * signature = NULL ;
166
174
size_t blen , dlen , slen = 0 ;
167
175
u_int flags = 0 ;
@@ -177,7 +185,7 @@ process_sign_request(struct sshbuf* request, struct sshbuf* response, HANDLE cli
177
185
178
186
if (((r = sshkey_from_blob (blob , blen , & key )) != 0 )
179
187
|| ((r = sign_blob (key , & signature , & slen ,
180
- data , dlen , 0 )) != 0 ))
188
+ data , dlen , 0 , con )) != 0 ))
181
189
goto done ;
182
190
183
191
done :
@@ -196,24 +204,29 @@ process_sign_request(struct sshbuf* request, struct sshbuf* response, HANDLE cli
196
204
}
197
205
198
206
int
199
- process_request_identities (struct sshbuf * request , struct sshbuf * response , HANDLE client ) {
207
+ process_request_identities (struct sshbuf * request , struct sshbuf * response , struct agent_connection * con ) {
200
208
int r , r1 , count = 0 , index = 0 ;
201
- HKEY root = NULL , sub = NULL ;
209
+ HKEY root = NULL , sub = NULL , user_root = 0 ;
202
210
char * count_ptr = NULL ;
203
211
wchar_t sub_name [MAX_KEY_LENGTH ];
204
212
DWORD sub_name_len = MAX_KEY_LENGTH ;
205
213
char * regdata = NULL ;
206
214
DWORD regdatalen = 0 , key_count = 0 ;
215
+ struct sshbuf * identities ;
207
216
208
217
regdata = malloc (4 );
209
218
regdatalen = 4 ;
210
219
211
- if ((r = RegOpenKeyEx (HKEY_LOCAL_MACHINE , SSHD_HOST_KEYS_ROOT ,
212
- 0 , STANDARD_RIGHTS_READ | KEY_ENUMERATE_SUB_KEYS , & root )) != 0 )
220
+ identities = sshbuf_new ();
221
+
222
+ if ((identities == NULL ) || (regdata == NULL ))
213
223
goto done ;
214
224
215
- if (((r = sshbuf_put_u8 (response , SSH2_AGENT_IDENTITIES_ANSWER )) != 0 )
216
- || ((r = sshbuf_reserve (response , 4 , & count_ptr )) != 0 ))
225
+ if ((r = get_user_root (con , & user_root )) != 0 )
226
+ goto done ;
227
+
228
+ if ((r = RegOpenKeyExW (user_root , SSHD_KEYS_ROOT ,
229
+ 0 , STANDARD_RIGHTS_READ | KEY_ENUMERATE_SUB_KEYS , & root )) != 0 )
217
230
goto done ;
218
231
219
232
while (1 ) {
@@ -222,9 +235,9 @@ process_request_identities(struct sshbuf* request, struct sshbuf* response, HAND
222
235
RegCloseKey (sub );
223
236
sub = NULL ;
224
237
}
225
- if ((r = RegEnumKeyEx (root , index ++ , sub_name , & sub_name_len , NULL , NULL , NULL , NULL )) == 0 ) {
226
- if ((r = RegOpenKeyEx (root , sub_name , 0 , KEY_QUERY_VALUE , & sub )) == 0 ) {
227
- if ((r = RegQueryValueEx (sub , L"pub" , 0 , NULL , regdata , & regdatalen )) != 0 ) {
238
+ if ((r = RegEnumKeyExW (root , index ++ , sub_name , & sub_name_len , NULL , NULL , NULL , NULL )) == 0 ) {
239
+ if ((r = RegOpenKeyExW (root , sub_name , 0 , KEY_QUERY_VALUE , & sub )) == 0 ) {
240
+ if ((r = RegQueryValueExW (sub , L"pub" , 0 , NULL , regdata , & regdatalen )) != 0 ) {
228
241
if (r == ERROR_MORE_DATA ) {
229
242
r = 0 ;
230
243
if (regdata )
@@ -233,7 +246,7 @@ process_request_identities(struct sshbuf* request, struct sshbuf* response, HAND
233
246
r = ENOMEM ;
234
247
goto done ;
235
248
}
236
- if ((r = RegQueryValueEx (sub , L"pub" , 0 , NULL , regdata , & regdatalen )) != 0 )
249
+ if ((r = RegQueryValueExW (sub , L"pub" , 0 , NULL , regdata , & regdatalen )) != 0 )
237
250
goto done ;
238
251
239
252
}
@@ -243,10 +256,10 @@ process_request_identities(struct sshbuf* request, struct sshbuf* response, HAND
243
256
}
244
257
}
245
258
246
- if ((r = sshbuf_put_string (response , regdata , regdatalen )) != 0 )
259
+ if ((r = sshbuf_put_string (identities , regdata , regdatalen )) != 0 )
247
260
goto done ;
248
261
249
- if ((r = RegQueryValueEx (sub , L"comment" , 0 , NULL , regdata , & regdatalen )) != 0 ) {
262
+ if ((r = RegQueryValueExW (sub , L"comment" , 0 , NULL , regdata , & regdatalen )) != 0 ) {
250
263
if (r == ERROR_MORE_DATA ) {
251
264
r = 0 ;
252
265
if (regdata )
@@ -255,7 +268,7 @@ process_request_identities(struct sshbuf* request, struct sshbuf* response, HAND
255
268
r = ENOMEM ;
256
269
goto done ;
257
270
}
258
- if ((r = RegQueryValueEx (sub , L"comment" , 0 , NULL , regdata , & regdatalen )) != 0 )
271
+ if ((r = RegQueryValueExW (sub , L"comment" , 0 , NULL , regdata , & regdatalen )) != 0 )
259
272
goto done ;
260
273
261
274
}
@@ -264,7 +277,7 @@ process_request_identities(struct sshbuf* request, struct sshbuf* response, HAND
264
277
goto done ;
265
278
}
266
279
}
267
- if ((r = sshbuf_put_string (response , regdata , regdatalen )) != 0 )
280
+ if ((r = sshbuf_put_string (identities , regdata , regdatalen )) != 0 )
268
281
goto done ;
269
282
key_count ++ ;
270
283
@@ -285,11 +298,19 @@ process_request_identities(struct sshbuf* request, struct sshbuf* response, HAND
285
298
286
299
}
287
300
288
- POKE_U32 (count_ptr , key_count );
301
+ if (((r = sshbuf_put_u8 (response , SSH2_AGENT_IDENTITIES_ANSWER )) != 0 )
302
+ || ((r = sshbuf_put_u32 (response , key_count )) != 0 )
303
+ || ((r = sshbuf_putb (response , identities )) != 0 ))
304
+ goto done ;
305
+
289
306
290
307
done :
291
308
if (regdata )
292
309
free (regdata );
310
+ if (identities )
311
+ sshbuf_free (identities );
312
+ if (user_root )
313
+ RegCloseKey (user_root );
293
314
if (root )
294
315
RegCloseKey (root );
295
316
if (sub )
0 commit comments