blob: 3061568309fc1975ddbaf4b22b04c3894777ded9
1 | /* |
2 | * drivers/amlogic/media_modules/amvdec_ports/decoder/h264_stream.c |
3 | * |
4 | * Copyright (C) 2017 Amlogic, Inc. All rights reserved. |
5 | * |
6 | * This program is free software; you can redistribute it and/or modify |
7 | * it under the terms of the GNU General Public License as published by |
8 | * the Free Software Foundation; either version 2 of the License, or |
9 | * (at your option) any later version. |
10 | * |
11 | * This program is distributed in the hope that it will be useful, but WITHOUT |
12 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or |
13 | * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for |
14 | * more details. |
15 | * |
16 | */ |
17 | |
18 | #include <linux/mm.h> |
19 | #include <linux/slab.h> |
20 | #include "h264_stream.h" |
21 | |
22 | void h264_stream_set(struct h264_stream_t *s, unsigned char *data, int size) |
23 | { |
24 | s->data = data; |
25 | s->size = size; |
26 | s->bit_pos = 7; |
27 | s->byte_pos = 0; |
28 | } |
29 | |
30 | unsigned int h264_stream_read_bits(struct h264_stream_t *s, unsigned int n) |
31 | { |
32 | unsigned int ret = 0; |
33 | unsigned char b = 0; |
34 | int i; |
35 | |
36 | if (n == 0) |
37 | return 0; |
38 | |
39 | for (i = 0; i < n; ++i) { |
40 | if (h264_stream_bits_remaining(s) == 0) |
41 | ret <<= n - i - 1; |
42 | |
43 | b = s->data[s->byte_pos]; |
44 | if (n - i <= 32) |
45 | ret = ret << 1 | BITAT(b, s->bit_pos); |
46 | |
47 | if (s->bit_pos == 0) { |
48 | s->bit_pos = 7; |
49 | s->byte_pos++; |
50 | } else |
51 | s->bit_pos--; |
52 | } |
53 | |
54 | return ret; |
55 | } |
56 | |
57 | unsigned int h264_stream_peek_bits(struct h264_stream_t *s, unsigned int n) |
58 | { |
59 | int prev_bit_pos = s->bit_pos; |
60 | int prev_byte_pos = s->byte_pos; |
61 | unsigned int ret = h264_stream_read_bits(s, n); |
62 | |
63 | s->bit_pos = prev_bit_pos; |
64 | s->byte_pos = prev_byte_pos; |
65 | |
66 | return ret; |
67 | } |
68 | |
69 | unsigned int h264_stream_read_bytes(struct h264_stream_t *s, unsigned int n) |
70 | { |
71 | unsigned int ret = 0; |
72 | int i; |
73 | |
74 | if (n == 0) |
75 | return 0; |
76 | |
77 | for (i = 0; i < n; ++i) { |
78 | if (h264_stream_bytes_remaining(s) == 0) { |
79 | ret <<= (n - i - 1) * 8; |
80 | break; |
81 | } |
82 | |
83 | if (n - i <= 4) |
84 | ret = ret << 8 | s->data[s->byte_pos]; |
85 | |
86 | s->byte_pos++; |
87 | } |
88 | |
89 | return ret; |
90 | } |
91 | |
92 | unsigned int h264_stream_peek_bytes(struct h264_stream_t *s, unsigned int n) |
93 | { |
94 | int prev_byte_pos = s->byte_pos; |
95 | unsigned int ret = h264_stream_read_bytes(s, n); |
96 | |
97 | s->byte_pos = prev_byte_pos; |
98 | |
99 | return ret; |
100 | } |
101 | |
102 | int h264_stream_bits_remaining(struct h264_stream_t *s) |
103 | { |
104 | return (s->size - s->byte_pos) * 8 + s->bit_pos; |
105 | } |
106 | |
107 | int h264_stream_bytes_remaining(struct h264_stream_t *s) |
108 | { |
109 | return s->size - s->byte_pos; |
110 | } |
111 | |
112 |