Copyright 2009 The Flvstreamer Team
http://rtmpdump.mplayerhq.hu/
+20 July 2011
+- add NetStream.Authenticate.UsherToken for Justin.tv
+
11 July 2011, v2.4
- add RTMPE type 9 handshake support
-.TH LIBRTMP 3 "2010-07-03" "RTMPDump v2.3"
-.\" Copyright 2010 Howard Chu.
+.TH LIBRTMP 3 "2011-07-20" "RTMPDump v2.4"
+.\" Copyright 2011 Howard Chu.
.\" Copying permitted according to the GNU General Public License V2.
.SH NAME
librtmp \- RTMPDump Real-Time Messaging Protocol API
Key for SecureToken response, used if the server requires SecureToken
authentication.
.TP
+.BI jtv= JSON
+JSON token used by legacy Justin.tv servers. Invokes NetStream.Authenticate.UsherToken
+.TP
.BI swfVfy= 0|1
If the value is 1 or TRUE, the SWF player is retrieved from the
specified
static int SendFCSubscribe(RTMP *r, AVal *subscribepath);
static int SendPlay(RTMP *r);
static int SendBytesReceived(RTMP *r);
+static int SendUsherToken(RTMP *r, AVal *usherToken);
#if 0 /* unused */
static int SendBGHasStream(RTMP *r, double dId, AVal *playpath);
uint32_t swfSize,
AVal *flashVer,
AVal *subscribepath,
+ AVal *usherToken,
int dStart,
int dStop, int bLiveStream, long int timeout)
{
RTMP_Log(RTMP_LOGDEBUG, "auth : %s", auth->av_val);
if (subscribepath && subscribepath->av_val)
RTMP_Log(RTMP_LOGDEBUG, "subscribepath : %s", subscribepath->av_val);
+ if (usherToken && usherToken->av_val)
+ RTMP_Log(RTMP_LOGDEBUG, "NetStream.Authenticate.UsherToken : %s", usherToken->av_val);
if (flashVer && flashVer->av_val)
RTMP_Log(RTMP_LOGDEBUG, "flashVer : %s", flashVer->av_val);
if (dStart > 0)
r->Link.flashVer = RTMP_DefaultFlashVer;
if (subscribepath && subscribepath->av_len)
r->Link.subscribepath = *subscribepath;
+ if (usherToken && usherToken->av_len)
+ r->Link.usherToken = *usherToken;
r->Link.seekTime = dStart;
r->Link.stopTime = dStop;
if (bLiveStream)
"Stream is live, no seeking possible" },
{ AVC("subscribe"), OFF(Link.subscribepath), OPT_STR, 0,
"Stream to subscribe to" },
+ { AVC("jtv"), OFF(Link.usherToken), OPT_STR, 0,
+ "Justin.tv authentication token" },
{ AVC("token"), OFF(Link.token), OPT_STR, 0,
"Key for SecureToken response" },
{ AVC("swfVfy"), OFF(Link.lFlags), OPT_BOOL, RTMP_LF_SWFV,
return RTMP_SendPacket(r, &packet, TRUE);
}
+//Justin.tv specific authentication
+static const AVal av_NetStream_Authenticate_UsherToken = AVC("NetStream.Authenticate.UsherToken"); //SAVC() isn't suitable for that
+
+static int
+SendUsherToken(RTMP *r, AVal *usherToken)
+{
+ RTMPPacket packet;
+ char pbuf[1024], *pend = pbuf + sizeof(pbuf);
+ char *enc;
+ packet.m_nChannel = 0x03; /* control channel (invoke) */
+ packet.m_headerType = RTMP_PACKET_SIZE_MEDIUM;
+ packet.m_packetType = RTMP_PACKET_TYPE_INVOKE;
+ packet.m_nTimeStamp = 0;
+ packet.m_nInfoField2 = 0;
+ packet.m_hasAbsTimestamp = 0;
+ packet.m_body = pbuf + RTMP_MAX_HEADER_SIZE;
+
+ RTMP_Log(RTMP_LOGDEBUG, "UsherToken: %s", usherToken->av_val);
+ enc = packet.m_body;
+ enc = AMF_EncodeString(enc, pend, &av_NetStream_Authenticate_UsherToken);
+ enc = AMF_EncodeNumber(enc, pend, ++r->m_numInvokes);
+ *enc++ = AMF_NULL;
+ enc = AMF_EncodeString(enc, pend, usherToken);
+
+ if (!enc)
+ return FALSE;
+
+ packet.m_nBodySize = enc - packet.m_body;
+
+ return RTMP_SendPacket(r, &packet, FALSE);
+}
+/******************************************/
+
SAVC(releaseStream);
static int
if (!(r->Link.protocol & RTMP_FEATURE_WRITE))
{
+ /* Authenticate on Justin.tv legacy servers before sending FCSubscribe */
+ if (r->Link.usherToken.av_len)
+ SendUsherToken(r, &r->Link.usherToken);
/* Send the FCSubscribe if live stream or if subscribepath is set */
if (r->Link.subscribepath.av_len)
SendFCSubscribe(r, &r->Link.subscribepath);
AVal auth;
AVal flashVer;
AVal subscribepath;
+ AVal usherToken;
AVal token;
AMFObject extras;
int edepth;
uint32_t swfSize,
AVal *flashVer,
AVal *subscribepath,
+ AVal *usherToken,
int dStart,
int dStop, int bLiveStream, long int timeout);
-.TH RTMPDUMP 1 "2010-05-02" "RTMPDump v2.2e"
-.\" Copyright 2010 Howard Chu.
+.TH RTMPDUMP 1 "2011-07-20" "RTMPDump v2.4"
+.\" Copyright 2011 Howard Chu.
.\" Copying permitted according to the GNU General Public License V2.
.SH NAME
rtmpdump \- RTMP streaming media client
[\c
.BI \-T \ key\fR]
[\c
+.BI \-j \ JSON\fR]
+[\c
.BI \-w \ swfHash\fR]
[\c
.BI \-x \ swfSize\fR]
Key for SecureToken response, used if the server requires SecureToken
authentication.
.TP
+\fB\-\-jtv \-j\fP\ \fIJSON\fP
+JSON token used by legacy Justin.tv servers. Invokes NetStream.Authenticate.UsherToken
+.TP
\fB\-\-swfhash \-w\fP\ \fIhexstring\fP
SHA256 hash of the decompressed SWF file. This option may be needed if
the server uses SWF Verification, but see the
("--stop|-B num Stop at num seconds into stream\n");
RTMP_LogPrintf
("--token|-T key Key for SecureToken response\n");
+ RTMP_LogPrintf
+ ("--jtv|-j JSON Authentication token for Justin.tv legacy servers\n");
RTMP_LogPrintf
("--hashes|-# Display progress with hashes, not with the byte counter\n");
RTMP_LogPrintf
AVal hostname = { 0, 0 };
AVal playpath = { 0, 0 };
AVal subscribepath = { 0, 0 };
+ AVal usherToken = { 0, 0 }; //Justin.tv auth token
int port = -1;
int protocol = RTMP_PROTOCOL_UNDEFINED;
int retries = 0;
{"debug", 0, NULL, 'z'},
{"quiet", 0, NULL, 'q'},
{"verbose", 0, NULL, 'V'},
+ {"jtv", 1, NULL, 'j'},
{0, 0, 0, 0}
};
while ((opt =
getopt_long(argc, argv,
- "hVveqzr:s:t:p:a:b:f:o:u:C:n:c:l:y:Ym:k:d:A:B:T:w:x:W:X:S:#",
+ "hVveqzr:s:t:p:a:b:f:o:u:C:n:c:l:y:Ym:k:d:A:B:T:w:x:W:X:S:#j:",
longopts, NULL)) != -1)
{
switch (opt)
case 'S':
STR2AVAL(sockshost, optarg);
break;
+ case 'j':
+ STR2AVAL(usherToken, optarg);
+ break;
default:
RTMP_LogPrintf("unknown option: %c\n", opt);
usage(argv[0]);
RTMP_SetupStream(&rtmp, protocol, &hostname, port, &sockshost, &playpath,
&tcUrl, &swfUrl, &pageUrl, &app, &auth, &swfHash, swfSize,
- &flashVer, &subscribepath, dSeek, dStopOffset, bLiveStream, timeout);
+ &flashVer, &subscribepath, &usherToken, dSeek, dStopOffset, bLiveStream, timeout);
/* Try to keep the stream moving if it pauses on us */
if (!bLiveStream && !(protocol & RTMP_FEATURE_HTTP))
-.TH RTMPGW 8 "2010-05-02" "RTMPDump v2.2e"
-.\" Copyright 2010 Howard Chu.
+.TH RTMPGW 8 "2011-07-20" "RTMPDump v2.4"
+.\" Copyright 2011 Howard Chu.
.\" Copying permitted according to the GNU General Public License V2.
.SH NAME
rtmpgw \- RTMP streaming media gateway
[\c
.BI \-T \ key\fR]
[\c
+.BI \-j \ JSON\fR]
+[\c
.BI \-w \ swfHash\fR]
[\c
.BI \-x \ swfSize\fR]
Key for SecureToken response, used if the server requires SecureToken
authentication.
.TP
+\fB\-\-jtv \-j\fP\ \fIJSON\fP
+JSON token used by legacy Justin.tv servers. Invokes NetStream.Authenticate.UsherToken
+.TP
\fB\-\-swfhash \-w\fP\ \fIhexstring\fP
SHA256 hash of the decompressed SWF file. This option may be needed if
the server uses SWF Verification, but see the
AVal flashVer;
AVal token;
AVal subscribepath;
+ AVal usherToken; //Justin.tv auth token
AVal sockshost;
AMFObject extras;
int edepth;
RTMP_Init(&rtmp);
RTMP_SetBufferMS(&rtmp, req.bufferTime);
RTMP_SetupStream(&rtmp, req.protocol, &req.hostname, req.rtmpport, &req.sockshost,
- &req.playpath, &req.tcUrl, &req.swfUrl, &req.pageUrl, &req.app, &req.auth, &req.swfHash, req.swfSize, &req.flashVer, &req.subscribepath, dSeek, req.dStopOffset,
+ &req.playpath, &req.tcUrl, &req.swfUrl, &req.pageUrl, &req.app, &req.auth, &req.swfHash, req.swfSize, &req.flashVer, &req.subscribepath, &req.usherToken, dSeek, req.dStopOffset,
req.bLiveStream, req.timeout);
/* backward compatibility, we always sent this as true before */
if (req.auth.av_len)
case 'z':
RTMP_debuglevel = RTMP_LOGALL;
break;
+ case 'j':
+ STR2AVAL(req->usherToken, arg);
+ break;
default:
RTMP_LogPrintf("unknown option: %c, arg: %s\n", opt, arg);
return FALSE;
{"debug", 0, NULL, 'z'},
{"quiet", 0, NULL, 'q'},
{"verbose", 0, NULL, 'V'},
+ {"jtv", 1, NULL, 'j'},
{0, 0, 0, 0}
};
while ((opt =
getopt_long(argc, argv,
- "hvqVzr:s:t:p:a:f:u:n:c:l:y:m:d:D:A:B:T:g:w:x:W:X:S:", longopts,
+ "hvqVzr:s:t:p:a:f:u:n:c:l:y:m:d:D:A:B:T:g:w:x:W:X:S:j:", longopts,
NULL)) != -1)
{
switch (opt)
("--stop|-B num Stop at num seconds into stream\n");
RTMP_LogPrintf
("--token|-T key Key for SecureToken response\n");
+ RTMP_LogPrintf
+ ("--jtv|-j JSON Authentication token for Justin.tv legacy servers\n");
RTMP_LogPrintf
("--buffer|-b Buffer time in milliseconds (default: %lu)\n\n",
defaultRTMPRequest.bufferTime);
AVal swfHash;
AVal flashVer;
AVal subscribepath;
+ AVal usherToken;
uint32_t swfSize;
uint32_t dStartOffset;