📄 jpegdec.cpp
字号:
}
}
Exit:
return jerr;
} // CJPEGDecoder::ParseJPEGBitStream()
JERRCODE CJPEGDecoder::Init(void)
{
int i;
int tr_buf_size = 0;
CJPEGColorComponent* curr_comp;
JERRCODE jerr;
if(m_init_done)
return JPEG_OK;
m_num_threads = get_num_threads();
// not implemented yet
if(m_jpeg_sampling == JS_OTHER)
{
return JPEG_NOT_IMPLEMENTED;
}
// TODO:
// need to add support for images with more then 4 components per frame
if(m_dst.precision <= 8)
{
switch (m_jpeg_dct_scale)
{
case JD_1_1:
default:
{
m_dd_factor = 1;
}
break;
case JD_1_2:
{
m_dd_factor = 2;
}
break;
case JD_1_4:
{
m_dd_factor = 4;
}
break;
case JD_1_8:
{
m_dd_factor = 8;
}
break;
}
}
for(i = 0; i < m_jpeg_ncomp; i++)
{
curr_comp = &m_ccomp[i];
switch(m_jpeg_mode)
{
case JPEG_BASELINE:
case JPEG_EXTENDED:
{
int ds = (m_dst.precision <= 8) ? sizeof(Ipp8u) : sizeof(Ipp16s);
int lnz_ds = curr_comp->m_vsampling * curr_comp->m_hsampling;
curr_comp->m_lnz_bufsize = lnz_ds * m_numxMCU;
curr_comp->m_lnz_ds = lnz_ds;
curr_comp->m_cc_height = m_mcuHeight;
curr_comp->m_cc_step = m_numxMCU * m_mcuWidth * ds;
curr_comp->m_ss_height = curr_comp->m_cc_height / curr_comp->m_v_factor;
curr_comp->m_ss_step = curr_comp->m_cc_step / curr_comp->m_h_factor;
if(curr_comp->m_h_factor == 2 && curr_comp->m_v_factor == 2)
{
curr_comp->m_ss_height += 2; // add border lines (top and bottom)
}
if(m_scan_ncomps == m_jpeg_ncomp)
tr_buf_size = m_numxMCU * m_nblock * DCTSIZE2 * sizeof(Ipp16s) * m_num_threads;
else
tr_buf_size = m_numxMCU * m_numyMCU * m_nblock * DCTSIZE2 * sizeof(Ipp16s);
break;
} // JPEG_BASELINE
case JPEG_PROGRESSIVE:
{
int lnz_ds = curr_comp->m_vsampling * curr_comp->m_hsampling;
curr_comp->m_lnz_bufsize = lnz_ds * m_numxMCU;
curr_comp->m_lnz_ds = lnz_ds;
curr_comp->m_cc_height = m_mcuHeight;
curr_comp->m_cc_step = m_numxMCU * m_mcuWidth;
curr_comp->m_ss_height = curr_comp->m_cc_height / curr_comp->m_v_factor;
curr_comp->m_ss_step = curr_comp->m_cc_step / curr_comp->m_h_factor;
if(curr_comp->m_h_factor == 2 && curr_comp->m_v_factor == 2)
{
curr_comp->m_ss_height += 2; // add border lines (top and bottom)
}
tr_buf_size = m_numxMCU * m_numyMCU * m_nblock * DCTSIZE2 * sizeof(Ipp16s);
break;
} // JPEG_PROGRESSIVE
case JPEG_LOSSLESS:
{
int lnz_ds = curr_comp->m_vsampling * curr_comp->m_hsampling;
curr_comp->m_lnz_bufsize = lnz_ds * m_numxMCU;
curr_comp->m_lnz_ds = lnz_ds;
curr_comp->m_cc_height = m_mcuHeight;
curr_comp->m_cc_step = m_numxMCU * m_mcuWidth * sizeof(Ipp16s);
curr_comp->m_ss_height = curr_comp->m_cc_height / curr_comp->m_v_factor;
curr_comp->m_ss_step = curr_comp->m_cc_step / curr_comp->m_h_factor;
if(m_scan_ncomps == m_jpeg_ncomp)
tr_buf_size = m_numxMCU * m_nblock * sizeof(Ipp16s);
else
tr_buf_size = m_numxMCU * m_numyMCU * m_nblock * sizeof(Ipp16s);
curr_comp->m_curr_row = (Ipp16s*)ippMalloc(curr_comp->m_cc_step * sizeof(Ipp16s));
if(0 == curr_comp->m_curr_row)
return JPEG_ERR_ALLOC;
curr_comp->m_prev_row = (Ipp16s*)ippMalloc(curr_comp->m_cc_step * sizeof(Ipp16s));
if(0 == curr_comp->m_prev_row)
return JPEG_ERR_ALLOC;
break;
} // JPEG_LOSSLESS
default:
return JPEG_ERR_INTERNAL;
} // m_jpeg_mode
// color convert buffer
jerr = curr_comp->CreateBufferCC(m_num_threads);
if(JPEG_OK != jerr)
return jerr;
jerr = curr_comp->CreateBufferSS(m_num_threads);
if(JPEG_OK != jerr)
return jerr;
jerr = curr_comp->CreateBufferLNZ(m_num_threads);
if(JPEG_OK != jerr)
return jerr;
} // m_jpeg_ncomp
if(0 == m_block_buffer)
{
m_block_buffer = (Ipp16s*)ippMalloc(tr_buf_size);
if(0 == m_block_buffer)
{
return JPEG_ERR_ALLOC;
}
ippsZero_8u((Ipp8u*)m_block_buffer,tr_buf_size);
}
m_state.Create();
m_init_done = 1;
return JPEG_OK;
} // CJPEGDecoder::Init()
JERRCODE CJPEGDecoder::ColorConvert(int nMCURow,int thread_id)
{
int dstStep;
Ipp8u* pDst8u = 0;
Ipp16u* pDst16u = 0;
IppiSize roi;
IppStatus status;
if(nMCURow == m_numyMCU - 1)
{
m_ccHeight = m_mcuHeight - m_yPadding;
}
roi.width = m_dst.width;
roi.height = m_ccHeight / m_dd_factor;
if(roi.height == 0)
return JPEG_OK;
dstStep = m_dst.lineStep[0];
if(m_dst.precision <= 8)
pDst8u = m_dst.p.Data8u[0] + nMCURow * m_mcuHeight * dstStep / m_dd_factor;
else
pDst16u = (Ipp16u*)((Ipp8u*)m_dst.p.Data16s[0] + nMCURow * m_mcuHeight * dstStep);
if(m_jpeg_color == JC_UNKNOWN && m_dst.color == JC_UNKNOWN)
{
switch(m_jpeg_ncomp)
{
case 1:
{
int srcStep;
Ipp8u* pSrc8u;
Ipp16u* pSrc16u;
srcStep = m_ccomp[0].m_cc_step;
if(m_dst.precision <= 8)
{
pSrc8u = m_ccomp[0].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_C1R(pSrc8u,srcStep,pDst8u,dstStep,roi);
}
else
{
pSrc16u = (Ipp16u*)m_ccomp[0].GetCCBufferPtr(thread_id);
status = ippiCopy_16s_C1R((Ipp16s*)pSrc16u,srcStep,(Ipp16s*)pDst16u,dstStep,roi);
}
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_C1R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
break;
case 3:
{
int srcStep;
Ipp8u* pSrc8u[3];
Ipp16u* pSrc16u[3];
srcStep = m_ccomp[0].m_cc_step;
if(m_dst.precision <= 8)
{
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
}
else
{
pSrc16u[0] = (Ipp16u*)m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc16u[1] = (Ipp16u*)m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc16u[2] = (Ipp16u*)m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_16s_P3C3R((Ipp16s**)pSrc16u,srcStep,(Ipp16s*)pDst16u,dstStep,roi);
}
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
break;
case 4:
{
int srcStep;
Ipp8u* pSrc8u[4];
Ipp16u* pSrc16u[4];
srcStep = m_ccomp[0].m_cc_step;
if(m_dst.precision <= 8)
{
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
pSrc8u[3] = m_ccomp[3].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P4C4R(pSrc8u,srcStep,pDst8u,dstStep,roi);
}
else
{
pSrc16u[0] = (Ipp16u*)m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc16u[1] = (Ipp16u*)m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc16u[2] = (Ipp16u*)m_ccomp[2].GetCCBufferPtr(thread_id);
pSrc16u[3] = (Ipp16u*)m_ccomp[3].GetCCBufferPtr(thread_id);
status = ippiCopy_16s_P4C4R((Ipp16s**)pSrc16u,srcStep,(Ipp16s*)pDst16u,dstStep,roi);
}
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P4C4R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
break;
default:
return JPEG_NOT_IMPLEMENTED;
}
}
// Gray to Gray
if(m_jpeg_color == JC_GRAY && m_dst.color == JC_GRAY)
{
int srcStep;
Ipp8u* pSrc8u;
Ipp16u* pSrc16u;
srcStep = m_ccomp[0].m_cc_step;
if(m_dst.precision <= 8)
{
pSrc8u = m_ccomp[0].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_C1R(pSrc8u,srcStep,pDst8u,dstStep,roi);
}
else
{
pSrc16u = (Ipp16u*)m_ccomp[0].GetCCBufferPtr(thread_id);
status = ippiCopy_16s_C1R((Ipp16s*)pSrc16u,srcStep,(Ipp16s*)pDst16u,dstStep,roi);
}
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_C1R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// Gray to RGB
if(m_jpeg_color == JC_GRAY && m_dst.color == JC_RGB)
{
int srcStep;
Ipp8u* pSrc8u[3];
srcStep = m_ccomp[0].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// Gray to BGR
if(m_jpeg_color == JC_GRAY && m_dst.color == JC_BGR)
{
int srcStep;
Ipp8u* pSrc8u[3];
srcStep = m_ccomp[0].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// RGB to RGB
if(m_jpeg_color == JC_RGB && m_dst.color == JC_RGB)
{
int srcStep;
Ipp8u* pSrc8u[3];
Ipp16u* pSrc16u[3];
srcStep = m_ccomp[0].m_cc_step;
if(m_dst.precision <= 8)
{
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
}
else
{
pSrc16u[0] = (Ipp16u*)m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc16u[1] = (Ipp16u*)m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc16u[2] = (Ipp16u*)m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_16s_P3C3R((Ipp16s**)pSrc16u,srcStep,(Ipp16s*)pDst16u,dstStep,roi);
}
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// RGB to BGR
if(m_jpeg_color == JC_RGB && m_dst.color == JC_BGR)
{
int srcStep;
Ipp8u* pSrc8u[3];
Ipp16u* pSrc16u[3];
srcStep = m_ccomp[0].m_cc_step;
if(m_dst.precision <= 8)
{
pSrc8u[2] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[0] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
}
else
{
pSrc16u[2] = (Ipp16u*)m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc16u[1] = (Ipp16u*)m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc16u[0] = (Ipp16u*)m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiCopy_16s_P3C3R((Ipp16s**)pSrc16u,srcStep,(Ipp16s*)pDst16u,dstStep,roi);
}
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// YCbCr to Gray
if(m_jpeg_color == JC_YCBCR && m_dst.color == JC_GRAY)
{
int srcStep;
Ipp8u* pSrc8u;
srcStep = m_ccomp[0].m_cc_step;
pSrc8u = m_ccomp[0].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_C1R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_C1R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// YCbCr to RGB
if(m_jpeg_color == JC_YCBCR && m_dst.color == JC_RGB)
{
int srcStep;
const Ipp8u* pSrc8u[3];
srcStep = m_ccomp[0].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiYCbCrToRGB_JPEG_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiYCbCrToRGB_JPEG_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// YCbCr to BGR
if(m_jpeg_color == JC_YCBCR && m_dst.color == JC_BGR)
{
int srcStep;
const Ipp8u* pSrc8u[3];
srcStep = m_ccomp[0].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiYCbCrToBGR_JPEG_8u_P3C3R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiYCbCrToBGR_JPEG_8u_P3C3R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// YCbCr to YCbCr (422 sampling)
if(m_jpeg_color == JC_YCBCR && m_dst.color == JC_YCBCR &&
m_jpeg_sampling == JS_422 && m_dst.sampling == JS_422)
{
int srcStep[3];
const Ipp8u* pSrc8u[3];
srcStep[0] = m_ccomp[0].m_cc_step;
srcStep[1] = m_ccomp[1].m_cc_step;
srcStep[2] = m_ccomp[2].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
status = ippiYCbCr422_8u_P3C2R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiYCbCr422_8u_P3C2R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// CMYK to CMYK
if(m_jpeg_color == JC_CMYK && m_dst.color == JC_CMYK)
{
int srcStep;
Ipp8u* pSrc8u[4];
srcStep = m_ccomp[0].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
pSrc8u[3] = m_ccomp[3].GetCCBufferPtr(thread_id);
status = ippiCopy_8u_P4C4R(pSrc8u,srcStep,pDst8u,dstStep,roi);
if(ippStsNoErr != status)
{
LOG1("IPP Error: ippiCopy_8u_P4C4R() failed - ",status);
return JPEG_ERR_INTERNAL;
}
}
// YCCK to CMYK
if(m_jpeg_color == JC_YCCK && m_dst.color == JC_CMYK)
{
int srcStep;
const Ipp8u* pSrc8u[4];
srcStep = m_ccomp[0].m_cc_step;
pSrc8u[0] = m_ccomp[0].GetCCBufferPtr(thread_id);
pSrc8u[1] = m_ccomp[1].GetCCBufferPtr(thread_id);
pSrc8u[2] = m_ccomp[2].GetCCBufferPtr(thread_id);
pSrc8u[3]
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -