From d8ae255f3d08b0f26a037d4c8d75b148903900a8 Mon Sep 17 00:00:00 2001 From: =?utf8?q?R=C3=A9mi=20Denis-Courmont?= Date: Mon, 5 Feb 2007 16:32:31 +0000 Subject: [PATCH] UDP-Lite access This is completely untested because vlc does not link at the moment :( --- NEWS | 3 ++ configure.ac | 2 +- include/vlc_network.h | 4 +-- modules/access/udp.c | 71 +++++++++++++++++++++++++------------------ src/network/udp.c | 16 +++++----- 5 files changed, 57 insertions(+), 39 deletions(-) diff --git a/NEWS b/NEWS index f4d648a3e9..d38ef9e3fb 100644 --- a/NEWS +++ b/NEWS @@ -28,6 +28,9 @@ Playlist: * Shoutcast TV listings * Audioscrobbler/last.fm support +Input/Demuxers: + * Support for UDP-Lite (requires OS support) for UDP-Raw and RTP + Decoders: * VP60/VP61 codecs support diff --git a/configure.ac b/configure.ac index 49e46dd8a5..e9a9866869 100644 --- a/configure.ac +++ b/configure.ac @@ -766,7 +766,7 @@ AC_EGREP_HEADER(strncasecmp,strings.h,[ dnl Check for headers AC_CHECK_HEADERS(signal.h time.h errno.h stdint.h stdbool.h getopt.h strings.h inttypes.h sys/int_types.h wchar.h) AC_CHECK_HEADERS(sys/sockio.h fcntl.h sys/types.h sys/time.h sys/times.h sys/ioctl.h sys/stat.h) -AC_CHECK_HEADERS(arpa/inet.h net/if.h netinet/in.h sys/socket.h) +AC_CHECK_HEADERS([arpa/inet.h net/if.h netinet/in.h sys/socket.h netinet/udplite.h]) if test "${SYS}" != "mingw32" -a "${SYS}" != "mingwce"; then AC_CHECK_HEADERS(machine/param.h sys/shm.h) AC_CHECK_HEADERS(linux/version.h) diff --git a/include/vlc_network.h b/include/vlc_network.h index 417fcd51b2..ff27b231fd 100644 --- a/include/vlc_network.h +++ b/include/vlc_network.h @@ -91,8 +91,8 @@ static inline int net_ListenUDP1 (vlc_object_t *obj, const char *host, int port) return net_ListenSingle (obj, host, port, AF_UNSPEC, SOCK_DGRAM, IPPROTO_UDP); } -#define net_OpenUDP(a, b, c, d, e ) __net_OpenUDP(VLC_OBJECT(a), b, c, d, e) -VLC_EXPORT( int, __net_OpenUDP, ( vlc_object_t *p_this, const char *psz_bind, int i_bind, const char *psz_server, int i_server ) ); +#define net_OpenDgram( a, b, c, d, e, g, h ) __net_OpenDgram(VLC_OBJECT(a), b, c, d, e, g, h) +VLC_EXPORT( int, __net_OpenDgram, ( vlc_object_t *p_this, const char *psz_bind, int i_bind, const char *psz_server, int i_server, int family, int proto ) ); VLC_EXPORT( void, net_Close, ( int fd ) ); VLC_EXPORT( void, net_ListenClose, ( int *fd ) ); diff --git a/modules/access/udp.c b/modules/access/udp.c index f6c1a3d135..19e4d60c44 100644 --- a/modules/access/udp.c +++ b/modules/access/udp.c @@ -35,6 +35,21 @@ #include #include +#if defined (HAVE_NETINET_UDPLITE_H) +# include +#elif defined (__linux__) +# define UDPLITE_SEND_CSCOV 10 +# define UDPLITE_RECV_CSCOV 11 +#endif + +#ifndef IPPROTO_UDPLITE +# define IPPROTO_UDPLITE 136 /* from IANA */ +#endif +#ifndef SOL_UDPLITE +# define SOL_UDPLITE IPPROTO_UDPLITE +#endif + + /***************************************************************************** * Module descriptor *****************************************************************************/ @@ -77,6 +92,9 @@ vlc_module_begin(); add_shortcut( "rtp" ); add_shortcut( "rtp4" ); add_shortcut( "rtp6" ); + add_shortcut( "udplite" ); + add_shortcut( "rtplite" ); + set_callbacks( Open, Close ); vlc_module_end(); @@ -116,34 +134,25 @@ static int Open( vlc_object_t *p_this ) char *psz_parser; const char *psz_server_addr, *psz_bind_addr = ""; int i_bind_port, i_server_port = 0; + int fam = AF_UNSPEC, proto = IPPROTO_UDP, cscov = 8; - /* First set ipv4/ipv6 */ - var_Create( p_access, "ipv4", VLC_VAR_BOOL | VLC_VAR_DOINHERIT ); - var_Create( p_access, "ipv6", VLC_VAR_BOOL | VLC_VAR_DOINHERIT ); - - if( *p_access->psz_access ) - { - vlc_value_t val; - /* Find out which shortcut was used */ - if( !strncmp( p_access->psz_access, "udp4", 6 ) || - !strncmp( p_access->psz_access, "rtp4", 6 )) + if (strlen (p_access->psz_access) >= 4) + switch (p_access->psz_access[3]) { - val.b_bool = VLC_TRUE; - var_Set( p_access, "ipv4", val ); + case '4': + fam = AF_INET; + break; - val.b_bool = VLC_FALSE; - var_Set( p_access, "ipv6", val ); + case '6': + fam = AF_INET6; + break; } - else if( !strncmp( p_access->psz_access, "udp6", 6 ) || - !strncmp( p_access->psz_access, "rtp6", 6 ) ) - { - val.b_bool = VLC_TRUE; - var_Set( p_access, "ipv6", val ); - - val.b_bool = VLC_FALSE; - var_Set( p_access, "ipv4", val ); - } - } + if (strcmp (p_access->psz_access + 3, "lite") == 0) + proto = IPPROTO_UDPLITE; + if (strncmp (p_access->psz_access, "rtp", 3) == 0) + /* Checksum coverage: RTP header is AT LEAST 12 bytes + * in addition to UDP header (8 bytes) */ + cscov += 12; i_bind_port = var_CreateGetInteger( p_access, "server-port" ); @@ -195,19 +204,23 @@ static int Open( vlc_object_t *p_this ) p_access->info.b_prebuffered = VLC_FALSE; MALLOC_ERR( p_access->p_sys, access_sys_t ); p_sys = p_access->p_sys; - p_sys->fd = net_OpenUDP( p_access, psz_bind_addr, i_bind_port, - psz_server_addr, i_server_port ); - if( p_sys->fd < 0 ) + p_sys->fd = net_Open( p_access, psz_bind_addr, i_bind_port, + psz_server_addr, i_server_port, fam, SOCK_DGRAM, proto ); + free (psz_name); + if( p_sys->fd == -1 ) { msg_Err( p_access, "cannot open socket" ); - free( psz_name ); free( p_sys ); return VLC_EGENERIC; } - free( psz_name ); net_StopSend( p_sys->fd ); +#ifdef UDPLITE_RECV_CSCOV + if (proto == IPPROTO_UDPLITE) + setsockopt (p_sys->fd, SOL_UDPLITE, UDPLITE_RECV_CSCOV, &cscov, sizeof (cscov)); +#endif + /* FIXME */ p_sys->i_mtu = var_CreateGetInteger( p_access, "mtu" ); if( p_sys->i_mtu <= 1 ) diff --git a/src/network/udp.c b/src/network/udp.c index b86948b16f..70d18566ba 100644 --- a/src/network/udp.c +++ b/src/network/udp.c @@ -618,25 +618,27 @@ int __net_ConnectUDP( vlc_object_t *p_this, const char *psz_host, int i_port, /***************************************************************************** - * __net_OpenUDP: + * __net_OpenDgram: ***************************************************************************** - * Open a UDP connection and return a handle + * OpenDgram a datagram socket and return a handle *****************************************************************************/ -int __net_OpenUDP( vlc_object_t *obj, const char *psz_bind, int i_bind, - const char *psz_server, int i_server ) +int __net_OpenDgram( vlc_object_t *obj, const char *psz_bind, int i_bind, + const char *psz_server, int i_server, + int family, int protocol ) { struct addrinfo hints, *loc, *rem; int val; if( !*psz_server ) - return net_ListenUDP1 (obj, psz_bind, i_bind); + return net_ListenSingle (obj, psz_bind, i_bind, + family, SOCK_DGRAM, protocol); msg_Dbg( obj, "net: connecting to [%s]:%d from [%s]:%d", psz_server, i_server, psz_bind, i_bind ); memset (&hints, 0, sizeof (hints)); + hints.ai_family = family; hints.ai_socktype = SOCK_DGRAM; - hints.ai_protocol = IPPROTO_UDP; hints.ai_flags = AI_PASSIVE; val = vlc_getaddrinfo (obj, psz_server, i_server, &hints, &rem); @@ -659,7 +661,7 @@ int __net_OpenUDP( vlc_object_t *obj, const char *psz_bind, int i_bind, for (struct addrinfo *ptr = loc; ptr != NULL; ptr = ptr->ai_next) { int fd = net_Socket (obj, ptr->ai_family, ptr->ai_socktype, - ptr->ai_protocol); + protocol ?: ptr->ai_protocol); if (fd == -1) continue; // usually, address family not supported -- 2.39.2