Revision f830c9a4

View differences:

libavformat/rtsp.c
888 888
                    int lower_transport, const char *real_challenge)
889 889
{
890 890
    RTSPState *rt = s->priv_data;
891
    int j, i, err, interleave = 0;
891
    int rtx, j, i, err, interleave = 0;
892 892
    RTSPStream *rtsp_st;
893 893
    RTSPMessageHeader reply1, *reply = &reply1;
894 894
    char cmd[2048];
......
906 906
    for(j = RTSP_RTP_PORT_MIN, i = 0; i < rt->nb_rtsp_streams; ++i) {
907 907
        char transport[2048];
908 908

  
909
        /**
910
         * WMS serves all UDP data over a single connection, the RTX, which
911
         * isn't necessarily the first in the SDP but has to be the first
912
         * to be set up, else the second/third SETUP will fail with a 461.
913
         */
914
        if (lower_transport == RTSP_LOWER_TRANSPORT_UDP &&
915
             rt->server_type == RTSP_SERVER_WMS) {
916
            if (i == 0) {
917
                /* rtx first */
918
                for (rtx = 0; rtx < rt->nb_rtsp_streams; rtx++) {
919
                    int len = strlen(rt->rtsp_streams[rtx]->control_url);
920
                    if (len >= 4 &&
921
                        !strcmp(rt->rtsp_streams[rtx]->control_url + len - 4, "/rtx"))
922
                        break;
923
                }
924
                if (rtx == rt->nb_rtsp_streams)
925
                    return -1; /* no RTX found */
926
                rtsp_st = rt->rtsp_streams[rtx];
927
            } else
928
                rtsp_st = rt->rtsp_streams[i > rtx ? i : i - 1];
929
        } else
909 930
        rtsp_st = rt->rtsp_streams[i];
910 931

  
911 932
        /* RTP/UDP */
912 933
        if (lower_transport == RTSP_LOWER_TRANSPORT_UDP) {
913 934
            char buf[256];
914 935

  
936
            if (rt->server_type == RTSP_SERVER_WMS && i > 1) {
937
                port = reply->transports[0].client_port_min;
938
                goto have_port;
939
            }
940

  
915 941
            /* first try in specified port range */
916 942
            if (RTSP_RTP_PORT_MIN != 0) {
917 943
                while(j <= RTSP_RTP_PORT_MAX) {
......
932 958

  
933 959
        rtp_opened:
934 960
            port = rtp_get_local_port(rtsp_st->rtp_handle);
961
        have_port:
935 962
            snprintf(transport, sizeof(transport) - 1,
936 963
                     "%s/UDP;", trans_pref);
937 964
            if (rt->server_type != RTSP_SERVER_REAL)
938 965
                av_strlcat(transport, "unicast;", sizeof(transport));
939 966
            av_strlcatf(transport, sizeof(transport),
940 967
                     "client_port=%d", port);
941
            if (rt->transport == RTSP_TRANSPORT_RTP)
968
            if (rt->transport == RTSP_TRANSPORT_RTP &&
969
                !(rt->server_type == RTSP_SERVER_WMS && i > 0))
942 970
                av_strlcatf(transport, sizeof(transport), "-%d", port + 1);
943 971
        }
944 972

  
......
1022 1050
                /* XXX: also use address if specified */
1023 1051
                snprintf(url, sizeof(url), "rtp://%s:%d",
1024 1052
                         host, reply->transports[0].server_port_min);
1025
                if (rtp_set_remote_url(rtsp_st->rtp_handle, url) < 0) {
1053
                if (!(rt->server_type == RTSP_SERVER_WMS && i > 1) &&
1054
                    rtp_set_remote_url(rtsp_st->rtp_handle, url) < 0) {
1026 1055
                    err = AVERROR_INVALIDDATA;
1027 1056
                    goto fail;
1028 1057
                }
......
1286 1315
        fd_max = -1;
1287 1316
        for(i = 0; i < rt->nb_rtsp_streams; i++) {
1288 1317
            rtsp_st = rt->rtsp_streams[i];
1318
            if (rtsp_st->rtp_handle) {
1289 1319
            /* currently, we cannot probe RTCP handle because of blocking restrictions */
1290 1320
            rtp_get_file_handles(rtsp_st->rtp_handle, &fd1, &fd2);
1291 1321
            if (fd1 > fd_max)
1292 1322
                fd_max = fd1;
1293 1323
            FD_SET(fd1, &rfds);
1324
            }
1294 1325
        }
1295 1326
        tv.tv_sec = 0;
1296 1327
        tv.tv_usec = 100 * 1000;
......
1298 1329
        if (n > 0) {
1299 1330
            for(i = 0; i < rt->nb_rtsp_streams; i++) {
1300 1331
                rtsp_st = rt->rtsp_streams[i];
1332
                if (rtsp_st->rtp_handle) {
1301 1333
                rtp_get_file_handles(rtsp_st->rtp_handle, &fd1, &fd2);
1302 1334
                if (FD_ISSET(fd1, &rfds)) {
1303 1335
                    ret = url_read(rtsp_st->rtp_handle, buf, buf_size);
......
1306 1338
                        return ret;
1307 1339
                    }
1308 1340
                }
1341
                }
1309 1342
            }
1310 1343
        }
1311 1344
    }

Also available in: Unified diff