Toggle navigation
Toggle navigation
此项目
正在载入...
Sign in
胡斌
/
srs
转到一个项目
Toggle navigation
项目
群组
代码片段
帮助
Toggle navigation pinning
Project
Activity
Repository
Pipelines
Graphs
Issues
0
Merge Requests
0
Wiki
Network
Create a new issue
Builds
Commits
Authored by
winlin
2014-05-28 19:01:47 +0800
Browse Files
Options
Browse Files
Download
Email Patches
Plain Diff
Commit
22968c85df33a23413a14180e518879acbc5cc00
22968c85
1 parent
4970664e
supprt inject flv
隐藏空白字符变更
内嵌
并排对比
正在显示
10 个修改的文件
包含
309 行增加
和
180 行删除
trunk/research/librtmp/srs_flv_codec.h
trunk/research/librtmp/srs_flv_injecter.c
trunk/research/librtmp/srs_flv_parser.c
trunk/research/librtmp/srs_ingest_flv.c
trunk/src/kernel/srs_kernel_flv.cpp
trunk/src/kernel/srs_kernel_flv.hpp
trunk/src/libs/srs_librtmp.cpp
trunk/src/libs/srs_librtmp.hpp
trunk/src/rtmp/srs_protocol_amf0.cpp
trunk/src/rtmp/srs_protocol_amf0.hpp
trunk/research/librtmp/srs_flv_codec.h
已删除
100644 → 0
查看文件 @
4970664
/*
The MIT License (MIT)
Copyright (c) 2013-2014 winlin
Permission is hereby granted, free of charge, to any person obtaining a copy of
this software and associated documentation files (the "Software"), to deal in
the Software without restriction, including without limitation the rights to
use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
the Software, and to permit persons to whom the Software is furnished to do so,
subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
*/
#ifndef SRS_RESEARH_FLV_CODEC_HPP
#define SRS_RESEARH_FLV_CODEC_HPP
/*
#include "srs_flv_codec.h"
*/
#include <unistd.h>
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
#define ERROR_FLV_CODEC_EOF 100
int
open_flv_file
(
char
*
in_flv_file
)
{
return
open
(
in_flv_file
,
O_RDONLY
);
}
void
close_flv_file
(
int
fd
)
{
if
(
fd
>
0
)
{
close
(
fd
);
}
}
int
flv_open_ic
(
int
flv_fd
)
{
int
ret
=
0
;
char
h
[
13
];
// 9+4
if
(
read
(
flv_fd
,
h
,
sizeof
(
h
))
!=
sizeof
(
h
))
{
ret
=
-
1
;
trace
(
"read flv header failed. ret=%d"
,
ret
);
return
ret
;
}
if
(
h
[
0
]
!=
'F'
||
h
[
1
]
!=
'L'
||
h
[
2
]
!=
'V'
)
{
ret
=
-
1
;
trace
(
"input is not a flv file. ret=%d"
,
ret
);
return
ret
;
}
return
ret
;
}
int
flv_read_packet
(
int
flv_fd
,
int
*
type
,
u_int32_t
*
timestamp
,
char
**
data
,
int
*
size
)
{
int
ret
=
0
;
char
th
[
11
];
// tag header
char
ts
[
4
];
// tag size
int32_t
data_size
=
0
;
u_int32_t
time
=
0
;
char
*
pp
;
// read tag header
if
((
ret
=
read
(
flv_fd
,
th
,
sizeof
(
th
)))
!=
sizeof
(
th
))
{
if
(
ret
==
0
)
{
return
ERROR_FLV_CODEC_EOF
;
}
ret
=
-
1
;
trace
(
"read flv tag header failed. ret=%d"
,
ret
);
return
ret
;
}
// Reserved UB [2]
// Filter UB [1]
// TagType UB [5]
*
type
=
(
int
)(
th
[
0
]
&
0x1F
);
// DataSize UI24
pp
=
(
char
*
)
&
data_size
;
pp
[
2
]
=
th
[
1
];
pp
[
1
]
=
th
[
2
];
pp
[
0
]
=
th
[
3
];
// Timestamp UI24
pp
=
(
char
*
)
&
time
;
pp
[
2
]
=
th
[
4
];
pp
[
1
]
=
th
[
5
];
pp
[
0
]
=
th
[
6
];
// TimestampExtended UI8
pp
[
3
]
=
th
[
7
];
*
timestamp
=
time
;
// check data size.
if
(
data_size
<=
0
)
{
ret
=
-
1
;
trace
(
"invalid data size. size=%d, ret=%d"
,
data_size
,
ret
);
return
ret
;
}
// read tag data.
*
size
=
data_size
;
*
data
=
(
char
*
)
malloc
(
data_size
);
if
((
ret
=
read
(
flv_fd
,
*
data
,
data_size
))
!=
data_size
)
{
if
(
ret
==
0
)
{
return
ERROR_FLV_CODEC_EOF
;
}
ret
=
-
1
;
trace
(
"read flv tag data failed. size=%d, ret=%d"
,
data_size
,
ret
);
return
ret
;
}
// ignore 4bytes tag size.
if
((
ret
=
read
(
flv_fd
,
ts
,
sizeof
(
ts
)))
!=
sizeof
(
ts
))
{
if
(
ret
==
0
)
{
return
ERROR_FLV_CODEC_EOF
;
}
ret
=
-
1
;
trace
(
"read flv tag size failed. ret=%d"
,
ret
);
return
ret
;
}
return
0
;
}
#endif
trunk/research/librtmp/srs_flv_injecter.c
查看文件 @
22968c8
...
...
@@ -34,7 +34,8 @@ gcc srs_flv_injecter.c ../../objs/lib/srs_librtmp.a -g -O0 -lstdc++ -o srs_flv_i
#include "../../objs/include/srs_librtmp.h"
#include "srs_research_public.h"
#include "srs_flv_codec.h"
#define ERROR_INJECTED 10000
int
process
(
const
char
*
in_flv_file
,
const
char
*
out_flv_file
,
srs_flv_t
*
pic
,
srs_flv_t
*
poc
);
int
inject_flv
(
srs_flv_t
ic
,
srs_flv_t
oc
);
...
...
@@ -87,7 +88,12 @@ int main(int argc, char** argv)
if
(
ret
!=
0
)
{
unlink
(
tmp_file
);
trace
(
"error, remove tmp file."
);
if
(
ret
==
ERROR_INJECTED
)
{
ret
=
0
;
trace
(
"file already injected."
);
}
else
{
trace
(
"error, remove tmp file."
);
}
}
else
{
rename
(
tmp_file
,
out_flv_file
);
trace
(
"completed, rename to %s"
,
out_flv_file
);
...
...
@@ -153,25 +159,32 @@ int inject_flv(srs_flv_t ic, srs_flv_t oc)
u_int32_t
timestamp
=
0
;
char
*
data
=
NULL
;
int32_t
size
;
int64_t
offset
=
0
;
// metadata
srs_amf0_t
amf0_name
=
NULL
;
int
amf0_name_size
=
0
;
srs_amf0_t
amf0_data
=
NULL
;
srs_amf0_t
keyframes
=
NULL
;
srs_amf0_t
filepositions
=
NULL
;
srs_amf0_t
times
=
NULL
;
// reset to generate metadata
srs_flv_lseek
(
ic
,
0
);
if
((
ret
=
srs_flv_read_header
(
o
c
,
header
))
!=
0
)
{
if
((
ret
=
srs_flv_read_header
(
i
c
,
header
))
!=
0
)
{
return
ret
;
}
trace
(
"
start inject
flv"
);
trace
(
"
build keyframe infos from
flv"
);
for
(;;)
{
offset
=
srs_flv_tellg
(
ic
);
// tag header
if
((
ret
=
srs_flv_read_tag_header
(
o
c
,
&
type
,
&
size
,
&
timestamp
))
!=
0
)
{
if
((
ret
=
srs_flv_read_tag_header
(
i
c
,
&
type
,
&
size
,
&
timestamp
))
!=
0
)
{
if
(
srs_flv_is_eof
(
ret
))
{
trace
(
"parse completed."
);
return
0
;
break
;
}
trace
(
"flv get packet failed. ret=%d"
,
ret
);
return
ret
;
...
...
@@ -184,16 +197,107 @@ int inject_flv(srs_flv_t ic, srs_flv_t oc)
// TODO: FIXME: mem leak when error.
data
=
(
char
*
)
malloc
(
size
);
if
((
ret
=
srs_flv_read_tag_data
(
o
c
,
data
,
size
))
!=
0
)
{
if
((
ret
=
srs_flv_read_tag_data
(
i
c
,
data
,
size
))
!=
0
)
{
return
ret
;
}
// data tag
if
(
type
==
SRS_RTMP_TYPE_VIDEO
)
{
if
(
!
srs_flv_is_sequence_header
(
data
,
size
)
&&
srs_flv_is_keyframe
(
data
,
size
))
{
srs_amf0_strict_array_append
(
filepositions
,
srs_amf0_create_number
(
offset
));
srs_amf0_strict_array_append
(
times
,
srs_amf0_create_number
(((
double
)
timestamp
)
/
1000
));
}
}
else
if
(
type
==
SRS_RTMP_TYPE_SCRIPT
)
{
if
((
ret
=
parse_metadata
(
data
,
size
,
&
amf0_name
,
&
amf0_data
))
!=
0
)
{
return
ret
;
}
if
(
srs_amf0_is_object
(
amf0_data
))
{
keyframes
=
srs_amf0_object_property
(
amf0_data
,
"keyframes"
);
if
(
keyframes
!=
NULL
)
{
return
0
;
}
keyframes
=
srs_amf0_create_ecma_array
();
srs_amf0_object_property_set
(
amf0_data
,
"keyframes"
,
keyframes
);
filepositions
=
srs_amf0_create_strict_array
();
srs_amf0_object_property_set
(
keyframes
,
"filepositions"
,
filepositions
);
times
=
srs_amf0_create_strict_array
();
srs_amf0_object_property_set
(
keyframes
,
"times"
,
times
);
}
else
if
(
srs_amf0_is_ecma_array
(
amf0_data
))
{
keyframes
=
srs_amf0_ecma_array_property
(
amf0_data
,
"keyframes"
);
if
(
keyframes
!=
NULL
)
{
return
0
;
}
keyframes
=
srs_amf0_create_ecma_array
();
srs_amf0_ecma_array_property_set
(
amf0_data
,
"keyframes"
,
keyframes
);
filepositions
=
srs_amf0_create_strict_array
();
srs_amf0_ecma_array_property_set
(
keyframes
,
"filepositions"
,
filepositions
);
times
=
srs_amf0_create_strict_array
();
srs_amf0_ecma_array_property_set
(
keyframes
,
"times"
,
times
);
}
}
free
(
data
);
}
// reset to write injected file
srs_flv_lseek
(
ic
,
0
);
if
((
ret
=
srs_flv_read_header
(
ic
,
header
))
!=
0
)
{
return
ret
;
}
if
((
ret
=
srs_flv_write_header
(
oc
,
header
))
!=
0
)
{
return
ret
;
}
// write metadata
if
(
amf0_name
!=
NULL
&&
amf0_data
!=
NULL
)
{
amf0_name_size
=
srs_amf0_size
(
amf0_name
);
size
=
amf0_name_size
+
srs_amf0_size
(
amf0_data
);
data
=
(
char
*
)
malloc
(
size
);
if
((
ret
=
srs_amf0_serialize
(
amf0_name
,
data
,
amf0_name_size
))
!=
0
)
{
return
ret
;
}
if
((
ret
=
srs_amf0_serialize
(
amf0_data
,
data
+
amf0_name_size
,
size
-
amf0_name_size
))
!=
0
)
{
return
ret
;
}
if
((
ret
=
srs_flv_write_tag
(
oc
,
SRS_RTMP_TYPE_SCRIPT
,
0
,
data
,
size
))
!=
0
)
{
return
ret
;
}
free
(
data
);
}
trace
(
"build keyframe infos from flv"
);
for
(;;)
{
// tag header
if
((
ret
=
srs_flv_read_tag_header
(
ic
,
&
type
,
&
size
,
&
timestamp
))
!=
0
)
{
if
(
srs_flv_is_eof
(
ret
))
{
trace
(
"parse completed."
);
return
0
;
}
trace
(
"flv get packet failed. ret=%d"
,
ret
);
return
ret
;
}
if
(
size
<=
0
)
{
trace
(
"invalid size=%d"
,
size
);
break
;
}
// TODO: FIXME: mem leak when error.
data
=
(
char
*
)
malloc
(
size
);
if
((
ret
=
srs_flv_read_tag_data
(
ic
,
data
,
size
))
!=
0
)
{
return
ret
;
}
// data tag
if
(
type
==
SRS_RTMP_TYPE_SCRIPT
)
{
continue
;
}
// copy
if
((
ret
=
srs_flv_write_tag
(
oc
,
type
,
timestamp
,
data
,
size
))
!=
0
)
{
return
ret
;
}
free
(
data
);
...
...
trunk/research/librtmp/srs_flv_parser.c
查看文件 @
22968c8
...
...
@@ -34,7 +34,6 @@ gcc srs_ingest_flv.c ../../objs/lib/srs_librtmp.a -g -O0 -lstdc++ -o srs_ingest_
#include "../../objs/include/srs_librtmp.h"
#include "srs_research_public.h"
#include "srs_flv_codec.h"
int
parse_flv
(
srs_flv_t
flv
);
int
main
(
int
argc
,
char
**
argv
)
...
...
trunk/research/librtmp/srs_ingest_flv.c
查看文件 @
22968c8
...
...
@@ -34,9 +34,8 @@ gcc srs_ingest_flv.c ../../objs/lib/srs_librtmp.a -g -O0 -lstdc++ -o srs_ingest_
#include "../../objs/include/srs_librtmp.h"
#include "srs_research_public.h"
#include "srs_flv_codec.h"
int
proxy
(
int
flv_fd
,
srs_rtmp_t
ortmp
);
int
proxy
(
srs_flv_t
flv
,
srs_rtmp_t
ortmp
);
int
connect_oc
(
srs_rtmp_t
ortmp
);
#define RE_PULSE_MS 300
...
...
@@ -59,7 +58,7 @@ int main(int argc, char** argv)
// rtmp handler
srs_rtmp_t
ortmp
;
// flv handler
int
flv_fd
;
srs_flv_t
flv
;
if
(
argc
<=
2
)
{
printf
(
"ingest flv file and publish to RTMP server
\n
"
...
...
@@ -94,8 +93,7 @@ int main(int argc, char** argv)
trace
(
"input: %s"
,
in_flv_file
);
trace
(
"output: %s"
,
out_rtmp_url
);
flv_fd
=
open_flv_file
(
in_flv_file
);
if
(
flv_fd
<=
0
)
{
if
((
flv
=
srs_flv_open_read
(
in_flv_file
))
==
NULL
)
{
ret
=
2
;
trace
(
"open flv file failed. ret=%d"
,
ret
);
return
ret
;
...
...
@@ -103,31 +101,46 @@ int main(int argc, char** argv)
ortmp
=
srs_rtmp_create
(
out_rtmp_url
);
ret
=
proxy
(
flv
_fd
,
ortmp
);
ret
=
proxy
(
flv
,
ortmp
);
trace
(
"ingest flv to RTMP completed"
);
srs_rtmp_destroy
(
ortmp
);
close_flv_file
(
flv_fd
);
srs_flv_close
(
flv
);
return
ret
;
}
int
do_proxy
(
int
flv_fd
,
srs_rtmp_t
ortmp
,
int64_t
re
,
u_int32_t
*
ptimestamp
)
int
do_proxy
(
srs_flv_t
flv
,
srs_rtmp_t
ortmp
,
int64_t
re
,
u_int32_t
*
ptimestamp
)
{
int
ret
=
0
;
// packet data
int
type
,
size
;
char
type
;
int
size
;
char
*
data
=
NULL
;
trace
(
"start ingest flv to RTMP stream"
);
for
(;;)
{
if
((
ret
=
flv_read_packet
(
flv_fd
,
&
type
,
ptimestamp
,
&
data
,
&
size
))
!=
0
)
{
trace
(
"irtmp get packet failed. ret=%d"
,
ret
);
// tag header
if
((
ret
=
srs_flv_read_tag_header
(
flv
,
&
type
,
&
size
,
ptimestamp
))
!=
0
)
{
if
(
srs_flv_is_eof
(
ret
))
{
trace
(
"parse completed."
);
return
0
;
}
trace
(
"flv get packet failed. ret=%d"
,
ret
);
return
ret
;
}
if
(
size
<=
0
)
{
trace
(
"invalid size=%d"
,
size
);
break
;
}
// TODO: FIXME: mem leak when error.
data
=
(
char
*
)
malloc
(
size
);
if
((
ret
=
srs_flv_read_tag_data
(
flv
,
data
,
size
))
!=
0
)
{
return
ret
;
}
verbose
(
"irtmp got packet: type=%s, time=%d, size=%d"
,
srs_type2string
(
type
),
timestamp
,
size
);
if
((
ret
=
srs_write_packet
(
ortmp
,
type
,
*
ptimestamp
,
data
,
size
))
!=
0
)
{
trace
(
"irtmp get packet failed. ret=%d"
,
ret
);
...
...
@@ -142,12 +155,13 @@ int do_proxy(int flv_fd, srs_rtmp_t ortmp, int64_t re, u_int32_t* ptimestamp)
return
ret
;
}
int
proxy
(
int
flv_fd
,
srs_rtmp_t
ortmp
)
int
proxy
(
srs_flv_t
flv
,
srs_rtmp_t
ortmp
)
{
int
ret
=
0
;
u_int32_t
timestamp
=
0
;
if
((
ret
=
flv_open_ic
(
flv_fd
))
!=
0
)
{
char
header
[
13
];
if
((
ret
=
srs_flv_read_header
(
flv
,
header
))
!=
0
)
{
return
ret
;
}
if
((
ret
=
connect_oc
(
ortmp
))
!=
0
)
{
...
...
@@ -156,7 +170,7 @@ int proxy(int flv_fd, srs_rtmp_t ortmp)
int64_t
re
=
re_create
();
ret
=
do_proxy
(
flv
_fd
,
ortmp
,
re
,
&
timestamp
);
ret
=
do_proxy
(
flv
,
ortmp
,
re
,
&
timestamp
);
// for the last pulse, always sleep.
re_cleanup
(
re
,
timestamp
);
...
...
trunk/src/kernel/srs_kernel_flv.cpp
查看文件 @
22968c8
...
...
@@ -207,20 +207,36 @@ int SrsFlvEncoder::write_header()
'F'
,
'L'
,
'V'
,
// Signatures "FLV"
(
char
)
0x01
,
// File version (for example, 0x01 for FLV version 1)
(
char
)
0x00
,
// 4, audio; 1, video; 5 audio+video.
(
char
)
0x00
,
(
char
)
0x00
,
(
char
)
0x00
,
(
char
)
0x09
,
// DataOffset UI32 The length of this header in bytes
(
char
)
0x00
,
(
char
)
0x00
,
(
char
)
0x00
,
(
char
)
0x00
// PreviousTagSize0 UI32 Always 0
(
char
)
0x00
,
(
char
)
0x00
,
(
char
)
0x00
,
(
char
)
0x09
// DataOffset UI32 The length of this header in bytes
};
// flv specification should set the audio and video flag,
// actually in practise, application generally ignore this flag,
// so we generally set the audio/video to 0.
// write 9bytes header.
if
((
ret
=
write_header
(
flv_header
))
!=
ERROR_SUCCESS
)
{
return
ret
;
}
return
ret
;
}
int
SrsFlvEncoder
::
write_header
(
char
flv_header
[
9
])
{
int
ret
=
ERROR_SUCCESS
;
// write data.
if
((
ret
=
_fs
->
write
(
flv_header
,
sizeof
(
flv_header
)
,
NULL
))
!=
ERROR_SUCCESS
)
{
if
((
ret
=
_fs
->
write
(
flv_header
,
9
,
NULL
))
!=
ERROR_SUCCESS
)
{
srs_error
(
"write flv header failed. ret=%d"
,
ret
);
return
ret
;
}
char
pts
[]
=
{
0x00
,
0x00
,
0x00
,
0x00
};
if
((
ret
=
_fs
->
write
(
pts
,
4
,
NULL
))
!=
ERROR_SUCCESS
)
{
return
ret
;
}
return
ret
;
}
...
...
trunk/src/kernel/srs_kernel_flv.hpp
查看文件 @
22968c8
...
...
@@ -92,6 +92,7 @@ public:
* that is, 9+4=13bytes.
*/
virtual
int
write_header
();
virtual
int
write_header
(
char
flv_header
[
9
]);
/**
* write flv metadata.
* serialize from:
...
...
trunk/src/libs/srs_librtmp.cpp
查看文件 @
22968c8
...
...
@@ -491,6 +491,34 @@ int srs_flv_read_tag_data(srs_flv_t flv, char* data, int32_t size)
return
ret
;
}
int
srs_flv_write_header
(
srs_flv_t
flv
,
char
header
[
9
])
{
int
ret
=
ERROR_SUCCESS
;
FlvContext
*
context
=
(
FlvContext
*
)
flv
;
if
((
ret
=
context
->
enc
.
write_header
(
header
))
!=
ERROR_SUCCESS
)
{
return
ret
;
}
return
ret
;
}
int
srs_flv_write_tag
(
srs_flv_t
flv
,
char
type
,
int32_t
time
,
char
*
data
,
int
size
)
{
int
ret
=
ERROR_SUCCESS
;
FlvContext
*
context
=
(
FlvContext
*
)
flv
;
if
(
type
==
SRS_RTMP_TYPE_AUDIO
)
{
return
context
->
enc
.
write_audio
(
time
,
data
,
size
);
}
else
if
(
type
==
SRS_RTMP_TYPE_VIDEO
)
{
return
context
->
enc
.
write_video
(
time
,
data
,
size
);
}
else
{
return
context
->
enc
.
write_metadata
(
data
,
size
);
}
return
ret
;
}
int64_t
srs_flv_tellg
(
srs_flv_t
flv
)
{
FlvContext
*
context
=
(
FlvContext
*
)
flv
;
...
...
@@ -508,6 +536,16 @@ flv_bool srs_flv_is_eof(int error_code)
return
error_code
==
ERROR_SYSTEM_FILE_EOF
;
}
flv_bool
srs_flv_is_sequence_header
(
char
*
data
,
int32_t
size
)
{
return
SrsCodec
::
video_is_sequence_header
((
int8_t
*
)
data
,
(
int
)
size
);
}
flv_bool
srs_flv_is_keyframe
(
char
*
data
,
int32_t
size
)
{
return
SrsCodec
::
video_is_keyframe
((
int8_t
*
)
data
,
(
int
)
size
);
}
srs_amf0_t
srs_amf0_parse
(
char
*
data
,
int
size
,
int
*
nparsed
)
{
int
ret
=
ERROR_SUCCESS
;
...
...
@@ -536,6 +574,21 @@ srs_amf0_t srs_amf0_parse(char* data, int size, int* nparsed)
return
amf0
;
}
srs_amf0_t
srs_amf0_create_number
(
amf0_number
value
)
{
return
SrsAmf0Any
::
number
(
value
);
}
srs_amf0_t
srs_amf0_create_ecma_array
()
{
return
SrsAmf0Any
::
ecma_array
();
}
srs_amf0_t
srs_amf0_create_strict_array
()
{
return
SrsAmf0Any
::
strict_array
();
}
void
srs_amf0_free
(
srs_amf0_t
amf0
)
{
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
amf0
;
...
...
@@ -547,6 +600,30 @@ void srs_amf0_free_bytes(char* data)
srs_freep
(
data
);
}
int
srs_amf0_size
(
srs_amf0_t
amf0
)
{
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
amf0
;
return
any
->
total_size
();
}
int
srs_amf0_serialize
(
srs_amf0_t
amf0
,
char
*
data
,
int
size
)
{
int
ret
=
ERROR_SUCCESS
;
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
amf0
;
SrsStream
stream
;
if
((
ret
=
stream
.
initialize
(
data
,
size
))
!=
ERROR_SUCCESS
)
{
return
ret
;
}
if
((
ret
=
any
->
write
(
&
stream
))
!=
ERROR_SUCCESS
)
{
return
ret
;
}
return
ret
;
}
amf0_bool
srs_amf0_is_string
(
srs_amf0_t
amf0
)
{
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
amf0
;
...
...
@@ -625,6 +702,19 @@ srs_amf0_t srs_amf0_object_property_value_at(srs_amf0_t amf0, int index)
return
(
srs_amf0_t
)
obj
->
value_at
(
index
);
}
srs_amf0_t
srs_amf0_object_property
(
srs_amf0_t
amf0
,
const
char
*
name
)
{
SrsAmf0Object
*
obj
=
(
SrsAmf0Object
*
)
amf0
;
return
(
srs_amf0_t
)
obj
->
get_property
(
name
);
}
void
srs_amf0_object_property_set
(
srs_amf0_t
amf0
,
const
char
*
name
,
srs_amf0_t
value
)
{
SrsAmf0Object
*
obj
=
(
SrsAmf0Object
*
)
amf0
;
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
value
;
obj
->
set
(
name
,
any
);
}
int
srs_amf0_ecma_array_property_count
(
srs_amf0_t
amf0
)
{
SrsAmf0EcmaArray
*
obj
=
(
SrsAmf0EcmaArray
*
)
amf0
;
...
...
@@ -643,16 +733,36 @@ srs_amf0_t srs_amf0_ecma_array_property_value_at(srs_amf0_t amf0, int index)
return
(
srs_amf0_t
)
obj
->
value_at
(
index
);
}
srs_amf0_t
srs_amf0_ecma_array_property
(
srs_amf0_t
amf0
,
const
char
*
name
)
{
SrsAmf0EcmaArray
*
obj
=
(
SrsAmf0EcmaArray
*
)
amf0
;
return
(
srs_amf0_t
)
obj
->
get_property
(
name
);
}
void
srs_amf0_ecma_array_property_set
(
srs_amf0_t
amf0
,
const
char
*
name
,
srs_amf0_t
value
)
{
SrsAmf0EcmaArray
*
obj
=
(
SrsAmf0EcmaArray
*
)
amf0
;
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
value
;
obj
->
set
(
name
,
any
);
}
int
srs_amf0_strict_array_property_count
(
srs_amf0_t
amf0
)
{
SrsAmf0
EcmaArray
*
obj
=
(
SrsAmf0Ecma
Array
*
)
amf0
;
SrsAmf0
StrictArray
*
obj
=
(
SrsAmf0Strict
Array
*
)
amf0
;
return
obj
->
count
();
}
srs_amf0_t
srs_amf0_strict_array_property_at
(
srs_amf0_t
amf0
,
int
index
)
{
SrsAmf0EcmaArray
*
obj
=
(
SrsAmf0EcmaArray
*
)
amf0
;
return
(
srs_amf0_t
)
obj
->
value_at
(
index
);
SrsAmf0StrictArray
*
obj
=
(
SrsAmf0StrictArray
*
)
amf0
;
return
(
srs_amf0_t
)
obj
->
at
(
index
);
}
void
srs_amf0_strict_array_append
(
srs_amf0_t
amf0
,
srs_amf0_t
value
)
{
SrsAmf0StrictArray
*
obj
=
(
SrsAmf0StrictArray
*
)
amf0
;
SrsAmf0Any
*
any
=
(
SrsAmf0Any
*
)
value
;
obj
->
append
(
any
);
}
void
__srs_fill_level_spaces
(
stringstream
&
ss
,
int
level
)
...
...
@@ -735,10 +845,14 @@ char* srs_amf0_human_print(srs_amf0_t amf0, char** pdata, int* psize)
memcpy
(
data
,
str
.
data
(),
str
.
length
());
data
[
str
.
length
()]
=
0
;
*
pdata
=
data
;
*
psize
=
str
.
length
();
if
(
pdata
)
{
*
pdata
=
data
;
}
if
(
psize
)
{
*
psize
=
str
.
length
();
}
return
*
p
data
;
return
data
;
}
#ifdef __cplusplus
...
...
trunk/src/libs/srs_librtmp.hpp
查看文件 @
22968c8
...
...
@@ -165,12 +165,23 @@ int srs_flv_read_header(srs_flv_t flv, char header[9]);
int
srs_flv_read_tag_header
(
srs_flv_t
flv
,
char
*
ptype
,
int32_t
*
pdata_size
,
u_int32_t
*
ptime
);
/* read the tag data. drop the 4bytes previous tag size */
int
srs_flv_read_tag_data
(
srs_flv_t
flv
,
char
*
data
,
int32_t
size
);
/* write flv header to file, auto write the 4bytes zero previous tag size. */
int
srs_flv_write_header
(
srs_flv_t
flv
,
char
header
[
9
]);
/* write flv tag to file, auto write the 4bytes previous tag size */
int
srs_flv_write_tag
(
srs_flv_t
flv
,
char
type
,
int32_t
time
,
char
*
data
,
int
size
);
/* file stream */
/* file stream tellg to get offset */
int64_t
srs_flv_tellg
(
srs_flv_t
flv
);
/* seek file stream, offset is form the start of file */
void
srs_flv_lseek
(
srs_flv_t
flv
,
int64_t
offset
);
/* error code */
/* whether the error code indicates EOF */
flv_bool
srs_flv_is_eof
(
int
error_code
);
/* media codec */
/* whether the video body is sequence header */
flv_bool
srs_flv_is_sequence_header
(
char
*
data
,
int32_t
size
);
/* whether the video body is keyframe */
flv_bool
srs_flv_is_keyframe
(
char
*
data
,
int32_t
size
);
/**
* amf0 codec
...
...
@@ -180,8 +191,14 @@ typedef void* srs_amf0_t;
typedef
int
amf0_bool
;
typedef
double
amf0_number
;
srs_amf0_t
srs_amf0_parse
(
char
*
data
,
int
size
,
int
*
nparsed
);
srs_amf0_t
srs_amf0_create_number
(
amf0_number
value
);
srs_amf0_t
srs_amf0_create_ecma_array
();
srs_amf0_t
srs_amf0_create_strict_array
();
void
srs_amf0_free
(
srs_amf0_t
amf0
);
void
srs_amf0_free_bytes
(
char
*
data
);
/* size and to bytes */
int
srs_amf0_size
(
srs_amf0_t
amf0
);
int
srs_amf0_serialize
(
srs_amf0_t
amf0
,
char
*
data
,
int
size
);
/* type detecter */
amf0_bool
srs_amf0_is_string
(
srs_amf0_t
amf0
);
amf0_bool
srs_amf0_is_boolean
(
srs_amf0_t
amf0
);
...
...
@@ -198,13 +215,18 @@ amf0_number srs_amf0_to_number(srs_amf0_t amf0);
int
srs_amf0_object_property_count
(
srs_amf0_t
amf0
);
const
char
*
srs_amf0_object_property_name_at
(
srs_amf0_t
amf0
,
int
index
);
srs_amf0_t
srs_amf0_object_property_value_at
(
srs_amf0_t
amf0
,
int
index
);
srs_amf0_t
srs_amf0_object_property
(
srs_amf0_t
amf0
,
const
char
*
name
);
void
srs_amf0_object_property_set
(
srs_amf0_t
amf0
,
const
char
*
name
,
srs_amf0_t
value
);
/* ecma array value converter */
int
srs_amf0_ecma_array_property_count
(
srs_amf0_t
amf0
);
const
char
*
srs_amf0_ecma_array_property_name_at
(
srs_amf0_t
amf0
,
int
index
);
srs_amf0_t
srs_amf0_ecma_array_property_value_at
(
srs_amf0_t
amf0
,
int
index
);
srs_amf0_t
srs_amf0_ecma_array_property
(
srs_amf0_t
amf0
,
const
char
*
name
);
void
srs_amf0_ecma_array_property_set
(
srs_amf0_t
amf0
,
const
char
*
name
,
srs_amf0_t
value
);
/* strict array value converter */
int
srs_amf0_strict_array_property_count
(
srs_amf0_t
amf0
);
srs_amf0_t
srs_amf0_strict_array_property_at
(
srs_amf0_t
amf0
,
int
index
);
void
srs_amf0_strict_array_append
(
srs_amf0_t
amf0
,
srs_amf0_t
value
);
/**
* human readable print
* @param pdata, output the heap data,
...
...
trunk/src/rtmp/srs_protocol_amf0.cpp
查看文件 @
22968c8
...
...
@@ -1113,6 +1113,11 @@ SrsAmf0Any* SrsAmf0StrictArray::at(int index)
return
properties
.
at
(
index
);
}
void
SrsAmf0StrictArray
::
append
(
SrsAmf0Any
*
any
)
{
properties
.
push_back
(
any
);
}
int
SrsAmf0Size
::
utf8
(
string
value
)
{
return
2
+
value
.
length
();
...
...
trunk/src/rtmp/srs_protocol_amf0.hpp
查看文件 @
22968c8
...
...
@@ -260,6 +260,7 @@ public:
virtual
int
count
();
// @remark: max index is count().
virtual
SrsAmf0Any
*
at
(
int
index
);
virtual
void
append
(
SrsAmf0Any
*
any
);
};
/**
...
...
请
注册
或
登录
后发表评论