📄 decoder.cpp
字号:
int i, c; int len; TRC0("-> APP0"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; if(m_src.pData[m_src.currPos + 0] == 0x45 && m_src.pData[m_src.currPos + 1] == 0x78 && m_src.pData[m_src.currPos + 2] == 0x69 && m_src.pData[m_src.currPos + 3] == 0x66 && m_src.pData[m_src.currPos + 4] == 0) { m_exif_app1_detected = 1; m_exif_app1_data_size = len; if(m_exif_app1_data != 0) { ippFree(m_exif_app1_data); } m_exif_app1_data = (Ipp8u*)ippMalloc(len); for(i = 0; i < len; i++) { m_src._READ_BYTE(&c); m_exif_app1_data[i] = (Ipp8u)c; } } else { m_src.currPos += len; } m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseAPP1()const int APP14_ADOBE_LENGTH = 12;JERRCODE CJPEGDecoder::ParseAPP14(void){ int len; TRC0("-> APP14"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; if(len >= APP14_ADOBE_LENGTH && m_src.pData[m_src.currPos + 0] == 0x41 && m_src.pData[m_src.currPos + 1] == 0x64 && m_src.pData[m_src.currPos + 2] == 0x6f && m_src.pData[m_src.currPos + 3] == 0x62 && m_src.pData[m_src.currPos + 4] == 0x65) { // we've found Adobe APP14 marker len -= 5; m_src.currPos += 5; m_adobe_app14_detected = 1; m_src._READ_WORD(&m_adobe_app14_version); m_src._READ_WORD(&m_adobe_app14_flags0); m_src._READ_WORD(&m_adobe_app14_flags1); m_src._READ_BYTE(&m_adobe_app14_transform); TRC1(" adobe_app14_version - ",m_adobe_app14_version); TRC1(" adobe_app14_flags0 - ",m_adobe_app14_flags0); TRC1(" adobe_app14_flags1 - ",m_adobe_app14_flags1); TRC1(" adobe_app14_transform - ",m_adobe_app14_transform); len -= 7; } m_src.currPos += len; m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseAPP14()JERRCODE CJPEGDecoder::ParseCOM(void){ int i; int c; int len; TRC0("-> COM"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; TRC1(" bytes for comment - ",len); m_jpeg_comment_detected = 1; m_jpeg_comment_size = len; if(m_jpeg_comment != 0) { ippFree(m_jpeg_comment); } m_jpeg_comment = (Ipp8u*)ippMalloc(len+1); for(i = 0; i < len; i++) { m_src._READ_BYTE(&c); m_jpeg_comment[i] = (Ipp8u)c; } m_jpeg_comment[len] = 0; m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseCOM()JERRCODE CJPEGDecoder::ParseDQT(void){ int id; int len; JERRCODE jerr; TRC0("-> DQT"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; while(len > 0) { m_src._READ_BYTE(&id); int precision = (id & 0xf0) >> 4; TRC1(" id - ",(id & 0x0f)); TRC1(" precision - ",precision); if((id & 0x0f) > MAX_QUANT_TABLES) { return JPEG_BAD_QUANT_SEGMENT; } int q; Ipp8u qnt[DCTSIZE2]; for(int i = 0; i < DCTSIZE2; i++) { if(precision) { m_src._READ_WORD(&q); } else { m_src._READ_BYTE(&q); } qnt[i] = (Ipp8u)q; } jerr = m_qntbl[id & 0x0f].Init(id,qnt); if(JPEG_OK != jerr) { return jerr; } len -= DCTSIZE2 + DCTSIZE2*precision + 1; } if(len != 0) { return JPEG_BAD_SEGMENT_LENGTH; } m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseDQT()JERRCODE CJPEGDecoder::ParseDHT(void){ int i; int len; int index; int count; JERRCODE jerr; TRC0("-> DHT"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; int v; Ipp8u bits[MAX_HUFF_BITS]; Ipp8u vals[MAX_HUFF_VALS]; while(len > 16) { m_src._READ_BYTE(&index); count = 0; for(i = 0; i < MAX_HUFF_BITS; i++) { m_src._READ_BYTE(&v); bits[i] = (Ipp8u)v; count += bits[i]; } len -= 16 + 1; if(count > MAX_HUFF_VALS || count > len) { return JPEG_BAD_HUFF_TBL; } for(i = 0; i < count; i++) { m_src._READ_BYTE(&v); vals[i] = (Ipp8u)v; } len -= count; if(index >> 4) { // make AC Huffman table if(m_actbl[index & 0x0f].IsEmpty()) { jerr = m_actbl[index & 0x0f].Create(); if(JPEG_OK != jerr) { LOG0(" Can't create AC huffman table"); return JPEG_INTERNAL_ERROR; } } TRC1(" AC Huffman Table - ",index & 0x0f); jerr = m_actbl[index & 0x0f].Init(index & 0x0f,index >> 4,bits,vals); if(JPEG_OK != jerr) { LOG0(" Can't build AC huffman table"); return JPEG_INTERNAL_ERROR; } } else { // make DC Huffman table if(m_dctbl[index & 0x0f].IsEmpty()) { jerr = m_dctbl[index & 0x0f].Create(); if(JPEG_OK != jerr) { LOG0(" Can't create DC huffman table"); return JPEG_INTERNAL_ERROR; } } TRC1(" DC Huffman Table - ",index & 0x0f); jerr = m_dctbl[index & 0x0f].Init(index & 0x0f,index >> 4,bits,vals); if(JPEG_OK != jerr) { LOG0(" Can't build DC huffman table"); return JPEG_INTERNAL_ERROR; } } } if(len != 0) { return JPEG_BAD_SEGMENT_LENGTH; } m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseDHT()JERRCODE CJPEGDecoder::ParseSOF0(void){ int i; int len; JERRCODE jerr; TRC0("-> SOF0"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; m_src._READ_BYTE(&m_jpeg_precision); if(m_jpeg_precision != 8) { return JPEG_NOT_IMPLEMENTED; } m_src._READ_WORD(&m_jpeg_height); m_src._READ_WORD(&m_jpeg_width); m_src._READ_BYTE(&m_jpeg_ncomp); TRC1(" height - ",m_jpeg_height); TRC1(" width - ",m_jpeg_width); TRC1(" nchannels - ",m_jpeg_ncomp); if(m_jpeg_ncomp < 0 || m_jpeg_ncomp > MAX_COMPS_PER_SCAN) { return JPEG_BAD_FRAME_SEGMENT; } len -= 6; if(len != m_jpeg_ncomp * 3) { return JPEG_BAD_SEGMENT_LENGTH; } for(i = 0; i < m_jpeg_ncomp; i++) { m_src._READ_BYTE(&m_ccomp[i].m_id); int ss; m_src._READ_BYTE(&ss); m_ccomp[i].m_hsampling = (ss >> 4) & 0x0f; m_ccomp[i].m_vsampling = (ss ) & 0x0f; m_src._READ_BYTE(&m_ccomp[i].m_q_selector); if(m_ccomp[i].m_hsampling <= 0 || m_ccomp[i].m_vsampling <= 0) { return JPEG_BAD_FRAME_SEGMENT; } TRC1(" id ",m_ccomp[i].m_id); TRC1(" hsampling - ",m_ccomp[i].m_hsampling); TRC1(" vsampling - ",m_ccomp[i].m_vsampling); TRC1(" qselector - ",m_ccomp[i].m_q_selector); } jerr = _set_sampling(); if(JPEG_OK != jerr) { return jerr; } m_max_hsampling = m_ccomp[0].m_hsampling; m_max_vsampling = m_ccomp[0].m_vsampling; for(i = 0; i < m_jpeg_ncomp; i++) { if(m_max_hsampling < m_ccomp[i].m_hsampling) m_max_hsampling = m_ccomp[i].m_hsampling; if(m_max_vsampling < m_ccomp[i].m_vsampling) m_max_vsampling = m_ccomp[i].m_vsampling; } for(i = 0; i < m_jpeg_ncomp; i++) { m_ccomp[i].m_h_factor = m_max_hsampling / m_ccomp[i].m_hsampling; m_ccomp[i].m_v_factor = m_max_vsampling / m_ccomp[i].m_vsampling; } m_jpeg_mode = JPEG_BASELINE; m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseSOF0()JERRCODE CJPEGDecoder::ParseSOF2(void){ int i; int len; JERRCODE jerr; TRC0("-> SOF2"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; m_src._READ_BYTE(&m_jpeg_precision); if(m_jpeg_precision != 8) { return JPEG_NOT_IMPLEMENTED; } m_src._READ_WORD(&m_jpeg_height); m_src._READ_WORD(&m_jpeg_width); m_src._READ_BYTE(&m_jpeg_ncomp); TRC1(" height - ",m_jpeg_height); TRC1(" width - ",m_jpeg_width); TRC1(" nchannels - ",m_jpeg_ncomp); if(m_jpeg_ncomp < 0 || m_jpeg_ncomp > MAX_COMPS_PER_SCAN) { return JPEG_BAD_FRAME_SEGMENT; } len -= 6; if(len != m_jpeg_ncomp * 3) { return JPEG_BAD_SEGMENT_LENGTH; } for(i = 0; i < m_jpeg_ncomp; i++) { m_src._READ_BYTE(&m_ccomp[i].m_id); m_ccomp[i].m_comp_no = i; int ss; m_src._READ_BYTE(&ss); m_ccomp[i].m_hsampling = (ss >> 4) & 0x0f; m_ccomp[i].m_vsampling = (ss ) & 0x0f; m_src._READ_BYTE(&m_ccomp[i].m_q_selector); if(m_ccomp[i].m_hsampling <= 0 || m_ccomp[i].m_vsampling <= 0) { return JPEG_BAD_FRAME_SEGMENT; } TRC1(" id ",m_ccomp[i].m_id); TRC1(" hsampling - ",m_ccomp[i].m_hsampling); TRC1(" vsampling - ",m_ccomp[i].m_vsampling); TRC1(" qselector - ",m_ccomp[i].m_q_selector); } jerr = _set_sampling(); if(JPEG_OK != jerr) { return jerr; } m_max_hsampling = m_ccomp[0].m_hsampling; m_max_vsampling = m_ccomp[0].m_vsampling; for(i = 0; i < m_jpeg_ncomp; i++) { if(m_max_hsampling < m_ccomp[i].m_hsampling) m_max_hsampling = m_ccomp[i].m_hsampling; if(m_max_vsampling < m_ccomp[i].m_vsampling) m_max_vsampling = m_ccomp[i].m_vsampling; } for(i = 0; i < m_jpeg_ncomp; i++) { m_ccomp[i].m_h_factor = m_max_hsampling / m_ccomp[i].m_hsampling; m_ccomp[i].m_v_factor = m_max_vsampling / m_ccomp[i].m_vsampling; } m_jpeg_mode = JPEG_PROGRESSIVE; m_marker = JM_NONE; return JPEG_OK;} // CJPEGDecoder::ParseSOF2()JERRCODE CJPEGDecoder::ParseSOF3(void){ int i; int len; JERRCODE jerr; TRC0("-> SOF3"); if(m_src.currPos + 2 >= m_src.DataLen) { LOG0("Error: buffer too small"); return JPEG_BUFF_TOO_SMALL; } m_src._READ_WORD(&len); len -= 2; m_src._READ_BYTE(&m_jpeg_precision); if(m_jpeg_precision < 2 || m_jpeg_precision > 16) { return JPEG_BAD_FRAME_SEGMENT; } m_src._READ_WORD(&m_jpeg_height); m_src._READ_WORD(&m_jpeg_width); m_src._READ_BYTE(&m_jpeg_ncomp); TRC1(" height - ",m_jpeg_height); TRC1(" width - ",m_jpeg_width); TRC1(" nchannels - ",m_jpeg_ncomp); if(m_jpeg_ncomp != 1) { return JPEG_NOT_IMPLEMENTED; } len -= 6; if(len != m_jpeg_ncomp * 3) { return JPEG_BAD_SEGMENT_LENGTH; } for(i = 0; i < m_jpeg_ncomp; i++) { m_src._READ_BYTE(&m_ccomp[i].m_id); int ss; m_src._READ_BYTE(&ss); m_ccomp[i].m_hsampling = (ss >> 4) & 0x0f; m_ccomp[i].m_vsampling = (ss ) & 0x0f; m_src._READ_BYTE(&m_ccomp[i].m_q_selector); if(m_ccomp[i].m_hsampling <= 0 || m_ccomp[i].m_vsampling <= 0) { return JPEG_BAD_FRAME_SEGMENT; } TRC1(" id ",m_ccomp[i].m_id); TRC1(" hsampling - ",m_ccomp[i].m_hsampling); TRC1(" vsampling - ",m_ccomp[i].m_vsampling); TRC1(" qselector - ",m_ccomp[i].m_q_selector); } jerr = _set_sampling(); if(JPEG_OK != jerr) { return jerr; } m_max_hsampling = m_ccomp[0].m_hsampling; m_max_vsampling = m_ccomp[0].m_vsampling; for(i = 0; i < m_jpeg_ncomp; i++) { if(m_max_hsampling < m_ccomp[i].m_hsampling) m_max_hsampling = m_ccomp[i].m_hsampling;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -