RTSP через HTTP через прокси - PullRequest
6 голосов
/ 03 ноября 2008

Я пытаюсь получить поток RTSP через HTTP, используя прокси. Поведение Реального клиента кажется немного беспокойным: он пробует все возможные порты, методы и протоколы одновременно. Единственное, что должно работать - это HTTP GET через порт 80. Такой запрос действительно выдается и принимается на сервере. Вот как выглядит запрос, когда он отправляется прокси на сервер:

GET /SmpDsBhgRl83c52ef2-d0f4-41ac-bada-93e5350f67d1?1="1" HTTP/1.0\r\n
Connection: Keep-Alive\r\n
Host: 10.194.5.162:80\r\n
Pragma: no-cache\r\n
User-Agent: RealPlayer G2\r\n
Expires: Mon, 18 May 1974 00:00:00 GMT\r\n
Accept: application/x-rtsp-tunnelled, */*\r\n
ClientID: WinNT_5.1_6.0.14.806_RealPlayer_R41UKD_en-GB_686\r\n
X-Actual-URL: rtsp://10.194.5.162:554/01.mp3\r\n
\r\n

Вот ответ сервера:

HTTP/1.0 200 OK\r\n
Server: RMServer 1.0\r\n
Expires: Mon, 18 May 1974 00:00:00 GMT\r\n
Pragma: no-cache\r\n
x-server-ipaddress: 10.194.5.162\r\n
Content-type: audio/x-pn-realaudio\r\n
\r\n

В этот момент с сервера приходит еще 4 байта (их значения 48 02 02 00) - и все, больше ничего. Ожидает ли сервер что-либо от клиента в этот момент, и если да, то что? Этот режим работы работает вообще?

Еще немного информации по этой проблеме: очевидно, предполагаемый механизм работы с RTSP через HTTP, встроенный в RealPlayer, выглядит следующим образом:

  1. Попробуйте подключиться к следующим портам: 80, 8080, 554, 7070. (Попробуйте также загрузить файл напрямую, просто так, выполнив команду GET http://hostname:port/mediafilename на порт 80)
  2. Для каждого из указанных портов создайте 2 соединения.
  3. Отправьте запрос GET на одно из соединений по URL-адресу http://hostname:port/SmpDsBhgRl?1="1",, где <guid> - это, да, только что созданный GUID. Добавьте к этому запросу заголовок с именем X-Actual-URL, содержащий исходный URL-адрес RTSP.
  4. Отправьте запрос POST по другому соединению на URL http://hostname:port/SmpDsBhgRl с указанным выше GUID как часть тела запроса. Отправьте заголовок Content-Length длиной 32767 байт, чтобы прокси-сервер преждевременно не закрыл соединение.
  5. Начните выдавать команды серверу через запрос POST и получите соответствующий поток RTSP как часть ответа GET.

Странная вещь (если вышеупомянутое не достаточно странно) заключается в том, что, например, она работает со Squid, но не при использовании любого из портов 3128 или 8080! Так или иначе, клиент использует порт, к которому он подключается, чтобы определить порядок запросов или когда запрос должен быть отменен, но в любом случае, как бы трудно это ни было, он работает с прокси-портом 9090, 3129, 8081, но не с 3128 или 8080.

Обновление № 2: Здесь - источник RealPlayer с объяснением вышеупомянутого поведения. Тем не менее, пока нет решения.

Обновление № 3: ОК, в свете вышесказанного, магическое значение 48 02 02 00 ясно: 48 == 'h' для HTTP_RESPONSE, следующие 02 - длина следующих данных, следующий 02 называется POST_NOT_RECEIVED (это означает, что запрос POST не достиг сервера в течение секунды после соответствующего запроса GET).

Обновление № 4: это поведение (то есть POST-запросы с огромным Content-Length) также характерно для ActiveX, используемого WebEx (и, возможно, многими другими веб-приложениями, которым требуется открытый канал для сервера).

Ответы [ 2 ]

3 голосов
/ 05 ноября 2008

Во-первых, вы можете прочитать это:

http://developer.apple.com/quicktime/icefloe/dispatch028.html

Во-вторых, HTTP-запросы (как GET, так и POST) необходимо отформатировать, чтобы они правильно проксировались. Я видел прокси-серверы, которые настаивают на том, чтобы кэшировать слишком много POST-запросов, чтобы они не доходили до сервера. Эти прокси содержат ошибки, но вы ничего не можете с этим поделать, и я не смог обойти эту проблему. В основном я видел это с антивирусным программным обеспечением, которое пытается прозрачно проксировать POST-запросы, поступающие из браузера, чтобы сканировать их на предмет личной информации, такой как номера социального страхования. Возможно, вы столкнулись с той же проблемой.

Вы случайно используете антивирус McAfee?

Кроме того, кажется, что Real изобрел свой собственный способ сделать то же самое, но базовый дизайн очень похож - GET для нисходящего канала, POST для восходящего потока, с каким-то волшебным cookie-файлом (в данном случае GUID) связать их вместе на сервере. В любом случае, POST должен попасть на сервер, а в вашем случае кажется, что это не так.

Кстати, поскольку, похоже, проблема в том, что POST-запрос не проходит через прокси, как насчет публикации этого запроса в дополнение к GET?

0 голосов
/ 04 ноября 2008
  1. Посмотрите, приведет ли к тому, что отправка того же запроса, но в обход прокси-сервера (например, воспроизведение запроса, отправленного вами выше с использованием Netcat), приведет к тому, что в теле ответа будет передано более четырех байтов.
  2. Посмотрите, какие TCP-пакеты получает прокси-сервер, например, прослушивая TCP трафик на машине, на которой работает прокси, скажем, с помощью Wireshark.
...