@@ -205,6 +205,38 @@ static struct iscsi_chap *chap_server_open(
205
205
return chap ;
206
206
}
207
207
208
+ static const char base64_lookup_table [] =
209
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/" ;
210
+
211
+ static int chap_base64_decode (u8 * dst , const char * src , size_t len )
212
+ {
213
+ int i , bits = 0 , ac = 0 ;
214
+ const char * p ;
215
+ u8 * cp = dst ;
216
+
217
+ for (i = 0 ; i < len ; i ++ ) {
218
+ if (src [i ] == '=' )
219
+ return cp - dst ;
220
+
221
+ p = strchr (base64_lookup_table , src [i ]);
222
+ if (p == NULL || src [i ] == 0 )
223
+ return -2 ;
224
+
225
+ ac <<= 6 ;
226
+ ac += (p - base64_lookup_table );
227
+ bits += 6 ;
228
+ if (bits >= 8 ) {
229
+ * cp ++ = (ac >> (bits - 8 )) & 0xff ;
230
+ ac &= ~(BIT (16 ) - BIT (bits - 8 ));
231
+ bits -= 8 ;
232
+ }
233
+ }
234
+ if (ac )
235
+ return -1 ;
236
+
237
+ return cp - dst ;
238
+ }
239
+
208
240
static int chap_server_compute_hash (
209
241
struct iscsit_conn * conn ,
210
242
struct iscsi_node_auth * auth ,
@@ -295,16 +327,27 @@ static int chap_server_compute_hash(
295
327
pr_err ("Could not find CHAP_R.\n" );
296
328
goto out ;
297
329
}
298
- if (type != HEX ) {
299
- pr_err ("Could not find CHAP_R.\n" );
300
- goto out ;
301
- }
302
- if (strlen (chap_r ) != chap -> digest_size * 2 ) {
303
- pr_err ("Malformed CHAP_R\n" );
304
- goto out ;
305
- }
306
- if (hex2bin (client_digest , chap_r , chap -> digest_size ) < 0 ) {
307
- pr_err ("Malformed CHAP_R\n" );
330
+
331
+ switch (type ) {
332
+ case HEX :
333
+ if (strlen (chap_r ) != chap -> digest_size * 2 ) {
334
+ pr_err ("Malformed CHAP_R\n" );
335
+ goto out ;
336
+ }
337
+ if (hex2bin (client_digest , chap_r , chap -> digest_size ) < 0 ) {
338
+ pr_err ("Malformed CHAP_R: invalid HEX\n" );
339
+ goto out ;
340
+ }
341
+ break ;
342
+ case BASE64 :
343
+ if (chap_base64_decode (client_digest , chap_r , strlen (chap_r )) !=
344
+ chap -> digest_size ) {
345
+ pr_err ("Malformed CHAP_R: invalid BASE64\n" );
346
+ goto out ;
347
+ }
348
+ break ;
349
+ default :
350
+ pr_err ("Could not find CHAP_R\n" );
308
351
goto out ;
309
352
}
310
353
@@ -404,23 +447,46 @@ static int chap_server_compute_hash(
404
447
goto out ;
405
448
}
406
449
407
- if (type != HEX ) {
450
+ switch (type ) {
451
+ case HEX :
452
+ initiatorchg_len = DIV_ROUND_UP (strlen (initiatorchg ), 2 );
453
+ if (!initiatorchg_len ) {
454
+ pr_err ("Unable to convert incoming challenge\n" );
455
+ goto out ;
456
+ }
457
+ if (initiatorchg_len > 1024 ) {
458
+ pr_err ("CHAP_C exceeds maximum binary size of 1024 bytes\n" );
459
+ goto out ;
460
+ }
461
+
462
+ if (hex2bin (initiatorchg_binhex , initiatorchg ,
463
+ initiatorchg_len ) < 0 ) {
464
+ pr_err ("Malformed CHAP_C: invalid HEX\n" );
465
+ goto out ;
466
+ }
467
+ break ;
468
+ case BASE64 :
469
+ initiatorchg_len = chap_base64_decode (initiatorchg_binhex ,
470
+ initiatorchg ,
471
+ strlen (initiatorchg ));
472
+ if (initiatorchg_len < 0 ) {
473
+ pr_err ("Malformed CHAP_C: invalid BASE64\n" );
474
+ goto out ;
475
+ }
476
+ if (!initiatorchg_len ) {
477
+ pr_err ("Unable to convert incoming challenge\n" );
478
+ goto out ;
479
+ }
480
+ if (initiatorchg_len > 1024 ) {
481
+ pr_err ("CHAP_C exceeds maximum binary size of 1024 bytes\n" );
482
+ goto out ;
483
+ }
484
+ break ;
485
+ default :
408
486
pr_err ("Could not find CHAP_C.\n" );
409
487
goto out ;
410
488
}
411
- initiatorchg_len = DIV_ROUND_UP (strlen (initiatorchg ), 2 );
412
- if (!initiatorchg_len ) {
413
- pr_err ("Unable to convert incoming challenge\n" );
414
- goto out ;
415
- }
416
- if (initiatorchg_len > 1024 ) {
417
- pr_err ("CHAP_C exceeds maximum binary size of 1024 bytes\n" );
418
- goto out ;
419
- }
420
- if (hex2bin (initiatorchg_binhex , initiatorchg , initiatorchg_len ) < 0 ) {
421
- pr_err ("Malformed CHAP_C\n" );
422
- goto out ;
423
- }
489
+
424
490
pr_debug ("[server] Got CHAP_C=%s\n" , initiatorchg );
425
491
/*
426
492
* During mutual authentication, the CHAP_C generated by the
0 commit comments