FileRead( FILE* f ) : m_stream( LZ4_createStreamDecode() ) , m_file( f ) , m_buf( m_bufData[1] ) , m_second( m_bufData[0] ) , m_offset( 0 ) , m_lastBlock( 0 ) , m_signalSwitch( false ) , m_signalAvailable( false ) , m_exit( false ) { char hdr[4]; if( fread( hdr, 1, sizeof( hdr ), m_file ) != sizeof( hdr ) ) throw NotTracyDump(); if( memcmp( hdr, Lz4Header, sizeof( hdr ) ) != 0 ) { fseek( m_file, 0, SEEK_SET ); uint32_t sz; static_assert( sizeof( sz ) == sizeof( hdr ), "Size mismatch" ); memcpy( &sz, hdr, sizeof( sz ) ); if( sz > LZ4Size ) throw NotTracyDump(); } ReadBlock(); std::swap( m_buf, m_second ); m_decThread = std::thread( [this] { Worker(); } ); }
static void test_decompress( FILE* outFp, FILE* inpFp, size_t messageMaxBytes, size_t ringBufferBytes) { LZ4_streamDecode_t* const lz4StreamDecode = LZ4_createStreamDecode(); char* const cmpBuf = (char*) malloc(LZ4_COMPRESSBOUND(messageMaxBytes)); char* const decBuf = (char*) malloc(ringBufferBytes); int decOffset = 0; for ( ; ; ) { uint16_t cmpBytes = 0; if (read_uint16(inpFp, &cmpBytes) != 1) break; if (cmpBytes <= 0) break; if (read_bin(inpFp, cmpBuf, cmpBytes) != cmpBytes) break; { char* const decPtr = &decBuf[decOffset]; const int decBytes = LZ4_decompress_safe_continue( lz4StreamDecode, cmpBuf, decPtr, cmpBytes, (int) messageMaxBytes); if (decBytes <= 0) break; write_bin(outFp, decPtr, decBytes); // Add and wraparound the ringbuffer offset decOffset += decBytes; if ((size_t)decOffset >= ringBufferBytes - messageMaxBytes) decOffset = 0; } } free(decBuf); free(cmpBuf); LZ4_freeStreamDecode(lz4StreamDecode); }