[c\c++] sosks5 server, ошибка

Discussion in 'С/С++, C#, Rust, Swift, Go, Java, Perl, Ruby' started by bad_boy, 25 Nov 2010.

  1. bad_boy

    bad_boy Elder - Старейшина

    Joined:
    30 Dec 2004
    Messages:
    187
    Likes Received:
    33
    Reputations:
    3
    Ниже написана процедура обработки socks5 сервером подключений. Но она не работает. Проблема, видимо, в цикле
    ...while(!error)..., хотя для socks4 один в один работает. Пересмотрел много сорцов, разницы вроде нет. Пробую подключаться через Miranda, сервер коннектится к серверу ICQ, но с мирандой они не обмениваются данными.
    Code:
    del
     
    #1 bad_boy, 25 Nov 2010
    Last edited: 26 Nov 2010
  2. slesh

    slesh Elder - Старейшина

    Joined:
    5 Mar 2007
    Messages:
    2,702
    Likes Received:
    1,224
    Reputations:
    455
    мдауж жестоко ты сделал.

    1) Если нравится многопоточность, то лучше бы сделал в одной функции цикл обработки коннектов и запуска потока обработки каждого клиента. т.е. создание нового потока с указанием в параметрах - сокета. пашет отлично такая комбинация.

    2) Когда считываешь параметры авторизации, то лучше смотреть что предлагает клиент. бывают случае когда клиент говорит что хотю подключиться тока с авторизацией, а ты ему в ответ гворишь всегда - подключайся без авторизации. Так что проверяй предложенные методы и отклоняй запрос если нет метода Без авторизации

    3) Хоть гдето проверяй что возвращает тебе recv то есть вероятность на долго подвиснуть + таймауты поставь на recv

    4) Ты уверен что миранда тебе шлет запрос на коннект по IP а не по домену?
    Очень часто во всём софте для универсальности и IP и домены шлются в запросах как домены. И там ты уже сам должен определить что это. А еще лучше сделай поддержку типов по IP v4 и по HOST. Потмоу что первый коннект может и пройдет по IP а потом хз что во втором коннекте будет. может и домен.

    5) чтото мне кажется select у тебя не правильно используется. Для nix систем там он отличается от виндового использования

    6) нафига гонять while(!error) если внутри цикла ты всё равно выходишь каждый раз по break. проще уже написать for (;;)

    7) close(sock_endpoint);
    shutdown(sock_endpoint,SD_BOTH);
    Вот тут ты ошибся с последовательностью операций. Странно как это ты не умудрился тут поймать сигнал об ошибочном сокете.

    8) Это С а не С++

    9) Почему ты отсылаешь ответный пакет клиенту тока в случае успешности коннекта? ты должен еще и в случае ошибки его отсылать.

    10) пакет отклика на запрос коннекта тебе совсем не надо очищать, достаточно просто выставить флаг удачности/ошибочности коннекта, ну и подправить ip и порт который был задействова при удачном коннекте если конечно коннект был удачным
     
    #2 slesh, 25 Nov 2010
    Last edited: 25 Nov 2010
    1 person likes this.
  3. bad_boy

    bad_boy Elder - Старейшина

    Joined:
    30 Dec 2004
    Messages:
    187
    Likes Received:
    33
    Reputations:
    3
    slesh
    1) Смысла, честно говоря, не вижу. Тут, если пришёл клиент - рождаем поток, иначе ждём.
    2) Ну, у меня вопрос про конкретный случай, Миранда шлёт как надо всё, хотя и проверять не обязательно, клиент не будет подключаться, если выбранный метод не посылал.
    3,5) select этим и занимается, что ждёт данных с таймаутом, тестирую под win, Миранды под nix вроде ещё не существует.
    4) Да.(в отладчике ж видно, да и галочка "Resolve hostname throuth proxy" не стоит и соединение есть с login.icq.com как говорил уже).
    6) Это скопипастил из обработчика socks4, там считал ошибку, можно и заменить :)
    7) Действительно, спасибо.
    8) Ну, не суть важно, указал с\с++
    9) Сделаю.
    10) Можно и так.

    Но дело всё таки не в этом всём. Вот процедура для socks4, и работает:
    Code:
    del
     
    #3 bad_boy, 25 Nov 2010
    Last edited: 26 Nov 2010
  4. becensed

    becensed Member

    Joined:
    2 Dec 2009
    Messages:
    84
    Likes Received:
    24
    Reputations:
    1
    Я, конечно, дико извиняюсь, но разве отладчики уже отменили?
    Вряд ли кому-то захочется разбираться в твоем коде (мне не захотелось).
     
  5. bad_boy

    bad_boy Elder - Старейшина

    Joined:
    30 Dec 2004
    Messages:
    187
    Likes Received:
    33
    Reputations:
    3
    becensed, можно не извиняться. Я уже писал что смотрел отладчиком.
    Форум это последнее место, куда я обратился.
    Люди даже не читают, видимо, а мельком просматривают текст.

    Вот организация передачи данных от клиента к серверу и обратно. Ошибка скорее всего тут, но она не очевидна.
    Code:
    FD_ZERO(&fds_zero);
    FD_SET(sock_endpoint,&fds_zero);
    FD_SET(sock_client,&fds_zero);
    while(!error)
    {
    	length = 0;
    	fds = fds_zero;					
    	select(0,&fds,0,0,&time_out5);
    	if(FD_ISSET(sock_client,&fds))
    	{
    		length = recv(sock_client,Buffer,ARR_SIZE(Buffer),0);if(len  gth <= 0) break;
    		length = send(sock_endpoint,Buffer,length,0);if(length <= 0) break;
    	}
    	if(FD_ISSET(sock_endpoint,&fds))
    	{
    		length = recv(sock_endpoint,Buffer,ARR_SIZE(Buffer),0);if(l  ength <= 0) break;
    		length = send(sock_client,Buffer,length,0);if(length <= 0) break;
    	}					
    }
    
    Возможно необходимо реализовать это абсолютно по-другому.
     
  6. slesh

    slesh Elder - Старейшина

    Joined:
    5 Mar 2007
    Messages:
    2,702
    Likes Received:
    1,224
    Reputations:
    455
    Этото код ты запускаешь на никсе или на винде?

    И причем тут селек и проверка recv ?
    recv(sock_client,(char*) &req,sizeof(req),0);
    do{recv(sock_client,&c,1,0);}while(c != 0);/* skip ident */

    Вот тут вот в цикле имеет 100% шансы зависнуть при обрыве связи.
     
    #6 slesh, 25 Nov 2010
    Last edited: 25 Nov 2010
  7. Gar|k

    Gar|k Moderator

    Joined:
    20 Mar 2009
    Messages:
    1,166
    Likes Received:
    266
    Reputations:
    82
    /showthread.php?p=2251788
     
    _________________________
  8. bad_boy

    bad_boy Elder - Старейшина

    Joined:
    30 Dec 2004
    Messages:
    187
    Likes Received:
    33
    Reputations:
    3
    Бинарник качал, через него нет подключения аналогично(передавался host:port).
    В сорцах, в процедуре обработки данных различий принципиальных нет.

    Да на винде, уже который раз говорю, при чём тут этот кусок кода, вопрос у меня про socks5, а не socks4, код я не оптимизирую, зависнуть не боюсь. Вопрос конкретный, а не пространный. Данные от Миранды в сокс-сервер идут, из сокс-сервера на сервер icq идут, а дальше ни ответа ни привета. Вот копипаст из tcpview:
     
  9. Gar|k

    Gar|k Moderator

    Joined:
    20 Mar 2009
    Messages:
    1,166
    Likes Received:
    266
    Reputations:
    82
    2 bad_boy принципиальные различия в проверке ответов сетевых функций и их корректная обработка. Сетевое программирование на самом деле не простая задача потому что нужно предусмотреть все возможные варианты сбоев и нагрузок на сеть и приложение.

    Сразу писать нужно с проверками, потому что "зависнуть" у тебя может в любом месте при приеме передаче подключении клиента и т.д. При одном тесте будет работать при другом нет, а ошибка в программе вообще не там :)
     
    _________________________
    1 person likes this.
  10. slesh

    slesh Elder - Старейшина

    Joined:
    5 Mar 2007
    Messages:
    2,702
    Likes Received:
    1,224
    Reputations:
    455
    А вообще тут может быть что угодно, зависит еще от описания структуры или от таймаута который ставишь. и главное от той чёртовой либы которую ты используешь.
    Код который я вижу - это чисто linux кода и никогда в жизни он не скомпилится на Win с использованием WinSock. Потому что там нету функций таких как close и тому подобные. Если ты написал самописную обертку то тоже может быть глюк в ней.

    Возможно просто структурs для socks5 не правильно определены.
     
    #10 slesh, 25 Nov 2010
    Last edited: 25 Nov 2010