233 lines
3.9 KiB
C++
233 lines
3.9 KiB
C++
////////////////////////////////////////////////////////////////////////////////
|
|
// B25Decoder.cpp
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
#include "B25Decoder.h"
|
|
|
|
int B25Decoder::strip = 1;
|
|
int B25Decoder::emm_proc = 0;
|
|
int B25Decoder::multi2_round = 4;
|
|
|
|
B25Decoder::B25Decoder() : _bcas(nullptr), _b25(nullptr), _data(nullptr)
|
|
{
|
|
}
|
|
|
|
B25Decoder::~B25Decoder()
|
|
{
|
|
if (_data)
|
|
::free(_data);
|
|
|
|
std::lock_guard<std::mutex> lock(_mtx);
|
|
|
|
if (_b25)
|
|
_b25->release(_b25);
|
|
|
|
if (_bcas)
|
|
_bcas->release(_bcas);
|
|
|
|
char log[64];
|
|
::wsprintfA(log, "B25Decoder::dtor() : end");
|
|
::OutputDebugStringA(log);
|
|
}
|
|
|
|
int B25Decoder::init()
|
|
{
|
|
int rc;
|
|
|
|
std::lock_guard<std::mutex> lock(_mtx);
|
|
|
|
if (_b25)
|
|
return -2;
|
|
|
|
char log[64];
|
|
|
|
_bcas = create_b_cas_card();
|
|
if (!_bcas)
|
|
return -3;
|
|
|
|
rc = _bcas->init(_bcas);
|
|
if (rc < 0)
|
|
{
|
|
::wsprintfA(log, "B25Decoder::init() : bcas init error / rc(%d)", rc);
|
|
::OutputDebugStringA(log);
|
|
rc = -4;
|
|
goto err;
|
|
}
|
|
|
|
_b25 = create_arib_std_b25();
|
|
if (!_b25)
|
|
{
|
|
rc = -5;
|
|
goto err;
|
|
}
|
|
|
|
if (_b25->set_b_cas_card(_b25, _bcas) < 0)
|
|
{
|
|
rc = -6;
|
|
goto err;
|
|
}
|
|
|
|
_b25->set_strip(_b25, strip);
|
|
_b25->set_emm_proc(_b25, emm_proc);
|
|
_b25->set_multi2_round(_b25, multi2_round);
|
|
|
|
::wsprintfA(log, "B25Decoder::init() : success");
|
|
::OutputDebugStringA(log);
|
|
return 0; // success
|
|
|
|
err:
|
|
if (_b25)
|
|
{
|
|
_b25->release(_b25);
|
|
_b25 = nullptr;
|
|
}
|
|
|
|
if (_bcas)
|
|
{
|
|
_bcas->release(_bcas);
|
|
_bcas = nullptr;
|
|
}
|
|
|
|
::wsprintfA(log, "B25Decoder::init() : error / rc(%d)", rc);
|
|
::OutputDebugStringA(log);
|
|
_errtime = ::GetTickCount();
|
|
return rc; // error
|
|
}
|
|
|
|
void B25Decoder::setemm(bool flag)
|
|
{
|
|
if (_b25)
|
|
_b25->set_emm_proc(_b25, flag ? 1 : 0);
|
|
}
|
|
|
|
void B25Decoder::decode(BYTE *pSrc, DWORD dwSrcSize, BYTE **ppDst, DWORD *pdwDstSize)
|
|
{
|
|
if (!_b25)
|
|
{
|
|
DWORD now = ::GetTickCount();
|
|
if ((now - _errtime) > RETRY_INTERVAL)
|
|
{
|
|
if (init() < 0)
|
|
_errtime = now;
|
|
}
|
|
|
|
if (!_b25)
|
|
{
|
|
if (*ppDst != pSrc)
|
|
{
|
|
*ppDst = pSrc;
|
|
*pdwDstSize = dwSrcSize;
|
|
}
|
|
return;
|
|
}
|
|
}
|
|
|
|
if (_data)
|
|
{
|
|
::free(_data);
|
|
_data = nullptr;
|
|
}
|
|
|
|
char log[64];
|
|
|
|
ARIB_STD_B25_BUFFER buf;
|
|
buf.data = pSrc;
|
|
buf.size = dwSrcSize;
|
|
const int rc = _b25->put(_b25, &buf);
|
|
if (rc < 0)
|
|
{
|
|
if (rc >= ARIB_STD_B25_ERROR_NO_ECM_IN_HEAD_32M)
|
|
{
|
|
// pass through
|
|
_b25->release(_b25);
|
|
_b25 = nullptr;
|
|
_bcas->release(_bcas);
|
|
_bcas = nullptr;
|
|
if (*ppDst != pSrc)
|
|
{
|
|
*ppDst = pSrc;
|
|
*pdwDstSize = dwSrcSize;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
BYTE *p = nullptr;
|
|
_b25->withdraw(_b25, &buf); // withdraw src buffer
|
|
if (buf.size > 0)
|
|
{
|
|
::wsprintfA(log, "B25Decoder::decode() : error / withdraw size(%u)", buf.size);
|
|
::OutputDebugStringA(log);
|
|
p = (BYTE *)::malloc(buf.size + dwSrcSize);
|
|
}
|
|
|
|
if (p)
|
|
{
|
|
::memcpy(p, buf.data, buf.size);
|
|
::memcpy(p + buf.size, pSrc, dwSrcSize);
|
|
*ppDst = p;
|
|
*pdwDstSize = buf.size + dwSrcSize;
|
|
_data = p;
|
|
}
|
|
else
|
|
{
|
|
if (*ppDst != pSrc)
|
|
{
|
|
*ppDst = pSrc;
|
|
*pdwDstSize = dwSrcSize;
|
|
}
|
|
}
|
|
|
|
if (rc == ARIB_STD_B25_ERROR_ECM_PROC_FAILURE)
|
|
{
|
|
// pass through
|
|
_b25->release(_b25);
|
|
_b25 = nullptr;
|
|
_bcas->release(_bcas);
|
|
_bcas = nullptr;
|
|
}
|
|
}
|
|
::wsprintfA(log, "B25Decoder::decode() : error / rc(%d)", rc);
|
|
::OutputDebugStringA(log);
|
|
_errtime = ::GetTickCount();
|
|
return; // error
|
|
}
|
|
_b25->get(_b25, &buf);
|
|
*ppDst = buf.data;
|
|
*pdwDstSize = buf.size;
|
|
return; // success
|
|
}
|
|
|
|
int B25Decoder::reset()
|
|
{
|
|
int rc = 0;
|
|
|
|
if (_b25)
|
|
rc = _b25->reset(_b25);
|
|
return rc;
|
|
}
|
|
|
|
int B25Decoder::flush()
|
|
{
|
|
int rc = 0;
|
|
|
|
if (_b25)
|
|
rc = _b25->flush(_b25);
|
|
return rc;
|
|
}
|
|
|
|
int B25Decoder::put(BYTE *pSrc, DWORD dwSrcSize)
|
|
{
|
|
ARIB_STD_B25_BUFFER buf;
|
|
buf.data = pSrc;
|
|
buf.size = dwSrcSize;
|
|
return _b25->put(_b25, &buf);
|
|
}
|
|
|
|
int B25Decoder::get(BYTE **ppDst, DWORD *pdwDstSize)
|
|
{
|
|
ARIB_STD_B25_BUFFER buf;
|
|
int rc = _b25->get(_b25, &buf);
|
|
*ppDst = buf.data;
|
|
*pdwDstSize = buf.size;
|
|
return rc;
|
|
}
|