From d381eae94f356438ff578090640b2254759cde17 Mon Sep 17 00:00:00 2001 From: hyc Date: Wed, 30 Dec 2009 08:17:27 +0000 Subject: [PATCH] Add 'ask' param back to HashSWF, expose HandlePacket as RTMP_ClientPacket git-svn-id: svn://svn.mplayerhq.hu/rtmpdump/trunk@144 400ebc74-4327-4243-bc38-086b20814532 --- hashswf.c | 5 +++- rtmp.c | 9 +++---- rtmp.h | 3 ++- rtmpdump.c | 2 +- rtmpsuck.c | 72 +++++++++++++++++++++++++++++++++++++++++++++--------- streams.c | 2 +- 6 files changed, 72 insertions(+), 21 deletions(-) diff --git a/hashswf.c b/hashswf.c index 8ad006b..779d606 100644 --- a/hashswf.c +++ b/hashswf.c @@ -222,7 +222,7 @@ leave: #define HEX2BIN(a) (((a)&0x40)?((a)&0xf)+9:((a)&0xf)) int -RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash) +RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash, int ask) { FILE *f = NULL; char *path, *home, date[64]; @@ -291,6 +291,9 @@ RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash) } } + if (got && !ask) + return 0; + in.first = 1; in.date = date; HMAC_CTX_init(&ctx); diff --git a/rtmp.c b/rtmp.c index 061007f..2efa0a8 100644 --- a/rtmp.c +++ b/rtmp.c @@ -93,7 +93,6 @@ static bool SendPlay(RTMP * r); static bool SendSeek(RTMP * r, double dTime); static bool SendBytesReceived(RTMP * r); -static int HandlePacket(RTMP * r, RTMPPacket * packet); static int HandleInvoke(RTMP * r, const char *body, unsigned int nBodySize); static bool HandleMetadata(RTMP * r, char *body, unsigned int len); static void HandleChangeChunkSize(RTMP * r, const RTMPPacket * packet); @@ -495,7 +494,7 @@ RTMP_ConnectStream(RTMP * r, double seekTime, uint32_t dLength) break; } - HandlePacket(r, &packet); + RTMP_ClientPacket(r, &packet); RTMPPacket_Free(&packet); } } @@ -555,7 +554,7 @@ RTMP_GetNextMediaPacket(RTMP * r, RTMPPacket * packet) continue; } - bHasMediaPacket = HandlePacket(r, packet); + bHasMediaPacket = RTMP_ClientPacket(r, packet); if (!bHasMediaPacket) { @@ -587,8 +586,8 @@ RTMP_GetNextMediaPacket(RTMP * r, RTMPPacket * packet) return bHasMediaPacket; } -static int -HandlePacket(RTMP * r, RTMPPacket * packet) +int +RTMP_ClientPacket(RTMP * r, RTMPPacket * packet) { int bHasMediaPacket = 0; switch (packet->m_packetType) diff --git a/rtmp.h b/rtmp.h index c08f386..98fd66e 100644 --- a/rtmp.h +++ b/rtmp.h @@ -198,6 +198,7 @@ bool RTMP_ConnectStream(RTMP *r, double seekTime, uint32_t dLength); bool RTMP_ReconnectStream(RTMP *r, int bufferTime, double seekTime, uint32_t dLength); void RTMP_DeleteStream(RTMP *r); int RTMP_GetNextMediaPacket(RTMP *r, RTMPPacket *packet); +int RTMP_ClientPacket(RTMP *r, RTMPPacket *packet); void RTMP_Init(RTMP *r); void RTMP_Close(RTMP *r); @@ -211,7 +212,7 @@ bool RTMP_FindFirstMatchingProperty(AMFObject *obj, const AVal *name, /* hashswf.c */ #define HASHLEN 32 -int RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash); +int RTMP_HashSWF(const char *url, unsigned int *size, unsigned char *hash, int ask); #endif #endif diff --git a/rtmpdump.c b/rtmpdump.c index d27e272..1d857d6 100644 --- a/rtmpdump.c +++ b/rtmpdump.c @@ -1284,7 +1284,7 @@ main(int argc, char **argv) } case 'W': STR2AVAL(swfUrl, optarg); - if (RTMP_HashSWF(optarg, &swfSize, hash) == 0) + if (RTMP_HashSWF(optarg, &swfSize, hash, 1) == 0) { swfHash.av_val = (char *)hash; swfHash.av_len = HASHLEN; diff --git a/rtmpsuck.c b/rtmpsuck.c index a278a51..1e8a468 100644 --- a/rtmpsuck.c +++ b/rtmpsuck.c @@ -110,6 +110,8 @@ FILE *netstackdump = NULL; FILE *netstackdump_read = NULL; #endif +#define BUFFERTIME (4*60*60*1000) /* 4 hours */ + #define SAVC(x) static const AVal av_##x = AVC(#x) SAVC(app); @@ -299,6 +301,11 @@ ServeInvoke(STREAMING_SERVER *server, RTMPPacket *pack, const char *body) for (p=file; *p; p++) if (*p == '/') *p = '_'; + else if (*p == '?') + { + *p = '\0'; + break; + } LogPrintf("Playpath: %.*s, writing to %s\n", server->rc.Link.playpath.av_len, server->rc.Link.playpath.av_val, file); server->out = fopen(file, "wb"); @@ -664,6 +671,7 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin RTMPPacket pc = { 0 }, ps = { 0 }; char *buf; unsigned int buflen = 131072; + bool paused = false; // timeout for http requests fd_set rfds; @@ -708,8 +716,8 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin } /* We have our own timeout in select() */ - server->rc.Link.timeout = 1; - server->rs.Link.timeout = 1; + server->rc.Link.timeout = 10; + server->rs.Link.timeout = 10; while (RTMP_IsConnected(&server->rs) || RTMP_IsConnected(&server->rc)) { int n; @@ -738,12 +746,17 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin if (select(n + 1, &rfds, NULL, NULL, &tv) <= 0) { - /* FIXME: Need to get the ToggleStream support in place */ - /* if (!server->out || !RTMP_ToggleStream(&server->rc)) */ + if (server->out && server->rc.m_mediaChannel && !paused) { - Log(LOGERROR, "Request timeout/select failed, ignoring request"); - goto cleanup; + server->rc.m_pauseStamp = server->rc.m_channelTimestamp[server->rc.m_mediaChannel]; + if (RTMP_ToggleStream(&server->rc)) + { + paused = true; + continue; + } } + Log(LOGERROR, "Request timeout/select failed, ignoring request"); + goto cleanup; } if (FD_ISSET(server->rs.m_socket, &rfds)) sr = 1; @@ -766,6 +779,31 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin server->rc.m_outChunkSize = server->rs.m_inChunkSize; } } + /* ctrl */ + else if (ps.m_packetType == 0x04) + { + short nType = AMF_DecodeInt16(ps.m_body); + /* UpdateBufferMS */ + if (nType == 0x03) + { + char *ptr = ps.m_body+2; + int id; + int len; + id = AMF_DecodeInt32(ptr); + /* Assume the interesting media is on a non-zero stream */ + if (id) + { + len = AMF_DecodeInt32(ptr+4); + /* request a big buffer */ + if (len < BUFFERTIME) + { + AMF_EncodeInt32(ptr+4, ptr+8, BUFFERTIME); + } + Log(LOGDEBUG, "%s, client: BufferTime change in stream %d to %d", __FUNCTION__, + id, len); + } + } + } else if (!server->out && (ps.m_packetType == 0x11 || ps.m_packetType == 0x14)) ServePacket(server, &ps); RTMP_SendPacket(&server->rc, &ps, false); @@ -779,6 +817,13 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin if (RTMPPacket_IsReady(&pc)) { int sendit = 1; + if (paused) + { + if (pc.m_nTimeStamp <= server->rc.m_mediaStamp) + continue; + paused = 0; + server->rc.m_pausing = 0; + } /* change chunk size */ if (pc.m_packetType == 0x01) { @@ -804,7 +849,8 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin pc.m_packetType == 0x08 || pc.m_packetType == 0x09 || pc.m_packetType == 0x12 || - pc.m_packetType == 0x16)) + pc.m_packetType == 0x16) && + RTMP_ClientPacket(&server->rc, &pc)) { int len = WriteStream(&buf, &buflen, &server->stamp, &pc); if (len > 0 && fwrite(buf, 1, len, server->out) != len) @@ -814,11 +860,11 @@ void doServe(STREAMING_SERVER * server, // server socket and state (our listenin pc.m_packetType == 0x11 || pc.m_packetType == 0x14)) { - if (ServePacket(server, &pc)) - { - fclose(server->out); - server->out = NULL; - } + if (ServePacket(server, &pc)) + { + fclose(server->out); + server->out = NULL; + } } if (sendit && RTMP_IsConnected(&server->rs)) @@ -994,6 +1040,8 @@ main(int argc, char **argv) LogPrintf("RTMP Proxy Server %s\n", RTMPDUMP_PROXY_VERSION); LogPrintf("(c) 2009 Andrej Stepanchuk, Howard Chu; license: GPL\n\n"); + debuglevel = LOGDEBUG; + if (argc > 1 && !strcmp(argv[1], "-z")) debuglevel = LOGALL; diff --git a/streams.c b/streams.c index 34b92c1..7067455 100644 --- a/streams.c +++ b/streams.c @@ -942,7 +942,7 @@ ParseOption(char opt, char *arg, RTMP_REQUEST * req) unsigned char hash[HASHLEN]; STR2AVAL(req->swfUrl, arg); - if (RTMP_HashSWF(arg, &req->swfSize, hash) == 0) + if (RTMP_HashSWF(arg, &req->swfSize, hash, 1) == 0) { req->swfHash.av_val = malloc(HASHLEN); req->swfHash.av_len = HASHLEN; -- 2.40.0