@@ -465,22 +465,42 @@ server_recv_cb(EV_P_ ev_io *w, int revents)
465
465
// all processed
466
466
return ;
467
467
} else if (server -> stage == STAGE_INIT ) {
468
- if (buf -> len < sizeof (struct method_select_request ) + 1 ) {
468
+ if (buf -> len < 1 )
469
+ return ;
470
+ if (buf -> data [0 ] != SVERSION ) {
471
+ close_and_free_remote (EV_A_ remote );
472
+ close_and_free_server (EV_A_ server );
473
+ return ;
474
+ }
475
+ if (buf -> len < sizeof (struct method_select_request )) {
469
476
return ;
470
477
}
471
478
struct method_select_request * method = (struct method_select_request * )buf -> data ;
472
479
int method_len = method -> nmethods + sizeof (struct method_select_request );
473
480
if (buf -> len < method_len ) {
474
481
return ;
475
482
}
483
+
476
484
struct method_select_response response ;
477
485
response .ver = SVERSION ;
478
- response .method = 0 ;
486
+ response .method = METHOD_UNACCEPTABLE ;
487
+ for (int i = 0 ; i < method -> nmethods ; i ++ ) {
488
+ if (method -> methods [i ] == METHOD_NOAUTH ) {
489
+ response .method = METHOD_NOAUTH ;
490
+ break ;
491
+ }
492
+ }
479
493
char * send_buf = (char * )& response ;
480
494
send (server -> fd , send_buf , sizeof (response ), 0 );
495
+ if (response .method == METHOD_UNACCEPTABLE ) {
496
+ close_and_free_remote (EV_A_ remote );
497
+ close_and_free_server (EV_A_ server );
498
+ return ;
499
+ }
500
+
481
501
server -> stage = STAGE_HANDSHAKE ;
482
502
483
- if (method -> ver == SVERSION && method_len < (int )(buf -> len )) {
503
+ if (method_len < (int )(buf -> len )) {
484
504
memmove (buf -> data , buf -> data + method_len , buf -> len - method_len );
485
505
buf -> len -= method_len ;
486
506
continue ;
0 commit comments