Ошибка при загрузке страницы через telnet -Linux

Всем привет!

Сразу говорю, как вы наверняка можете заметить, я далеко не мастер в этой теме....

Проблема заключается в том, что когда я хочу запустить какой-то сайт в терминале с помощью telnet(я использую ubuntu), происходит что-то такое:

$ telnet en.wikipedia.org 80
Trying 91.198.174.192...
Connected to dyna.wikimedia.org.
Escape character is '^]'.
GET Connection closed by foreign host.

То есть соединение устанавливается, но как только я хочу что-то ввести, выходит надпись "Connection closed by foreign host" и всё заканчивается.

При этом. когда я запускаю свой сервер, он прекрасно работает:

$ telnet 127.0.0.1 30000
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.
Internet Knock-knock Protocol Server
Version 1.0
Knock-knock!
>Who is there?
Doctor.
>Doctor Who?
Ha-ha.
Connection closed by foreign host.

Причём, что интересно:

$ netstat -tapnl | grep 443
(Не все процессы были идентифицированы, информация о процессах без владельца
 не будет отображена, вам нужны права суперпользователя (root), чтобы увидеть всю информацию.)
tcp        0      0 0.0.0.0:443             0.0.0.0:*               LISTEN      - 

     

Я не изменял никаких настроек telnet и даже понятия не имею с чем это может быть связано. Пробовал с другими сайтами, пробовал менять порт, но ничего не помогало.

С чем это может быть связано, и, самое главное, как решить эту проблему?


Ответы (2 шт):

Автор решения: aleksandr barakin

То есть соединение устанавливается, но как только я хочу что-то ввести, выходит надпись "Connection closed by foreign host" и всё заканчивается.

у http-сервера, от которого вы пытаетесь получить информацию по протоколу http, очень маленькая пауза ожидания информации от клиента. программу telnet для подобных экспериментов лучше заменить на что-то более подходящее. например, netcat. этой программе информацию, которую она отправит серверу, можно передать на её стандартный ввод (stdin).

пример отправки запроса:

$ echo -ne 'GET / HTTP/1.0\r\nHost: en.wikipedia.org\r\n\r\n' | nc en.wikipedia.org 80

на что получим вполне разумный ответ от http-сервера:

HTTP/1.1 301 TLS Redirect
Date: Sat, 27 Jun 2020 19:43:24 GMT
Server: Varnish
X-Varnish: 531026174
X-Cache: cp3056 int
X-Cache-Status: int-front
Server-Timing: cache;desc="int-front"
Set-Cookie: WMF-Last-Access=27-Jun-2020;Path=/;HttpOnly;secure;Expires=Wed, 29 Jul 2020 12:00:00 GMT
Set-Cookie: WMF-Last-Access-Global=27-Jun-2020;Path=/;Domain=.wikipedia.org;HttpOnly;secure;Expires=Wed, 29 Jul 2020 12:00:00 GMT
X-Client-IP: 188.134.16.218
Location: https://en.wikipedia.org/
Content-Length: 0
Connection: close
→ Ссылка
Автор решения: timob256

Ответ несовсем по вопросу ябы сказал по реализации моего совета.

Мой пример реализации клиента и сервера на СИ .

Сервер

/* определяет типы данных */
#include <sys/types.h>
/* "Главный" по сокетам */
#include <sys/socket.h>
/* sockaddr_in struct, sin_family, sin_port, in_addr_t, in_port_t, ...*/
#include <netinet/in.h>

#include <stdio.h>
#include <memory.h>
#include <string.h>
#include <errno.h>

/**@brief Получает от клиента последовательность байт, не длиннее 30 и печатает её на экран по
 * завершении соединения. Клиенту отправляет "Hi, dear!"*/
int main(int argc, char * argv)
{
      /*создаём сокет*/
      int s = socket(AF_INET, SOCK_STREAM, 0);
      if(s < 0)
      {
              perror("Error calling socket");
              return 0;
      }

      /*определяем прослушиваемый порт и адрес*/
      struct sockaddr_in addr;
      addr.sin_family = AF_INET;
      addr.sin_port = htons(18666);
      addr.sin_addr.s_addr = htonl(INADDR_ANY);
      if( bind(s, (struct sockaddr *)&addr, sizeof(addr)) < 0 )
      {
              perror("Error calling bind");
              return 0;
      }

      /*помечаем сокет, как пассивный - он будет слушать порт*/
      if( listen(s, 5) )
      {
              perror("Error calling listen");
              return 0;
      }

      /*начинаем слушать, для соединения создаём другой сокет, в котором можем общаться.*/
      int s1 = accept(s, NULL, NULL);
      if( s1 < 0 )
      {
              perror("Error calling accept");
              return 0;
      }

      /*читаем данные из сокета*/
      char buffer[31];
      int counter = 0;
      for(;;)
      {
              memset(buffer, 0, sizeof(char)*31);
              /*следует помнить, что данные поступают неравномерно*/
              int rc = recv(s1, buffer, 30, 0);
              if( rc < 0 )
              {
                      /*чтение может быть прервано системным вызовом, это нормально*/
                      if( errno == EINTR )
                              continue;
                      perror("Can't receive data.");
                      return 0;
              }
              if( rc == 0 )
                      break;
              printf("%s\n", buffer);
      }
      char response[] = "Hi, dear!";
      if( sendto( s1, response, sizeof(response), 0, (struct sockaddr *)&addr, sizeof(addr) ) < 0 )
              perror("Error sending response");
      printf("Response send\n");
      return 0;
} 

Клиент

include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
/* hton, ntoh и проч. */
#include <arpa/inet.h>
#include <memory.h>
#include <stdio.h>

int main(int argc, char * argv[])
{

      /*объявляем сокет*/
      int s = socket( AF_INET, SOCK_STREAM, 0 );
      if(s < 0)
      {
              perror( "Error calling socket" );
              return 0;
      }

      /*соединяемся по определённому порту с хостом*/
      struct sockaddr_in peer;
      peer.sin_family = AF_INET;
      peer.sin_port = htons( 18666 );
      peer.sin_addr.s_addr = inet_addr( "172.16.8.169" ); // тут замени на свой адрес адрес можно узнать командой sudo ifconfig
      int result = connect( s, ( struct sockaddr * )&peer, sizeof( peer ) );
      if( result )
      {
              perror( "Error calling connect" );
              return 0;
      }

      /*посылаем данные
       *
       * Если быть точным, данные не посланы, а записаны где-то в стеке, когда и как они будут
       * отправлены реализации стека TCP/IP виднее. Зато мы сразу получаем управление, не
       * дожидаясь у моря погоды.*/
      char buf[] = "Hello, world!";
      result = send( s, "Hello, world!", 13, 0);
      if( result <= 0 )
      {
              perror( "Error calling send" );
              return 0;
      }
      /* закрываем соединения для посылки данных */
      if( shutdown(s, 1) < 0)
      {
              perror("Error calling shutdown");
              return 0;
      }

      /* читаем ответ сервера */
      fd_set readmask;
      fd_set allreads;
      FD_ZERO( &allreads );
      FD_SET( 0, &allreads );
      FD_SET( s, &allreads );
      for(;;)
      {
              readmask = allreads;
              if( select(s + 1, &readmask, NULL, NULL, NULL ) <= 0 )
              {
                      perror("Error calling select");
                      return 0;
              }
              if( FD_ISSET( s, &readmask ) )
              {
                      char buffer[20];
                      memset(buffer, 0, 20*sizeof(char));
                      int result = recv( s, buffer, sizeof(buffer) - 1, 0 );
                      if( result < 0 )
                      {
                              perror("Error calling recv");
                              return 0;
                      }
                      if( result == 0 )
                      {
                              perror("Server disconnected");
                              return 0;
                      }
                      if(strncmp(buffer, "Hi, dear!", 9) == 0)
                              printf("Got answer. Success.\n");
                      else
                              perror("Wrong answer!");
              }
              if( FD_ISSET( 0, &readmask ) )
              {
                      printf( "No server response" );
                      return 0;
              }
      }
      return 0;
}

Собираем сервер и запускаем его

[email protected]:~/mita/TCP_IP$ gcc client.c -o client
[email protected]:~/mita/TCP_IP$ ./client 

В создаём отдельный терминал и там собираем клиент :

[email protected]:~/mita/TCP_IP$ gcc client.c -o client
[email protected]:~/mita/TCP_IP$ ./client 

Сервер выведет

Hello, world!
Response send

Клиент выведет

Got answer. Success.
Server disconnected: Success
→ Ссылка