128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan/* 228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan * Copyright 2017 The Chromium OS Authors. All rights reserved. 328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan * Use of this source code is governed by a BSD-style license that can be 428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan * found in the LICENSE file. 528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan */ 628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan#include "arc/jpeg_compressor.h" 828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan#include <memory> 1028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 1128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan#include <errno.h> 1228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 1328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan#include "arc/common.h" 1428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 1528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathannamespace arc { 1628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 1728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan// The destination manager that can access |result_buffer_| in JpegCompressor. 1828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanstruct destination_mgr { 1928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan public: 2028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan struct jpeg_destination_mgr mgr; 2128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan JpegCompressor* compressor; 2228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan}; 2328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 2428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth SwaminathanJpegCompressor::JpegCompressor() {} 2528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 2628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth SwaminathanJpegCompressor::~JpegCompressor() {} 2728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 2828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanbool JpegCompressor::CompressImage(const void* image, int width, int height, 2928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan int quality, const void* app1Buffer, 3028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan unsigned int app1Size) { 3128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (width % 8 != 0 || height % 2 != 0) { 3228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan LOGF(ERROR) << "Image size can not be handled: " << width << "x" << height; 3328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return false; 3428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 3528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 3628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan result_buffer_.clear(); 3728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (!Encode(image, width, height, quality, app1Buffer, app1Size)) { 3828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return false; 3928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 4028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan LOGF(INFO) << "Compressed JPEG: " << (width * height * 12) / 8 << "[" << width 4128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan << "x" << height << "] -> " << result_buffer_.size() << " bytes"; 4228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return true; 4328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 4428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 4528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanconst void* JpegCompressor::GetCompressedImagePtr() { 4628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return result_buffer_.data(); 4728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 4828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 4928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathansize_t JpegCompressor::GetCompressedImageSize() { 5028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return result_buffer_.size(); 5128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 5228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 5328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanvoid JpegCompressor::InitDestination(j_compress_ptr cinfo) { 5428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan destination_mgr* dest = reinterpret_cast<destination_mgr*>(cinfo->dest); 5528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan std::vector<JOCTET>& buffer = dest->compressor->result_buffer_; 5628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan buffer.resize(kBlockSize); 5728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.next_output_byte = &buffer[0]; 5828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.free_in_buffer = buffer.size(); 5928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 6028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 6128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanboolean JpegCompressor::EmptyOutputBuffer(j_compress_ptr cinfo) { 6228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan destination_mgr* dest = reinterpret_cast<destination_mgr*>(cinfo->dest); 6328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan std::vector<JOCTET>& buffer = dest->compressor->result_buffer_; 6428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan size_t oldsize = buffer.size(); 6528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan buffer.resize(oldsize + kBlockSize); 6628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.next_output_byte = &buffer[oldsize]; 6728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.free_in_buffer = kBlockSize; 6828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return true; 6928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 7028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 7128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanvoid JpegCompressor::TerminateDestination(j_compress_ptr cinfo) { 7228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan destination_mgr* dest = reinterpret_cast<destination_mgr*>(cinfo->dest); 7328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan std::vector<JOCTET>& buffer = dest->compressor->result_buffer_; 7428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan buffer.resize(buffer.size() - dest->mgr.free_in_buffer); 7528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 7628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 7728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanvoid JpegCompressor::OutputErrorMessage(j_common_ptr cinfo) { 7828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan char buffer[JMSG_LENGTH_MAX]; 7928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 8028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan /* Create the message */ 8128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan (*cinfo->err->format_message)(cinfo, buffer); 8228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan LOGF(ERROR) << buffer; 8328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 8428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 8528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanbool JpegCompressor::Encode(const void* inYuv, int width, int height, 8628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan int jpegQuality, const void* app1Buffer, 8728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan unsigned int app1Size) { 8828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_compress_struct cinfo; 8928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_error_mgr jerr; 9028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 9128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo.err = jpeg_std_error(&jerr); 9228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan // Override output_message() to print error log with ALOGE(). 9328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo.err->output_message = &OutputErrorMessage; 9428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_create_compress(&cinfo); 9528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan SetJpegDestination(&cinfo); 9628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 9728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan SetJpegCompressStruct(width, height, jpegQuality, &cinfo); 9828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_start_compress(&cinfo, TRUE); 9928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 10028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (app1Buffer != nullptr && app1Size > 0) { 10128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_write_marker(&cinfo, JPEG_APP0 + 1, 10228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan static_cast<const JOCTET*>(app1Buffer), app1Size); 10328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 10428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 10528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (!Compress(&cinfo, static_cast<const uint8_t*>(inYuv))) { 10628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return false; 10728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 10828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_finish_compress(&cinfo); 10928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return true; 11028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 11128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 11228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanvoid JpegCompressor::SetJpegDestination(jpeg_compress_struct* cinfo) { 11328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan destination_mgr* dest = 11428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan static_cast<struct destination_mgr*>((*cinfo->mem->alloc_small)( 11528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan (j_common_ptr)cinfo, JPOOL_PERMANENT, sizeof(destination_mgr))); 11628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->compressor = this; 11728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.init_destination = &InitDestination; 11828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.empty_output_buffer = &EmptyOutputBuffer; 11928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan dest->mgr.term_destination = &TerminateDestination; 12028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->dest = reinterpret_cast<struct jpeg_destination_mgr*>(dest); 12128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 12228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 12328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanvoid JpegCompressor::SetJpegCompressStruct(int width, int height, int quality, 12428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_compress_struct* cinfo) { 12528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->image_width = width; 12628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->image_height = height; 12728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->input_components = 3; 12828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->in_color_space = JCS_YCbCr; 12928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_set_defaults(cinfo); 13028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 13128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_set_quality(cinfo, quality, TRUE); 13228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan jpeg_set_colorspace(cinfo, JCS_YCbCr); 13328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->raw_data_in = TRUE; 13428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->dct_method = JDCT_IFAST; 13528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 13628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan // Configure sampling factors. The sampling factor is JPEG subsampling 420 13728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan // because the source format is YUV420. 13828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->comp_info[0].h_samp_factor = 2; 13928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->comp_info[0].v_samp_factor = 2; 14028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->comp_info[1].h_samp_factor = 1; 14128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->comp_info[1].v_samp_factor = 1; 14228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->comp_info[2].h_samp_factor = 1; 14328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cinfo->comp_info[2].v_samp_factor = 1; 14428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 14528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 14628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathanbool JpegCompressor::Compress(jpeg_compress_struct* cinfo, const uint8_t* yuv) { 14728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan JSAMPROW y[kCompressBatchSize]; 14828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan JSAMPROW cb[kCompressBatchSize / 2]; 14928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan JSAMPROW cr[kCompressBatchSize / 2]; 15028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan JSAMPARRAY planes[3]{y, cb, cr}; 15128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 15228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan size_t y_plane_size = cinfo->image_width * cinfo->image_height; 15328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan size_t uv_plane_size = y_plane_size / 4; 15428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan uint8_t* y_plane = const_cast<uint8_t*>(yuv); 15528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan uint8_t* u_plane = const_cast<uint8_t*>(yuv + y_plane_size); 15628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan uint8_t* v_plane = const_cast<uint8_t*>(yuv + y_plane_size + uv_plane_size); 15728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan std::unique_ptr<uint8_t[]> empty(new uint8_t[cinfo->image_width]); 15828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan memset(empty.get(), 0, cinfo->image_width); 15928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 16028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan while (cinfo->next_scanline < cinfo->image_height) { 16128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan for (int i = 0; i < kCompressBatchSize; ++i) { 16228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan size_t scanline = cinfo->next_scanline + i; 16328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (scanline < cinfo->image_height) { 16428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan y[i] = y_plane + scanline * cinfo->image_width; 16528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } else { 16628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan y[i] = empty.get(); 16728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 16828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 16928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan // cb, cr only have half scanlines 17028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan for (int i = 0; i < kCompressBatchSize / 2; ++i) { 17128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan size_t scanline = cinfo->next_scanline / 2 + i; 17228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (scanline < cinfo->image_height / 2) { 17328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan int offset = scanline * (cinfo->image_width / 2); 17428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cb[i] = u_plane + offset; 17528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cr[i] = v_plane + offset; 17628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } else { 17728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan cb[i] = cr[i] = empty.get(); 17828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 17928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 18028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 18128e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan int processed = jpeg_write_raw_data(cinfo, planes, kCompressBatchSize); 18228e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan if (processed != kCompressBatchSize) { 18328e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan LOGF(ERROR) << "Number of processed lines does not equal input lines."; 18428e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return false; 18528e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 18628e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan } 18728e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan return true; 18828e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} 18928e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan 19028e0f76353e06b24b7dae54e636dbb5ddc64d1a5Prashanth Swaminathan} // namespace arc 191