[FFmpeg-trac] #5994(avformat:new): Heap-overflow in rtmppkt.c results Remote Code Execution

FFmpeg trac at avcodec.org
Mon Dec 5 05:44:25 EET 2016


#5994: Heap-overflow in rtmppkt.c results Remote Code Execution
----------------------------------+--------------------------------------
             Reporter:  paulch    |                     Type:  defect
               Status:  new       |                 Priority:  critical
            Component:  avformat  |                  Version:  git-master
             Keywords:            |               Blocked By:
             Blocking:            |  Reproduced by developer:  0
Analyzed by developer:  0         |
----------------------------------+--------------------------------------
 '''Summary of the bug''':
 We managed to find and successfully exploit critical security bug in
 libavformat/rtmppkt.c that results Remote Code Execution in latest version
 of FFmpeg.

 '''Prerequisites:'''
 * Attacker has to reproduce SSRF bug and send RTMP request to his remote
 host. There are multiple ways of doing this already described all over the
 Internet. (For ex. you can trigger SSRF using HLS playlists or the way I
 described earlier in this ​[https://trac.ffmpeg.org/ticket/5991#ticket
 ticket] ).
 * For full exploitation knowledge of FFmpeg binary is required.

 '''Overview:'''
 Main issue is contained inside
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L171
 rtmp_packet_read_one_chunk] function. Size of each packet is being read
 using
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L215
 AV_RB24] each time the packet has been received. If packet with such
 channel_id does not exist it creates new one using
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L239
 ff_rtmp_packet_create]. Inside ff_rtmp_packet_create space gets allocated
 using
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L406
 av_realloc] using size variable. Later
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L268
 toread] value is computed which really means {{{toread = FFMIN(value,
 0x80) }}}) and passed to
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L269
 ffurl_read_complete] function. If
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L277
 size] value is still more than zero we have to read once
 [https://github.com/FFmpeg/FFmpeg/blob/1f5630af51f24d79053b6bef5b8b3ba93d637306/libavformat/rtmppkt.c#L283
 more]. Next time we can send another size value and it is not being
 checked that is different from the previous one, so more bytes have been
 read than size of the current packet.

 '''Steps to reproduce:'''

 I am attaching PoC file that reproduces the simple crash. Steps to
 reproduce bug:
 {{{
 $ python rtmp_poc.py &
 $ ffmpeg -v trace -i rtmp://localhost:12345/
 $ gdb -q ./ffmpeg_g
 (gdb) r -v trace -i rtmp://localhost:12345/
 }}}

 I am also attaching gdb stack-trace.

 '''Recommended fix:'''

 Checking that the size has not been changed from one chunk to another
 would do it.

 '''Final words:'''
 Our team plans to release full exploit and blogpost with full details on
 exploitation in 30 days or as soon as you patch vulnerability.
 Contact me if you need more details on vulnerability.

--
Ticket URL: <https://trac.ffmpeg.org/ticket/5994>
FFmpeg <https://ffmpeg.org>
FFmpeg issue tracker


More information about the FFmpeg-trac mailing list