LCOV - code coverage report
Current view: top level - libavcodec - bytestream.h (source / functions) Hit Total Coverage
Test: coverage.info Lines: 100 116 86.2 %
Date: 2017-12-12 11:08:38 Functions: 71 72 98.6 %

          Line data    Source code
       1             : /*
       2             :  * Bytestream functions
       3             :  * copyright (c) 2006 Baptiste Coudurier <baptiste.coudurier@free.fr>
       4             :  * Copyright (c) 2012 Aneesh Dogra (lionaneesh) <lionaneesh@gmail.com>
       5             :  *
       6             :  * This file is part of FFmpeg.
       7             :  *
       8             :  * FFmpeg is free software; you can redistribute it and/or
       9             :  * modify it under the terms of the GNU Lesser General Public
      10             :  * License as published by the Free Software Foundation; either
      11             :  * version 2.1 of the License, or (at your option) any later version.
      12             :  *
      13             :  * FFmpeg is distributed in the hope that it will be useful,
      14             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      15             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      16             :  * Lesser General Public License for more details.
      17             :  *
      18             :  * You should have received a copy of the GNU Lesser General Public
      19             :  * License along with FFmpeg; if not, write to the Free Software
      20             :  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
      21             :  */
      22             : 
      23             : #ifndef AVCODEC_BYTESTREAM_H
      24             : #define AVCODEC_BYTESTREAM_H
      25             : 
      26             : #include <stdint.h>
      27             : #include <string.h>
      28             : 
      29             : #include "libavutil/avassert.h"
      30             : #include "libavutil/common.h"
      31             : #include "libavutil/intreadwrite.h"
      32             : 
      33             : typedef struct GetByteContext {
      34             :     const uint8_t *buffer, *buffer_end, *buffer_start;
      35             : } GetByteContext;
      36             : 
      37             : typedef struct PutByteContext {
      38             :     uint8_t *buffer, *buffer_end, *buffer_start;
      39             :     int eof;
      40             : } PutByteContext;
      41             : 
      42             : #define DEF(type, name, bytes, read, write)                                  \
      43             : static av_always_inline type bytestream_get_ ## name(const uint8_t **b)        \
      44             : {                                                                              \
      45             :     (*b) += bytes;                                                             \
      46             :     return read(*b - bytes);                                                   \
      47             : }                                                                              \
      48             : static av_always_inline void bytestream_put_ ## name(uint8_t **b,              \
      49             :                                                      const type value)         \
      50             : {                                                                              \
      51             :     write(*b, value);                                                          \
      52             :     (*b) += bytes;                                                             \
      53             : }                                                                              \
      54             : static av_always_inline void bytestream2_put_ ## name ## u(PutByteContext *p,  \
      55             :                                                            const type value)   \
      56             : {                                                                              \
      57             :     bytestream_put_ ## name(&p->buffer, value);                                \
      58             : }                                                                              \
      59             : static av_always_inline void bytestream2_put_ ## name(PutByteContext *p,       \
      60             :                                                       const type value)        \
      61             : {                                                                              \
      62             :     if (!p->eof && (p->buffer_end - p->buffer >= bytes)) {                     \
      63             :         write(p->buffer, value);                                               \
      64             :         p->buffer += bytes;                                                    \
      65             :     } else                                                                     \
      66             :         p->eof = 1;                                                            \
      67             : }                                                                              \
      68             : static av_always_inline type bytestream2_get_ ## name ## u(GetByteContext *g)  \
      69             : {                                                                              \
      70             :     return bytestream_get_ ## name(&g->buffer);                                \
      71             : }                                                                              \
      72             : static av_always_inline type bytestream2_get_ ## name(GetByteContext *g)       \
      73             : {                                                                              \
      74             :     if (g->buffer_end - g->buffer < bytes) {                                   \
      75             :         g->buffer = g->buffer_end;                                             \
      76             :         return 0;                                                              \
      77             :     }                                                                          \
      78             :     return bytestream2_get_ ## name ## u(g);                                   \
      79             : }                                                                              \
      80             : static av_always_inline type bytestream2_peek_ ## name(GetByteContext *g)      \
      81             : {                                                                              \
      82             :     if (g->buffer_end - g->buffer < bytes)                                     \
      83             :         return 0;                                                              \
      84             :     return read(g->buffer);                                                    \
      85             : }
      86             : 
      87       61998 : DEF(uint64_t,     le64, 8, AV_RL64, AV_WL64)
      88     6840471 : DEF(unsigned int, le32, 4, AV_RL32, AV_WL32)
      89    62976529 : DEF(unsigned int, le24, 3, AV_RL24, AV_WL24)
      90   168798720 : DEF(unsigned int, le16, 2, AV_RL16, AV_WL16)
      91     1077850 : DEF(uint64_t,     be64, 8, AV_RB64, AV_WB64)
      92    24363320 : DEF(unsigned int, be32, 4, AV_RB32, AV_WB32)
      93     2974977 : DEF(unsigned int, be24, 3, AV_RB24, AV_WB24)
      94   109473408 : DEF(unsigned int, be16, 2, AV_RB16, AV_WB16)
      95   349620306 : DEF(unsigned int, byte, 1, AV_RB8 , AV_WB8)
      96             : 
      97             : #if AV_HAVE_BIGENDIAN
      98             : #   define bytestream2_get_ne16  bytestream2_get_be16
      99             : #   define bytestream2_get_ne24  bytestream2_get_be24
     100             : #   define bytestream2_get_ne32  bytestream2_get_be32
     101             : #   define bytestream2_get_ne64  bytestream2_get_be64
     102             : #   define bytestream2_get_ne16u bytestream2_get_be16u
     103             : #   define bytestream2_get_ne24u bytestream2_get_be24u
     104             : #   define bytestream2_get_ne32u bytestream2_get_be32u
     105             : #   define bytestream2_get_ne64u bytestream2_get_be64u
     106             : #   define bytestream2_put_ne16  bytestream2_put_be16
     107             : #   define bytestream2_put_ne24  bytestream2_put_be24
     108             : #   define bytestream2_put_ne32  bytestream2_put_be32
     109             : #   define bytestream2_put_ne64  bytestream2_put_be64
     110             : #   define bytestream2_peek_ne16 bytestream2_peek_be16
     111             : #   define bytestream2_peek_ne24 bytestream2_peek_be24
     112             : #   define bytestream2_peek_ne32 bytestream2_peek_be32
     113             : #   define bytestream2_peek_ne64 bytestream2_peek_be64
     114             : #else
     115             : #   define bytestream2_get_ne16  bytestream2_get_le16
     116             : #   define bytestream2_get_ne24  bytestream2_get_le24
     117             : #   define bytestream2_get_ne32  bytestream2_get_le32
     118             : #   define bytestream2_get_ne64  bytestream2_get_le64
     119             : #   define bytestream2_get_ne16u bytestream2_get_le16u
     120             : #   define bytestream2_get_ne24u bytestream2_get_le24u
     121             : #   define bytestream2_get_ne32u bytestream2_get_le32u
     122             : #   define bytestream2_get_ne64u bytestream2_get_le64u
     123             : #   define bytestream2_put_ne16  bytestream2_put_le16
     124             : #   define bytestream2_put_ne24  bytestream2_put_le24
     125             : #   define bytestream2_put_ne32  bytestream2_put_le32
     126             : #   define bytestream2_put_ne64  bytestream2_put_le64
     127             : #   define bytestream2_peek_ne16 bytestream2_peek_le16
     128             : #   define bytestream2_peek_ne24 bytestream2_peek_le24
     129             : #   define bytestream2_peek_ne32 bytestream2_peek_le32
     130             : #   define bytestream2_peek_ne64 bytestream2_peek_le64
     131             : #endif
     132             : 
     133      171922 : static av_always_inline void bytestream2_init(GetByteContext *g,
     134             :                                               const uint8_t *buf,
     135             :                                               int buf_size)
     136             : {
     137      171922 :     av_assert0(buf_size >= 0);
     138      171922 :     g->buffer       = buf;
     139      171922 :     g->buffer_start = buf;
     140      171922 :     g->buffer_end   = buf + buf_size;
     141      171922 : }
     142             : 
     143        1500 : static av_always_inline void bytestream2_init_writer(PutByteContext *p,
     144             :                                                      uint8_t *buf,
     145             :                                                      int buf_size)
     146             : {
     147        1500 :     av_assert0(buf_size >= 0);
     148        1500 :     p->buffer       = buf;
     149        1500 :     p->buffer_start = buf;
     150        1500 :     p->buffer_end   = buf + buf_size;
     151        1500 :     p->eof          = 0;
     152        1500 : }
     153             : 
     154    16682539 : static av_always_inline unsigned int bytestream2_get_bytes_left(GetByteContext *g)
     155             : {
     156    16682539 :     return g->buffer_end - g->buffer;
     157             : }
     158             : 
     159       86094 : static av_always_inline unsigned int bytestream2_get_bytes_left_p(PutByteContext *p)
     160             : {
     161       86094 :     return p->buffer_end - p->buffer;
     162             : }
     163             : 
     164      770434 : static av_always_inline void bytestream2_skip(GetByteContext *g,
     165             :                                               unsigned int size)
     166             : {
     167      770434 :     g->buffer += FFMIN(g->buffer_end - g->buffer, size);
     168      770434 : }
     169             : 
     170       70196 : static av_always_inline void bytestream2_skipu(GetByteContext *g,
     171             :                                                unsigned int size)
     172             : {
     173       70196 :     g->buffer += size;
     174       70196 : }
     175             : 
     176          39 : static av_always_inline void bytestream2_skip_p(PutByteContext *p,
     177             :                                                 unsigned int size)
     178             : {
     179             :     int size2;
     180          39 :     if (p->eof)
     181           0 :         return;
     182          39 :     size2 = FFMIN(p->buffer_end - p->buffer, size);
     183          39 :     if (size2 != size)
     184           0 :         p->eof = 1;
     185          39 :     p->buffer += size2;
     186             : }
     187             : 
     188     4261697 : static av_always_inline int bytestream2_tell(GetByteContext *g)
     189             : {
     190     4261697 :     return (int)(g->buffer - g->buffer_start);
     191             : }
     192             : 
     193      148640 : static av_always_inline int bytestream2_tell_p(PutByteContext *p)
     194             : {
     195      148640 :     return (int)(p->buffer - p->buffer_start);
     196             : }
     197             : 
     198         125 : static av_always_inline int bytestream2_size(GetByteContext *g)
     199             : {
     200         125 :     return (int)(g->buffer_end - g->buffer_start);
     201             : }
     202             : 
     203             : static av_always_inline int bytestream2_size_p(PutByteContext *p)
     204             : {
     205             :     return (int)(p->buffer_end - p->buffer_start);
     206             : }
     207             : 
     208      777104 : static av_always_inline int bytestream2_seek(GetByteContext *g,
     209             :                                              int offset,
     210             :                                              int whence)
     211             : {
     212      777104 :     switch (whence) {
     213         990 :     case SEEK_CUR:
     214         990 :         offset     = av_clip(offset, -(g->buffer - g->buffer_start),
     215         990 :                              g->buffer_end - g->buffer);
     216         990 :         g->buffer += offset;
     217         990 :         break;
     218         792 :     case SEEK_END:
     219         792 :         offset    = av_clip(offset, -(g->buffer_end - g->buffer_start), 0);
     220         792 :         g->buffer = g->buffer_end + offset;
     221         792 :         break;
     222      775322 :     case SEEK_SET:
     223      775322 :         offset    = av_clip(offset, 0, g->buffer_end - g->buffer_start);
     224      775322 :         g->buffer = g->buffer_start + offset;
     225      775322 :         break;
     226           0 :     default:
     227           0 :         return AVERROR(EINVAL);
     228             :     }
     229      777104 :     return bytestream2_tell(g);
     230             : }
     231             : 
     232       11594 : static av_always_inline int bytestream2_seek_p(PutByteContext *p,
     233             :                                                int offset,
     234             :                                                int whence)
     235             : {
     236       11594 :     p->eof = 0;
     237       11594 :     switch (whence) {
     238        7050 :     case SEEK_CUR:
     239        7050 :         if (p->buffer_end - p->buffer < offset)
     240           0 :             p->eof = 1;
     241        7050 :         offset     = av_clip(offset, -(p->buffer - p->buffer_start),
     242        7050 :                              p->buffer_end - p->buffer);
     243        7050 :         p->buffer += offset;
     244        7050 :         break;
     245           0 :     case SEEK_END:
     246           0 :         if (offset > 0)
     247           0 :             p->eof = 1;
     248           0 :         offset    = av_clip(offset, -(p->buffer_end - p->buffer_start), 0);
     249           0 :         p->buffer = p->buffer_end + offset;
     250           0 :         break;
     251        4544 :     case SEEK_SET:
     252        4544 :         if (p->buffer_end - p->buffer_start < offset)
     253           0 :             p->eof = 1;
     254        4544 :         offset    = av_clip(offset, 0, p->buffer_end - p->buffer_start);
     255        4544 :         p->buffer = p->buffer_start + offset;
     256        4544 :         break;
     257           0 :     default:
     258           0 :         return AVERROR(EINVAL);
     259             :     }
     260       11594 :     return bytestream2_tell_p(p);
     261             : }
     262             : 
     263      791549 : static av_always_inline unsigned int bytestream2_get_buffer(GetByteContext *g,
     264             :                                                             uint8_t *dst,
     265             :                                                             unsigned int size)
     266             : {
     267      791549 :     int size2 = FFMIN(g->buffer_end - g->buffer, size);
     268      791549 :     memcpy(dst, g->buffer, size2);
     269      791549 :     g->buffer += size2;
     270      791549 :     return size2;
     271             : }
     272             : 
     273      471344 : static av_always_inline unsigned int bytestream2_get_bufferu(GetByteContext *g,
     274             :                                                              uint8_t *dst,
     275             :                                                              unsigned int size)
     276             : {
     277      471344 :     memcpy(dst, g->buffer, size);
     278      471344 :     g->buffer += size;
     279      471344 :     return size;
     280             : }
     281             : 
     282        2350 : static av_always_inline unsigned int bytestream2_put_buffer(PutByteContext *p,
     283             :                                                             const uint8_t *src,
     284             :                                                             unsigned int size)
     285             : {
     286             :     int size2;
     287        2350 :     if (p->eof)
     288           0 :         return 0;
     289        2350 :     size2 = FFMIN(p->buffer_end - p->buffer, size);
     290        2350 :     if (size2 != size)
     291           0 :         p->eof = 1;
     292        2350 :     memcpy(p->buffer, src, size2);
     293        2350 :     p->buffer += size2;
     294        2350 :     return size2;
     295             : }
     296             : 
     297             : static av_always_inline unsigned int bytestream2_put_bufferu(PutByteContext *p,
     298             :                                                              const uint8_t *src,
     299             :                                                              unsigned int size)
     300             : {
     301             :     memcpy(p->buffer, src, size);
     302             :     p->buffer += size;
     303             :     return size;
     304             : }
     305             : 
     306             : static av_always_inline void bytestream2_set_buffer(PutByteContext *p,
     307             :                                                     const uint8_t c,
     308             :                                                     unsigned int size)
     309             : {
     310             :     int size2;
     311             :     if (p->eof)
     312             :         return;
     313             :     size2 = FFMIN(p->buffer_end - p->buffer, size);
     314             :     if (size2 != size)
     315             :         p->eof = 1;
     316             :     memset(p->buffer, c, size2);
     317             :     p->buffer += size2;
     318             : }
     319             : 
     320             : static av_always_inline void bytestream2_set_bufferu(PutByteContext *p,
     321             :                                                      const uint8_t c,
     322             :                                                      unsigned int size)
     323             : {
     324             :     memset(p->buffer, c, size);
     325             :     p->buffer += size;
     326             : }
     327             : 
     328        4557 : static av_always_inline unsigned int bytestream2_get_eof(PutByteContext *p)
     329             : {
     330        4557 :     return p->eof;
     331             : }
     332             : 
     333             : static av_always_inline unsigned int bytestream2_copy_bufferu(PutByteContext *p,
     334             :                                                               GetByteContext *g,
     335             :                                                               unsigned int size)
     336             : {
     337             :     memcpy(p->buffer, g->buffer, size);
     338             :     p->buffer += size;
     339             :     g->buffer += size;
     340             :     return size;
     341             : }
     342             : 
     343             : static av_always_inline unsigned int bytestream2_copy_buffer(PutByteContext *p,
     344             :                                                              GetByteContext *g,
     345             :                                                              unsigned int size)
     346             : {
     347             :     int size2;
     348             : 
     349             :     if (p->eof)
     350             :         return 0;
     351             :     size  = FFMIN(g->buffer_end - g->buffer, size);
     352             :     size2 = FFMIN(p->buffer_end - p->buffer, size);
     353             :     if (size2 != size)
     354             :         p->eof = 1;
     355             : 
     356             :     return bytestream2_copy_bufferu(p, g, size2);
     357             : }
     358             : 
     359        1320 : static av_always_inline unsigned int bytestream_get_buffer(const uint8_t **b,
     360             :                                                            uint8_t *dst,
     361             :                                                            unsigned int size)
     362             : {
     363        1320 :     memcpy(dst, *b, size);
     364        1320 :     (*b) += size;
     365        1320 :     return size;
     366             : }
     367             : 
     368     2175782 : static av_always_inline void bytestream_put_buffer(uint8_t **b,
     369             :                                                    const uint8_t *src,
     370             :                                                    unsigned int size)
     371             : {
     372     2175782 :     memcpy(*b, src, size);
     373     2175782 :     (*b) += size;
     374     2175782 : }
     375             : 
     376             : #endif /* AVCODEC_BYTESTREAM_H */

Generated by: LCOV version 1.13