diff --git a/cunit/test_librfx.c b/cunit/test_librfx.c index 7671b591a..0719ffe98 100644 --- a/cunit/test_librfx.c +++ b/cunit/test_librfx.c @@ -195,7 +195,8 @@ void test_bitstream(void) rfx_bitstream_attach(bs, (uint8*) y_data, sizeof(y_data)); while (!rfx_bitstream_eos(bs)) { - b = rfx_bitstream_get_bits(bs, 3); + rfx_bitstream_get_bits(bs, 3, b); + (void) b; //printf("%u ", b); } xfree(bs); diff --git a/libfreerdp-rfx/CMakeLists.txt b/libfreerdp-rfx/CMakeLists.txt index fa7cea0c9..6ff170e33 100644 --- a/libfreerdp-rfx/CMakeLists.txt +++ b/libfreerdp-rfx/CMakeLists.txt @@ -18,7 +18,6 @@ # limitations under the License. set(LIBFREERDP_RFX_SRCS - rfx_bitstream.c rfx_bitstream.h rfx_constants.h rfx_decode.c diff --git a/libfreerdp-rfx/rfx_bitstream.c b/libfreerdp-rfx/rfx_bitstream.c deleted file mode 100644 index eaac6ea2d..000000000 --- a/libfreerdp-rfx/rfx_bitstream.c +++ /dev/null @@ -1,86 +0,0 @@ -/** - * FreeRDP: A Remote Desktop Protocol client. - * RemoteFX Codec Library - Bit Stream - * - * Copyright 2011 Vic Lee - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#include -#include -#include -#include - -#include "rfx_bitstream.h" - -void rfx_bitstream_attach(RFX_BITSTREAM* bs, uint8* buffer, int nbytes) -{ - bs->buffer = buffer; - bs->nbytes = nbytes; - bs->byte_pos = 0; - bs->bits_left = 8; -} - -uint16 rfx_bitstream_get_bits(RFX_BITSTREAM* bs, int nbits) -{ - int b; - uint16 n = 0; - - while (bs->byte_pos < bs->nbytes && nbits > 0) - { - b = nbits; - - if (b > bs->bits_left) - b = bs->bits_left; - - if (n) - n <<= b; - - n |= (bs->buffer[bs->byte_pos] >> (bs->bits_left - b)) & ((1 << b) - 1); - bs->bits_left -= b; - nbits -= b; - - if (bs->bits_left == 0) - { - bs->bits_left = 8; - bs->byte_pos++; - } - } - - return n; -} - -void rfx_bitstream_put_bits(RFX_BITSTREAM* bs, uint16 bits, int nbits) -{ - int b; - - while (bs->byte_pos < bs->nbytes && nbits > 0) - { - b = nbits; - - if (b > bs->bits_left) - b = bs->bits_left; - - bs->buffer[bs->byte_pos] &= ~(((1 << b) - 1) << (bs->bits_left - b)); - bs->buffer[bs->byte_pos] |= ((bits >> (nbits - b)) & ((1 << b) - 1)) << (bs->bits_left - b); - bs->bits_left -= b; - nbits -= b; - - if (bs->bits_left == 0) - { - bs->bits_left = 8; - bs->byte_pos++; - } - } -} diff --git a/libfreerdp-rfx/rfx_bitstream.h b/libfreerdp-rfx/rfx_bitstream.h index 0766543f7..9bf9f43d1 100644 --- a/libfreerdp-rfx/rfx_bitstream.h +++ b/libfreerdp-rfx/rfx_bitstream.h @@ -31,9 +31,53 @@ struct _RFX_BITSTREAM }; typedef struct _RFX_BITSTREAM RFX_BITSTREAM; -void rfx_bitstream_attach(RFX_BITSTREAM* bs, uint8* buffer, int nbytes); -uint16 rfx_bitstream_get_bits(RFX_BITSTREAM* bs, int nbits); -void rfx_bitstream_put_bits(RFX_BITSTREAM* bs, uint16 bits, int nbits); +#define rfx_bitstream_attach(bs, _buffer, _nbytes) do { \ + bs->buffer = (uint8*) (_buffer); \ + bs->nbytes = (_nbytes); \ + bs->byte_pos = 0; \ + bs->bits_left = 8; } while (0) + +#define rfx_bitstream_get_bits(bs, _nbits, _r) do { \ + int nbits = _nbits; \ + int b; \ + uint16 n = 0; \ + while (bs->byte_pos < bs->nbytes && nbits > 0) \ + { \ + b = nbits; \ + if (b > bs->bits_left) \ + b = bs->bits_left; \ + if (n) \ + n <<= b; \ + n |= (bs->buffer[bs->byte_pos] >> (bs->bits_left - b)) & ((1 << b) - 1); \ + bs->bits_left -= b; \ + nbits -= b; \ + if (bs->bits_left == 0) \ + { \ + bs->bits_left = 8; \ + bs->byte_pos++; \ + } \ + } \ + _r = n; } while (0) + +#define rfx_bitstream_put_bits(bs, _bits, _nbits) do { \ + uint16 bits = (_bits); \ + int nbits = (_nbits); \ + int b; \ + while (bs->byte_pos < bs->nbytes && nbits > 0) \ + { \ + b = nbits; \ + if (b > bs->bits_left) \ + b = bs->bits_left; \ + bs->buffer[bs->byte_pos] &= ~(((1 << b) - 1) << (bs->bits_left - b)); \ + bs->buffer[bs->byte_pos] |= ((bits >> (nbits - b)) & ((1 << b) - 1)) << (bs->bits_left - b); \ + bs->bits_left -= b; \ + nbits -= b; \ + if (bs->bits_left == 0) \ + { \ + bs->bits_left = 8; \ + bs->byte_pos++; \ + } \ + } } while (0) #define rfx_bitstream_eos(_bs) ((_bs)->byte_pos >= (_bs)->nbytes) #define rfx_bitstream_left(_bs) ((_bs)->byte_pos >= (_bs)->nbytes ? 0 : ((_bs)->nbytes - (_bs)->byte_pos - 1) * 8 + (_bs)->bits_left) diff --git a/libfreerdp-rfx/rfx_rlgr.c b/libfreerdp-rfx/rfx_rlgr.c index a38cae93c..1897e948b 100644 --- a/libfreerdp-rfx/rfx_rlgr.c +++ b/libfreerdp-rfx/rfx_rlgr.c @@ -39,7 +39,7 @@ #define DQ_GR (3) /* decrease in kp after zero symbol in GR mode */ /* Gets (returns) the next nBits from the bitstream */ -#define GetBits(nBits) rfx_bitstream_get_bits(bs, nBits) +#define GetBits(nBits, r) rfx_bitstream_get_bits(bs, nBits, r) /* From current output pointer, write "value", check and update buffer_size */ #define WriteValue(value) \ @@ -99,13 +99,22 @@ static uint16 rfx_rlgr_get_gr_code(RFX_BITSTREAM* bs, int* krp, int* kr) { int vk; uint16 mag; + uint16 r; /* chew up/count leading 1s and escape 0 */ - for (vk = 0; GetBits(1) == 1;) - vk++; + vk = 0; + do + { + GetBits(1, r); + if (r == 1) + vk++; + else + break; + } while (1); /* get next *kr bits, and combine with leading 1s */ - mag = (vk << *kr) | GetBits(*kr); + GetBits(*kr, mag); + mag |= (vk << *kr); /* adjust krp and kr based on vk */ if (!vk) @@ -127,11 +136,12 @@ int rfx_rlgr_decode(RLGR_MODE mode, const uint8* data, int data_size, sint16* bu int kp; int kr; int krp; + uint16 r; sint16* dst; RFX_BITSTREAM* bs; bs = xnew(RFX_BITSTREAM); - rfx_bitstream_attach(bs, (uint8*) data, data_size); + rfx_bitstream_attach(bs, data, data_size); dst = buffer; /* initialize the parameters */ @@ -149,19 +159,22 @@ int rfx_rlgr_decode(RLGR_MODE mode, const uint8* data, int data_size, sint16* bu uint32 sign; /* RL MODE */ - while (!rfx_bitstream_eos(bs) && GetBits(1) == 0) + while (!rfx_bitstream_eos(bs)) { + GetBits(1, r); + if (r) + break; /* we have an RL escape "0", which translates to a run (1<