/*
* Copyright (C) 2000-2003 the xine project
*
* This file is part of xine, a free video player.
*
* xine is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* xine is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
*
* $Id: mms.c,v 1.2 2005/12/12 09:24:19 theuraeus Exp $
*
* demultiplexer for asf streams
*
* based on ffmpeg's
* ASF compatible encoder and decoder.
* Copyright (c) 2000, 2001 Gerard Lantau.
*
* GUID list from avifile
* some other ideas from MPlayer
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "unistd.h"
#include <stdio.h>
#include <Winsock2.h>
#include <ws2tcpip.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <errno.h>
#include <stdlib.h>
#include <time.h>
#pragma comment (lib,"ws2_32.lib")
#if defined(HAVE_ICONV) && defined(HAVE_LANGINFO_CODESET)
#define USE_ICONV
#include <iconv.h>
#include <locale.h>
#include <langinfo.h>
#endif
/********** logging **********/
#define LOG_MODULE "mms"
#define LOG_VERBOSE
//#ifdef DEBUG
# define lprintf printf
//#else
//# define lprintf(x...)
//#endif
#define __MMS_C__
#include "bswap.h"
#include "mms.h"
#include "asfheader.h"
#include "uri.h"
/*
* mms specific types
*/
#define MMST_PORT 1755
#define BUF_SIZE 102400
#define CMD_HEADER_LEN 40
#define CMD_PREFIX_LEN 8
#define CMD_BODY_LEN 1024
#define ASF_HEADER_LEN (8192 * 2)
#define MMS_PACKET_ERR 0
#define MMS_PACKET_COMMAND 1
#define MMS_PACKET_ASF_HEADER 2
#define MMS_PACKET_ASF_PACKET 3
#define ASF_HEADER_PACKET_ID_TYPE 2
#define ASF_MEDIA_PACKET_ID_TYPE 4
typedef struct mms_buffer_s mms_buffer_t;
struct mms_buffer_s {
uint8_t *buffer;
int pos;
};
typedef struct mms_packet_header_s mms_packet_header_t;
struct mms_packet_header_s {
uint32_t packet_len;
uint8_t flags;
uint8_t packet_id_type;
uint32_t packet_seq;
};
typedef struct mms_stream_s mms_stream_t;
struct mms_stream_s {
int stream_id;
int stream_type;
uint32_t bitrate;
uint32_t bitrate_pos;
};
struct mms_s {
/* FIXME: de-xine-ification */
void *custom_data;
int s;
/* url parsing */
char *url;
char *proto;
char *host;
int port;
char *user;
char *password;
char *uri;
/* command to send */
char scmd[CMD_HEADER_LEN + CMD_BODY_LEN];
char *scmd_body; /* pointer to &scmd[CMD_HEADER_LEN] */
int scmd_len; /* num bytes written in header */
char str[1024]; /* scratch buffer to built strings */
/* receive buffer */
uint8_t buf[BUF_SIZE];
int buf_size;
int buf_read;
off_t buf_packet_seq_offset; /* packet sequence offset residing in
buf */
uint8_t asf_header[ASF_HEADER_LEN];
uint32_t asf_header_len;
uint32_t asf_header_read;
int seq_num;
int num_stream_ids;
mms_stream_t streams[ASF_MAX_NUM_STREAMS];
uint8_t packet_id_type;
off_t start_packet_seq; /* for live streams != 0, need to keep it around */
int need_discont; /* whether we need to set start_packet_seq */
uint32_t asf_packet_len;
uint64_t file_len;
double time_len; /* playback time in 100 nanosecs (10^-7) */
double ftime_len;//forward time
uint64_t preroll;
uint64_t asf_num_packets;
char guid[37];
int bandwidth;
int has_audio;
int has_video;
int live_flag;
int seekable;
off_t current_pos;
int eos;
};
//read the stream
static off_t fallback_io_read(void *data, int socket, char *buf, off_t num)
{
off_t len = 0, ret;
/* lprintf("%d\n", fallback_io_select(data, socket, MMS_IO_READ_READY, 1000)); */
errno = 0;
while (len < num)
{
ret = (off_t)recv(socket,buf+len,num - len,0);
if(ret == 0)
break; /* EOF */
if(ret < 0)
switch(errno)
{
case EAGAIN:
// lprintf("len == %lld\n", (long int) len);
break;
default:
// lprintf("len == %lld\n", (long int) len);
perror(NULL);
/* if already read something, return it, we will fail next time */
return len ? len : ret;
}
len += ret;
}
// lprintf("ret len == %lld\nnum == %lld\n", (long int) len, (long int) num);
return len;
}
//send the command
static off_t fallback_io_write(void *data, int socket, char *buf, off_t num)
{
return (off_t)send(socket,buf,num,0);
}
//connect the site
static int fallback_io_tcp_connect(void *data, const char *host, int port)
{
WORD wVersionRequested;
WSADATA wsaData;
int err;
struct hostent *h;
int i, s;
wVersionRequested = MAKEWORD( 1, 1 );
err = WSAStartup( wVersionRequested, &wsaData );
if ( err != 0 ) {
return -1;
}
if ( LOBYTE( wsaData.wVersion ) != 1 ||
HIBYTE( wsaData.wVersion ) != 1 ) {
WSACleanup();
return -1;
}
h = gethostbyname(host);
if (h == NULL) {
/* fprintf(stderr, "unable to resolve host: %s\n", host); */
return -1;
}
s = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
if (s == -1) {
/* fprintf(stderr, "failed to create socket: %s", strerror(errno)); */
return -1;
}
for (i = 0; h->h_addr_list[i]; i++) {
struct in_addr ia;
struct sockaddr_in sin;
memcpy (&ia, h->h_addr_list[i], 4);
sin.sin_family = AF_INET;
sin.sin_addr = ia;
sin.sin_port = htons(port);
if (connect(s, (struct sockaddr *)&sin, sizeof(sin)) ==-1 ) {
/* FIXME: de-xine-ification */
/* _x_message(stream, XINE_MSG_CONNECTION_REFUSED, strerror(errno), NULL); */
closesocket(s);
continue;
}
return s;
}
return -1;
}
static mms_io_t default_io = {
NULL,
NULL,
&fallback_io_read,
NULL,
&fallback_io_write,
NULL,
&fallback_io_tcp_connect,
NULL,
};
#define io_connect(io, arg1,arg2) default_io.connect(NULL, arg1,arg2)
#define io_write(io, arg1,arg2,arg3) default_io.write(NULL , arg1,arg2,arg3)
#define io_read(io, arg1,arg2,arg3) default_io.read(NULL ,arg1,arg2,arg3 )
static void mms_buffer_init (mms_buffer_t *mms_buffer, uint8_t *buffer) {
mms_buffer->buffer = buffer;
mms_buffer->pos = 0;
}
static void mms_buffer_put_8 (mms_buffer_t *mms_buffer, uint8_t value) {
mms_buffer->buffer[mms_buffer->pos] = value & 0xff;
mms_buffer->pos += 1;
}
#if 0
static void mms_buffer_put_16 (mms_buffer_t *mms_buffer, uint16_t value) {
mms_buffer->buffer[mms_buffer->pos] = value & 0xff;
mms_buffer->buffer[mms_buffer->pos + 1] = (value >> 8) & 0xff;
mms_buffer->pos += 2;
}
#endif
static void mms_buffer_put_32 (mms_buffer_t *mms_buffer, uint32_t value) {
mms_buffer->buffer[mms_buffer->pos] = value & 0xff;
mms_buffer->buffer[mms_buffer->pos + 1] = (value >> 8) & 0xff;
mms_buffer->buffer[mms_buffer->pos + 2] = (value >> 16) & 0xff;
mms_buffer->buffer[mms_buffer->pos + 3] = (value >> 24) & 0xff;
mms_buffer->pos += 4;
}
static int get_guid (unsigned char *buffer, int offset) {
int i;
GUID g;
g.Data1 = LE_32(buffer + offset);
g.Data2 = LE_16(buffer + offset + 4);
g.Data3 = LE_16(buffer + offset + 6);
for(i = 0; i < 8; i++) {
g.Data4[i] = buffer[offset + 8 + i];
}
for (i = 1; i < GUID_END; i++) {
if (!memcmp(&g, &guids[i].guid, sizeof(GUID))) {
// lprintf("GUID: %s\n", guids[i].name);
return i;
}
}
/* lprintf("unknown GUID: 0x%
没有合适的资源?快使用搜索试试~ 我知道了~
windows系统下的mms流媒体下载函数
共20个文件
h:11个
c:4个
opt:1个
4星 · 超过85%的资源 需积分: 10 182 下载量 168 浏览量
2009-10-11
13:56:46
上传
评论 1
收藏 50KB ZIP 举报
温馨提示
此函数为修改的开源的libmms包,能够实现mms流媒体协议下载。希望能给大家的编程带来用处!
资源推荐
资源详情
资源评论
收起资源包目录
mmstestVC.zip (20个子文件)
mmstest
bswap.h 4KB
mmstest.opt 54KB
mms.c 39KB
mmstest.c 1KB
mmstest.dsw 539B
asfheader.h 9KB
uri.h 3KB
inttypes.h 8KB
unistd.h 200B
mms.h 2KB
mms_config.h 144B
mmsx.c 3KB
mmsio.h 4KB
config.h 1KB
mmstest.plg 4KB
mmstest.dsp 4KB
mmstest.ncb 81KB
uri.c 18KB
stdint.h 7KB
mmsx.h 2KB
共 20 条
- 1
flytreeleft
- 粉丝: 38
- 资源: 18
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功
- 1
- 2
- 3
- 4
前往页