pnw_hostjpeg.c revision f91c8768670386683a281cc39141e21bdda9c97f
1/*
2 * Copyright (c) 2011 Intel Corporation. All Rights Reserved.
3 * Copyright (c) Imagination Technologies Limited, UK
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the
7 * "Software"), to deal in the Software without restriction, including
8 * without limitation the rights to use, copy, modify, merge, publish,
9 * distribute, sub license, and/or sell copies of the Software, and to
10 * permit persons to whom the Software is furnished to do so, subject to
11 * the following conditions:
12 *
13 * The above copyright notice and this permission notice (including the
14 * next paragraph) shall be included in all copies or substantial portions
15 * of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
18 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
19 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
20 * IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
21 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
22 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
23 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 *
25 * Authors:
26 *    Elaine Wang <elaine.wang@intel.com>
27 *
28 */
29
30/*#include <string.h>*/
31#include <stdio.h>
32
33#include <pnw_hostcode.h>
34#include <pnw_hostjpeg.h>
35
36#define TRACK_FREE(ptr)                 free(ptr)
37#define TRACK_MALLOC(ptr)               malloc(ptr)
38#define TRACK_DEVICE_MEMORY_INIT
39#define TRACK_DEVICE_MEMORY_SHOW
40#define TIMER_INIT
41#define TIMER_START(...)
42#define TIMER_END(...)
43#define TIMER_CLOSE
44#define TIMER_CAPTURE(...)
45
46
47//#include <stdio.h>
48//#include <memory.h>
49//#include <stdlib.h>
50//#include <stdlib.h>
51//#include "malloc.h"
52//#include "mtxmain.h"
53
54//#include "mtxccb.h"
55//#include "topaz_tests.h"
56//#include "mvea_regs.h"
57//#include "mtx_regs.h"
58//#include "defs.h"
59//#include "mtxencode.h"
60//#include "topaz_vlc_regs.h"
61//#include "mtxheader.h"
62//#include "apiinternal.h"
63
64//#ifdef FIXME
65//extern void JPEGInitialiseHardware();
66//#endif
67
68#define JPEG_INCLUDE_NONAPI 1
69
70
71
72/////////////////////////////////////////////////////////////////////////////////////
73// BMP Reading Header Stuff
74/////////////////////////////////////////////////////////////////////////////////////
75
76
77const IMG_UINT8 gQuantLuma[QUANT_TABLE_SIZE_BYTES] = {   16, 11, 10, 16, 24, 40, 51, 61,
78        12, 12, 14, 19, 26, 58, 60, 55,
79        14, 13, 16, 24, 40, 57, 69, 56,
80        14, 17, 22, 29, 51, 87, 80, 62,
81        18, 22, 37, 56, 68, 109, 103, 77,
82        24, 35, 55, 64, 81, 104, 113, 92,
83        49, 64, 78, 87, 103, 121, 120, 101,
84        72, 92, 95, 98, 112, 100, 103, 99
85                                                     };
86
87
88/*const IMG_UINT8 DEBUG_gQuantLumaForCoverage[QUANT_TABLE_SIZE_BYTES] =
89{
90    16, 17, 21, 22, 30, 31, 22, 45,
91    18, 20, 23, 29, 32, 29, 44, 46,
92    19, 24, 28, 33, 36, 43, 47, 58,
93    25, 27, 34, 29, 42, 48, 57, 59,
94    26, 34, 37, 41, 49, 56 , 60 , 67,
95    36, 35, 40, 50, 55, 61 , 66 , 68,
96    37, 39, 51, 54, 62 , 65 , 69 , 72 ,
97    38, 52, 53, 63, 64 , 70 , 71 , 73
98};*/
99
100int DEBUG_giUsegQuantLumaForCoverageTable = 0;
101
102/*****************************************************************************/
103/*  \brief   gQuantChroma                                                    */
104/*                                                                           */
105/*  Contains the data that needs to be sent in the marker segment of an      */
106/*  interchange format JPEG stream or an abbreviated format table            */
107/*  specification data stream.                                               */
108/*  Quantizer table for the chrominance component                            */
109/*****************************************************************************/
110const IMG_UINT8 gQuantChroma[QUANT_TABLE_SIZE_BYTES] = {
111    17, 18, 24, 47, 99, 99, 99, 99,
112    18, 21, 26, 66, 99, 99, 99, 99,
113    24, 26, 56, 99, 99, 99, 99, 99,
114    47, 66, 99, 99, 99, 99, 99, 99,
115    99, 99, 99, 99, 99, 99, 99, 99,
116    99, 99, 99, 99, 99, 99, 99, 99,
117    99, 99, 99, 99, 99, 99, 99, 99,
118    99, 99, 99, 99, 99, 99, 99, 99
119};
120
121/*****************************************************************************/
122/*  \brief   gZigZag                                                         */
123/*                                                                           */
124/*  Zigzag scan pattern                                                      */
125/*****************************************************************************/
126const IMG_UINT8 gZigZag[] = {
127    0,  1,  8, 16,  9,  2,  3, 10,
128    17, 24, 32, 25, 18, 11,  4,  5,
129    12, 19, 26, 33, 40, 48, 41, 34,
130    27, 20, 13,  6,  7, 14, 21, 28,
131    35, 42, 49, 56, 57, 50, 43, 36,
132    29, 22, 15, 23, 30, 37, 44, 51,
133    58, 59, 52, 45, 38, 31, 39, 46,
134    53, 60, 61, 54, 47, 55, 62, 63
135};
136
137/*****************************************************************************/
138/*  \brief   gMarkerDataLumaDc                                               */
139/*                                                                           */
140/*  Contains the data that needs to be sent in the marker segment of an      */
141/*  interchange format JPEG stream or an abbreviated format table            */
142/*  specification data stream.                                               */
143/*  Specifies the huffman table used for encoding the luminance DC           */
144/*  coefficient differences. The table represents Table K.3 of               */
145/*  IS0/IEC 10918-1:1994(E)                                                  */
146/*****************************************************************************/
147const IMG_UINT8 gMarkerDataLumaDc[] = {
148    //TcTh  Li
149    0x00, 0x00, 0x01, 0x05, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x00, 0x00,
150    0x00, 0x00, 0x00, 0x00, 0x00,
151    // Vi
152    0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B
153};
154
155/*****************************************************************************/
156/*  \brief   gMarkerDataLumaAc                                               */
157/*                                                                           */
158/*  Contains the data that needs to be sent in the marker segment of an      */
159/*  interchange format JPEG stream or an abbreviated format table            */
160/*  specification data stream.                                               */
161/*  Specifies the huffman table used for encoding the luminance AC           */
162/*  coefficients. The table represents Table K.5 of IS0/IEC 10918-1:1994(E)  */
163/*****************************************************************************/
164const IMG_UINT8 gMarkerDataLumaAc[] = {
165    // TcTh  Li
166    0x10, 0x00, 0x02, 0x01, 0x03, 0x03, 0x02, 0x04, 0x03, 0x05, 0x05, 0x04,
167    0x04, 0x00, 0x00, 0x01, 0x7D,
168    // Vi
169    0x01, 0x02, 0x03, 0x00, 0x04, 0x11, 0x05, 0x12, 0x21, 0x31, 0x41, 0x06,
170    0x13, 0x51, 0x61, 0x07, 0x22, 0x71, 0x14, 0x32, 0x81, 0x91, 0xA1, 0x08,
171    0x23, 0x42, 0xB1, 0xC1, 0x15, 0x52, 0xD1, 0xF0, 0x24, 0x33, 0x62, 0x72,
172    0x82, 0x09, 0x0A, 0x16, 0x17, 0x18, 0x19, 0x1A, 0x25, 0x26, 0x27, 0x28,
173    0x29, 0x2A, 0x34, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44, 0x45,
174    0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58, 0x59,
175    0x5A, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x73, 0x74, 0x75,
176    0x76, 0x77, 0x78, 0x79, 0x7A, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89,
177    0x8A, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9A, 0xA2, 0xA3,
178    0xA4, 0xA5, 0xA6, 0xA7, 0xA8, 0xA9, 0xAA, 0xB2, 0xB3, 0xB4, 0xB5, 0xB6,
179    0xB7, 0xB8, 0xB9, 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7, 0xC8, 0xC9,
180    0xCA, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA, 0xE1, 0xE2,
181    0xE3, 0xE4, 0xE5, 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xF1, 0xF2, 0xF3, 0xF4,
182    0xF5, 0xF6, 0xF7, 0xF8, 0xF9, 0xFA
183};
184
185/*****************************************************************************/
186/*  \brief   gMarkerDataChromaDc                                             */
187/*                                                                           */
188/*  Contains the data that needs to be sent in the marker segment of an      */
189/*  interchange format JPEG stream or an abbreviated format table            */
190/*  specification data stream.                                               */
191/*  Specifies the huffman table used for encoding the chrominance DC         */
192/*  coefficient differences. The table represents Table K.4 of               */
193/*  IS0/IEC 10918-1:1994(E)                                                  */
194/*****************************************************************************/
195const IMG_UINT8 gMarkerDataChromaDc[] = {
196    // TcTh Li
197    0x01, 0x00, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
198    0x00, 0x00, 0x00, 0x00, 0x00,
199
200    // Vi
201    0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B
202};
203
204/*****************************************************************************/
205/*  \brief   gMarkerDataChromaAc                                             */
206/*                                                                           */
207/*  Contains the data that needs to be sent in the marker segment of an      */
208/*  interchange format JPEG stream or an abbreviated format table            */
209/*  specification data stream.                                               */
210/*  Specifies the huffman table used for encoding the chrominance AC         */
211/*  coefficients. The table represents Table K.6 of IS0/IEC 10918-1:1994(E)  */
212/*****************************************************************************/
213const IMG_UINT8 gMarkerDataChromaAc[] = {
214    // TcTh
215    0x11, 0x00, 0x02, 0x01, 0x02, 0x04, 0x04, 0x03, 0x04, 0x07, 0x05, 0x04,
216    0x04, 0x00, 0x01, 0x02, 0x77,
217
218    // Vi
219    0x00, 0x01, 0x02, 0x03, 0x11, 0x04, 0x05, 0x21, 0x31, 0x06, 0x12, 0x41,
220    0x51, 0x07, 0x61, 0x71, 0x13, 0x22, 0x32, 0x81, 0x08, 0x14, 0x42, 0x91,
221    0xA1, 0xB1, 0xC1, 0x09, 0x23, 0x33, 0x52, 0xF0, 0x15, 0x62, 0x72, 0xD1,
222    0x0A, 0x16, 0x24, 0x34, 0xE1, 0x25, 0xF1, 0x17, 0x18, 0x19, 0x1A, 0x26,
223    0x27, 0x28, 0x29, 0x2A, 0x35, 0x36, 0x37, 0x38, 0x39, 0x3A, 0x43, 0x44,
224    0x45, 0x46, 0x47, 0x48, 0x49, 0x4A, 0x53, 0x54, 0x55, 0x56, 0x57, 0x58,
225    0x59, 0x5A, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68, 0x69, 0x6A, 0x73, 0x74,
226    0x75, 0x76, 0x77, 0x78, 0x79, 0x7A, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
227    0x88, 0x89, 0x8A, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x98, 0x99, 0x9A,
228    0xA2, 0xA3, 0xA4, 0xA5, 0xA6, 0xA7, 0xA8, 0xA9, 0xAA, 0xB2, 0xB3, 0xB4,
229    0xB5, 0xB6, 0xB7, 0xB8, 0xB9, 0xBA, 0xC2, 0xC3, 0xC4, 0xC5, 0xC6, 0xC7,
230    0xC8, 0xC9, 0xCA, 0xD2, 0xD3, 0xD4, 0xD5, 0xD6, 0xD7, 0xD8, 0xD9, 0xDA,
231    0xE2, 0xE3, 0xE4, 0xE5, 0xE6, 0xE7, 0xE8, 0xE9, 0xEA, 0xF2, 0xF3, 0xF4,
232    0xF5, 0xF6, 0xF7, 0xF8, 0xF9, 0xFA
233};
234
235/*****************************************************************************/
236/*  \brief   gLumaDCCode                                                     */
237/*                                                                           */
238/*  Contains the code words to encode the luminance DC coefficient           */
239/*  differences. The code words are mentioned in table K.3 of                */
240/*  ISO/IEC 10918-1:1994(E)                                                  */
241/*****************************************************************************/
242const IMG_UINT16 gLumaDCCode[] = {
243    0x0000, 0x0002, 0x0003, 0x0004, 0x0005, 0x0006,
244    0x000E, 0x001E, 0x003E, 0x007E, 0x00FE, 0x01FE
245};
246
247/*****************************************************************************/
248/*  \brief   gLumaDCSize                                                     */
249/*                                                                           */
250/*  Contains the code length of the code words that are used to encode the   */
251/*  luminance DC coefficient differences. The code lengths are mentioned in  */
252/*  table K.3 of ISO/IEC 10918-1:1994(E)                                     */
253/*****************************************************************************/
254const IMG_UINT8 gLumaDCSize[] = {
255    0x0002, 0x0003, 0x0003, 0x0003, 0x0003, 0x0003,
256    0x0004, 0x0005, 0x0006, 0x0007, 0x0008, 0x0009
257};
258
259/*****************************************************************************/
260/*  \brief   gChromaDCCode                                                   */
261/*                                                                           */
262/*  Contains the code words to encode the chrominance DC coefficient         */
263/*  differences. The code words are mentioned in table K.4 of                */
264/*  ISO/IEC 10918-1:1994(E)                                                  */
265/*****************************************************************************/
266const IMG_UINT16 gChromaDCCode[] = {
267    0x0000, 0x0001, 0x0002, 0x0006, 0x000E, 0x001E,
268    0x003E, 0x007E, 0x00FE, 0x01FE, 0x03FE, 0x07FE
269};
270
271/*****************************************************************************/
272/*  \brief   gChromaDCSize                                                   */
273/*                                                                           */
274/*  Contains the code length of the code words that are used to encode the   */
275/*  chrominance DC coefficient differences. The code lengths are mentioned in*/
276/*  table K.4 of ISO/IEC 10918-1:1994(E)                                     */
277/*****************************************************************************/
278const IMG_UINT8 gChromaDCSize[] = {
279    0x0002, 0x0002, 0x0002, 0x0003, 0x0004, 0x0005,
280    0x0006, 0x0007, 0x0008, 0x0009, 0x000A, 0x000B
281};
282
283
284/*****************************************************************************/
285/*  \brief   gLumaACCode                                                     */
286/*                                                                           */
287/*  Contains the code words to encode the luminance AC coefficients. The     */
288/*  code words are arrange in the increasing order of run followed by size as*/
289/*  in table K.5 of ISO/IEC 10918-1:1994(E)                                  */
290/*****************************************************************************/
291const IMG_UINT16 gLumaACCode[] = {
292    0x000A, 0x0000, 0x0001, 0x0004, 0x000B, 0x001A, 0x0078, 0x00F8, 0x03F6,
293    0xFF82, 0xFF83, /* codes for run 0 */
294    0x000C, 0x001B, 0x0079, 0x01F6, 0x07F6, 0xFF84, 0xFF85, 0xFF86,
295    0xFF87, 0xFF88, /* codes for run 1 */
296    0x001C, 0x00F9, 0x03F7, 0x0FF4, 0xFF89, 0xFF8A, 0xFF8b, 0xFF8C,
297    0xFF8D, 0xFF8E, /* codes for run 2 */
298    0x003A, 0x01F7, 0x0FF5, 0xFF8F, 0xFF90, 0xFF91, 0xFF92, 0xFF93,
299    0xFF94, 0xFF95, /* codes for run 3 */
300    0x003B, 0x03F8, 0xFF96, 0xFF97, 0xFF98, 0xFF99, 0xFF9A, 0xFF9B,
301    0xFF9C, 0xFF9D, /* codes for run 4 */
302    0x007A, 0x07F7, 0xFF9E, 0xFF9F, 0xFFA0, 0xFFA1, 0xFFA2, 0xFFA3,
303    0xFFA4, 0xFFA5, /* codes for run 5 */
304    0x007B, 0x0FF6, 0xFFA6, 0xFFA7, 0xFFA8, 0xFFA9, 0xFFAA, 0xFFAB,
305    0xFFAC, 0xFFAD, /* codes for run 6 */
306    0x00FA, 0x0FF7, 0xFFAE, 0xFFAF, 0xFFB0, 0xFFB1, 0xFFB2, 0xFFB3,
307    0xFFB4, 0xFFB5, /* codes for run 7 */
308    0x01F8, 0x7FC0, 0xFFB6, 0xFFB7, 0xFFB8, 0xFFB9, 0xFFBA, 0xFFBB,
309    0xFFBC, 0xFFBD, /* codes for run 8 */
310    0x01F9, 0xFFBE, 0xFFBF, 0xFFC0, 0xFFC1, 0xFFC2, 0xFFC3, 0xFFC4,
311    0xFFC5, 0xFFC6, /* codes for run 9 */
312    0x01FA, 0xFFC7, 0xFFC8, 0xFFC9, 0xFFCA, 0xFFCB, 0xFFCC, 0xFFCD,
313    0xFFCE, 0xFFCF, /* codes for run A */
314    0x03F9, 0xFFD0, 0xFFD1, 0xFFD2, 0xFFD3, 0xFFD4, 0xFFD5, 0xFFD6,
315    0xFFD7, 0xFFD8, /* codes for run B */
316    0x03FA, 0xFFD9, 0xFFDA, 0xFFDB, 0xFFDC, 0xFFDD, 0xFFDE, 0xFFDF,
317    0xFFE0, 0xFFE1, /* codes for run C */
318    0x07F8, 0xFFE2, 0xFFE3, 0xFFE4, 0xFFE5, 0xFFE6, 0xFFE7, 0xFFE8,
319    0xFFE9, 0xFFEA, /* codes for run D */
320    0xFFEB, 0xFFEC, 0xFFED, 0xFFEE, 0xFFEF, 0xFFF0, 0xFFF1, 0xFFF2,
321    0xFFF3, 0xFFF4, /* codes for run E */
322    0xFFF5, 0xFFF6, 0xFFF7, 0xFFF8, 0xFFF9, 0xFFFA, 0xFFFB, 0xFFFC, 0xFFFD,
323    0xFFFE, 0x07F9  /* codes for run F */
324};
325
326/*****************************************************************************/
327/*  \brief   gLumaACSize                                                     */
328/*                                                                           */
329/*  Contains the code length of the code words that are used to encode the   */
330/*  luminance AC coefficients. The code lengths as in table K.5 of           */
331/*  ISO/IEC 10918-1:1994(E), are arranged in the increasing order of run     */
332/*  followed by size                                                         */
333/*****************************************************************************/
334const IMG_UINT8 gLumaACSize[] = {
335    0x04, 0x02, 0x02, 0x03, 0x04, 0x05, 0x07, 0x08, 0x0A, 0x10, 0x10,/* run 0 */
336    0x04, 0x05, 0x07, 0x09, 0x0B, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 1 */
337    0x05, 0x08, 0x0A, 0x0C, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 2 */
338    0x06, 0x09, 0x0C, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 3 */
339    0x06, 0x0A, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 4 */
340    0x07, 0x0B, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 5 */
341    0x07, 0x0C, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 6 */
342    0x08, 0x0C, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 7 */
343    0x09, 0x0F, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 8 */
344    0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 9 */
345    0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run A */
346    0x0A, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run B */
347    0x0A, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run C */
348    0x0B, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run D */
349    0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run E */
350    0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x0B /* run F */
351};
352
353/*****************************************************************************/
354/*  \brief   gChromaACCode                                                   */
355/*                                                                           */
356/*  Contains the code words to encode the chromiannce AC coefficients. The   */
357/*  code words are arrange in the increasing order of run followed by size   */
358/*  as in table K.6 of ISO/IEC 10918-1:1994(E)                               */
359/*****************************************************************************/
360const IMG_UINT16 gChromaACCode[] = {
361    0x0000, 0x0001, 0x0004, 0x000A, 0x0018, 0x0019, 0x0038, 0x0078, 0x01F4,
362    0x03F6, 0x0FF4, /* codes for run 0 */
363    0x000B, 0x0039, 0x00F6, 0x01F5, 0x07F6, 0x0FF5, 0xFF88, 0xFF89,
364    0xFF8A, 0xFF8B, /* codes for run 1 */
365    0x001A, 0x00F7, 0x03F7, 0x0FF6, 0x7FC2, 0xFF8C, 0xFF8D, 0xFF8E,
366    0xFF8F, 0xFF90, /* codes for run 2 */
367    0x001B, 0x00F8, 0x03F8, 0x0FF7, 0xFF91, 0xFF92, 0xFF93, 0xFF94,
368    0xFF95, 0xFF96, /* codes for run 3 */
369    0x003A, 0x01F6, 0xFF97, 0xFF98, 0xFF99, 0xFF9A, 0xFF9B, 0xFF9C,
370    0xFF9D, 0xFF9E, /* codes for run 4 */
371    0x003B, 0x03F9, 0xFF9F, 0xFFA0, 0xFFA1, 0xFFA2, 0xFFA3, 0xFFA4,
372    0xFFA5, 0xFFA6, /* codes for run 5 */
373    0x0079, 0x07F7, 0xFFA7, 0xFFA8, 0xFFA9, 0xFFAA, 0xFFAB, 0xFFAC,
374    0xFFAD, 0xFFAE, /* codes for run 6 */
375    0x007A, 0x07F8, 0xFFAF, 0xFFB0, 0xFFB1, 0xFFB2, 0xFFB3, 0xFFB4,
376    0xFFB5, 0xFFB6, /* codes for run 7 */
377    0x00F9, 0xFFB7, 0xFFB8, 0xFFB9, 0xFFBA, 0xFFBB, 0xFFBC, 0xFFBD,
378    0xFFBE, 0xFFBF, /* codes for run 8 */
379    0x01F7, 0xFFC0, 0xFFC1, 0xFFC2, 0xFFC3, 0xFFC4, 0xFFC5, 0xFFC6,
380    0xFFC7, 0xFFC8, /* codes for run 9 */
381    0x01F8, 0xFFC9, 0xFFCA, 0xFFCB, 0xFFCC, 0xFFCD, 0xFFCE, 0xFFCF,
382    0xFFD0, 0xFFD1, /* codes for run A */
383    0x01F9, 0xFFD2, 0xFFD3, 0xFFD4, 0xFFD5, 0xFFD6, 0xFFD7, 0xFFD8,
384    0xFFD9, 0xFFDA, /* codes for run B */
385    0x01FA, 0xFFDB, 0xFFDC, 0xFFDD, 0xFFDE, 0xFFDF, 0xFFE0, 0xFFE1,
386    0xFFE2, 0xFFE3, /* codes for run C */
387    0x07F9, 0xFFE4, 0xFFE5, 0xFFE6, 0xFFE7, 0xFFE8, 0xFFE9, 0xFFEA,
388    0xFFEb, 0xFFEC, /* codes for run D */
389    0x3FE0, 0xFFED, 0xFFEE, 0xFFEF, 0xFFF0, 0xFFF1, 0xFFF2, 0xFFF3,
390    0xFFF4, 0xFFF5, /* codes for run E */
391    0x7FC3, 0xFFF6, 0xFFF7, 0xFFF8, 0xFFF9, 0xFFFA, 0xFFFB, 0xFFFC, 0xFFFD,
392    0xFFFE, 0x03FA  /* codes for run F */
393};
394
395/*****************************************************************************/
396/*  \brief   gChromaACSize                                                   */
397/*                                                                           */
398/*  Contains the code length of the code words that are used to encode the   */
399/*  chrominance AC coefficients. The code lengths as in table K.5 of         */
400/*  ISO/IEC 10918-1:1994(E), are arranged in the increasing order of run     */
401/*  followed by size                                                         */
402/*****************************************************************************/
403const IMG_UINT8 gChromaACSize[] = {
404    0x02, 0x02, 0x03, 0x04, 0x05, 0x05, 0x06, 0x07, 0x09, 0x0A, 0x0C,/* run 0 */
405    0x04, 0x06, 0x08, 0x09, 0x0B, 0x0C, 0x10, 0x10, 0x10, 0x10,/* run 1 */
406    0x05, 0x08, 0x0A, 0x0C, 0x0F, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 2 */
407    0x05, 0x08, 0x0A, 0x0C, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 3 */
408    0x06, 0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 4 */
409    0x06, 0x0A, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 5 */
410    0x07, 0x0B, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 6 */
411    0x07, 0x0B, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 7 */
412    0x08, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 8 */
413    0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run 9 */
414    0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run A */
415    0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run B */
416    0x09, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run C */
417    0x0B, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run D */
418    0x0E, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10,/* run E */
419    0x0F, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x0A /* run F */
420};
421
422/*****************************************************************************/
423/*  \brief   gSize                                                           */
424/*                                                                           */
425/*  Table used in the computation of 4 lease significant bits 'SSSS' as      */
426/*  specified in table F.1 and F.2 of ISO/IEC 10918-1:1994(E). These values  */
427/*  are used to computes the 4 least significant bits and are not exactly    */
428/*  the values mentioned in the table                                        */
429/*****************************************************************************/
430const IMG_UINT8 gSize[] = {
431    0,
432    1,
433    2, 2,
434    3, 3, 3, 3,
435    4, 4, 4, 4, 4, 4, 4, 4,
436    5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5, 5
437};
438
439
440
441/*****************************************************************************/
442/*                                                                           */
443/* Function Name : fPutBitsToBuffer                                          */
444/*                                                                           */
445/* Description   : The function write a bit string into the stream           */
446/*                                                                           */
447/* Inputs        :                                                           */
448/* BitStream     : Pointer to the stream context                             */
449/* NoOfBits      : Size of the bit string                                    */
450/* ActualBits    : Bit string to be written                                  */
451/*                                                                           */
452/* Outputs       : On return the function has written the bit string into    */
453/*                 the stream                                                */
454/*                                                                           */
455/* Returns       : void                                                      */
456/*                                                                           */
457/* Revision History:                                                         */
458/*                                                                           */
459/* 14 12 2001 BG Creation                                                    */
460/*                                                                           */
461/*****************************************************************************/
462
463void fPutBitsToBuffer(STREAMTYPEW *BitStream, IMG_UINT8 NoOfBytes, IMG_UINT32 ActualBits)
464{
465    IMG_UINT8 ui8Lp;
466    IMG_UINT8 *pui8S;
467
468    pui8S = (IMG_UINT8 *)BitStream->Buffer;
469    pui8S += BitStream->Offset;
470
471    for (ui8Lp = NoOfBytes; ui8Lp > 0; ui8Lp--)
472        *(pui8S++) = ((IMG_UINT8 *) & ActualBits)[ui8Lp-1];
473
474    BitStream->Offset += NoOfBytes;
475}
476
477
478
479/***********************************************************************************
480 * Function Name      : AllocateCodedDataBuffers
481 * Inputs             :
482 * Outputs            :
483 * Returns            : PVRRC
484 * Description        : Allocates Device memory for coded buffers and build BUFFERINFO array
485 ************************************************************************************/
486
487IMG_ERRORCODE AllocateCodedDataBuffers(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext)
488{
489    IMG_UINT8 ui8Loop;
490
491    for (ui8Loop = 0 ; ui8Loop < pContext->sScan_Encode_Info.ui8NumberOfCodedBuffers; ui8Loop ++)
492        if (pContext->sScan_Encode_Info.aBufferTable[ui8Loop].pMemInfo == NULL) {
493            pContext->sScan_Encode_Info.aBufferTable[ui8Loop].ui32DataBufferSizeBytes = ((DATA_BUFFER_SIZE(pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan) + sizeof(BUFFER_HEADER)) + 3) & ~3;
494            pContext->sScan_Encode_Info.aBufferTable[ui8Loop].ui32DataBufferUsedBytes = 0;
495            pContext->sScan_Encode_Info.aBufferTable[ui8Loop].i8MTXNumber = 0; // Indicates buffer is idle
496            pContext->sScan_Encode_Info.aBufferTable[ui8Loop].ui16ScanNumber = 0; // Indicates buffer is idle
497            pContext->sScan_Encode_Info.aBufferTable[ui8Loop].pMemInfo =
498                pContext->jpeg_coded_buf.pMemInfo + PNW_JPEG_HEADER_MAX_SIZE + ui8Loop * pContext->ui32SizePerCodedBuffer;
499
500        }
501
502    return IMG_ERR_OK;
503}
504
505
506
507/***********************************************************************************
508 * Function Name      : FreeCodedDataBuffers
509 * Inputs             :
510 * Outputs            :
511 * Returns            : PVRRC
512 * Description        : Loops through our coded data buffers and frees them
513 ************************************************************************************/
514
515IMG_UINT32 FreeCodedDataBuffers(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext)
516{
517    IMG_UINT8 ui8Loop;
518    ui8Loop = pContext->sScan_Encode_Info.ui8NumberOfCodedBuffers;
519    /* Spin through and remove */
520    while (ui8Loop--)
521        if (pContext->sScan_Encode_Info.aBufferTable[ui8Loop].pMemInfo != NULL) {
522            /*      MMFreeDeviceMemory( &(pContext->sScan_Encode_Info.aBufferTable[ui8Loop].pMemInfo));*/
523            pContext->sScan_Encode_Info.aBufferTable[ui8Loop].pMemInfo = NULL;
524        }
525
526    return 0;
527}
528
529
530
531
532void SetupMCUDetails(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext,
533                     const IMG_UINT32 uiComponentNumber ,
534                     const IMG_UINT32 uiWidthBlocks ,
535                     const IMG_UINT32 uiHeightBlocks,
536                     const IMG_UINT32 uiLastRow,
537                     const IMG_UINT32 uiLastCol)
538{
539    MCUCOMPONENT* pMCUComp;
540
541    if (uiComponentNumber >=  MTX_MAX_COMPONENTS)
542        return;
543
544    pMCUComp = &pContext->pMTXSetup->MCUComponent[uiComponentNumber];
545
546    pMCUComp->ui32WidthBlocks = uiWidthBlocks * 8;
547    pMCUComp->ui32HeightBlocks = uiHeightBlocks * 8;
548
549    pMCUComp->ui32XLimit = uiLastCol;
550    pMCUComp->ui32YLimit = uiLastRow;
551
552    psb__information_message("MCU Details %i : %ix%i  %i  %i\n", uiComponentNumber, uiWidthBlocks , uiHeightBlocks ,  uiLastCol , uiLastRow);
553
554}
555
556
557/*****************************************************************************/
558/*                                                                           */
559/* Function Name : InitializeJpegEncode                                      */
560/*                                                                           */
561/* Description   : The function initializes an instance of the JPEG encoder  */
562/* Inputs/Outputs: Pointer to the JPEG Host context                                                      */
563/*                 Pointer to a IMG_FRAME type which will be created to be filled        */
564/*                      with the source image data                                                                               */
565/*****************************************************************************/
566
567IMG_ERRORCODE InitializeJpegEncode(TOPAZSC_JPEG_ENCODER_CONTEXT * pContext, object_surface_p pTFrame)
568{
569    IMG_ERRORCODE rc = IMG_ERR_OK;
570    IMG_UINT8  uc_i = 0;
571    IMG_UINT16 ui16_height_min;
572    IMG_UINT16 ui16_height_max;
573    IMG_UINT16 ui16_width_min;
574    IMG_UINT16 ui16_width_max;
575    //IMG_UINT16 ui16_width;
576    //IMG_UINT16 ui16_height;
577    IMG_UINT32 uiBlockCount = 0;
578    IMG_UINT16 ui16_comp_width, ui16_comp_height;
579    IMG_UINT8  uc_h_scale_max = 0, uc_v_scale_max = 0, uc_h_scale = 0;
580    IMG_UINT8  uc_v_scale;
581    IMG_UINT16 ui16_height;
582    context_ENC_p ctx = (context_ENC_p)pContext->ctx;
583
584    /*************************************************************************/
585    /* Determine the horizontal and the vertical scaling factor of each of   */
586    /* the components of the image                                           */
587    /*************************************************************************/
588
589    /*FIXME: ONLY support NV12, YV12 here*/
590    /*pTFrame->height isn't the real height of image, since vaCreateSurface
591     * makes it aligned with 32*/
592    ui16_height = ctx->Height;
593    switch (pContext->eFormat) {
594    case IMG_CODEC_YV16: /*422 format*/
595        ui16_height_min = ui16_height;
596        ui16_height_max = ui16_height;
597        ui16_width_min = pTFrame->width >> 1;
598        ui16_width_max = pTFrame->width;
599        break;
600    case IMG_CODEC_NV12:
601    default:
602        ui16_height_min = ui16_height >> 1;
603        ui16_height_max = ui16_height;
604        ui16_width_min = pTFrame->width >> 1;
605        ui16_width_max = pTFrame->width;
606        break;
607    }
608    /*ui16_height_min = ui16_width_min  = 65535;
609    ui16_height_max = ui16_width_max  = 0;
610
611    for(uc_i = 0; uc_i < pContext->pMTXSetup->ui32ComponentsInScan; uc_i++)
612    {
613    ui16_width  = pTFrame->Width;
614    if(ui16_width_min > ui16_width)
615    ui16_width_min  = ui16_width;
616    if(ui16_width_max < ui16_width)
617    ui16_width_max  = ui16_width;
618
619    ui16_height = pTFrame->Height;
620    if(ui16_height_min > ui16_height)
621    ui16_height_min = ui16_height;
622    if(ui16_height_max < ui16_height)
623    ui16_height_max = ui16_height;
624    }
625    */
626    /*********************************************************************/
627    /* Determine the horizonal and the vertical sampling frequency of    */
628    /* each of components in the image                                   */
629    /*********************************************************************/
630
631    uc_h_scale_max = (ui16_width_max + ui16_width_min - 1) /
632                     ui16_width_min;
633    uc_v_scale_max = (ui16_height_max + ui16_height_min - 1) /
634                     ui16_height_min;
635
636    for (uc_i = 0; uc_i < pContext->pMTXSetup->ui32ComponentsInScan; uc_i++) {
637
638        /*      ui16_comp_width  = pTFrame->aui32ComponentInfo[uc_i].ui32Width;
639                ui16_comp_height = pTFrame->aui32ComponentInfo[uc_i].ui32Height;*/
640        /*Support NV12, YV12, YV16 here. uc_h/v_scale should be
641         * 2x2(Y) or 1x1(U/V)*/
642        if (0 == uc_i) {
643            ui16_comp_width  = pTFrame->width;
644            ui16_comp_height = ui16_height;
645        } else {
646            switch (pContext->eFormat) {
647            case IMG_CODEC_YV16: /*422 format*/
648                ui16_comp_width  = pTFrame->width >> 1;
649                ui16_comp_height = ui16_height;
650                break;
651            case IMG_CODEC_NV12:
652            default:
653                ui16_comp_width  = pTFrame->width >> 1;
654                ui16_comp_height = ui16_height >> 1;
655            }
656        }
657
658        uc_h_scale       = (ui16_comp_width *  uc_h_scale_max) /
659                           ui16_width_max;
660        uc_v_scale       = (ui16_comp_height * uc_v_scale_max) /
661                           ui16_height_max;
662
663        uiBlockCount += (uc_h_scale * uc_v_scale);
664
665        switch (ISCHROMAINTERLEAVED(pContext->eFormat)) {
666        case C_INTERLEAVE:
667            // Chroma format is byte interleaved, as the engine runs using planar colour surfaces we need
668            // to fool the engine into offsetting by 16 instead of 8
669            if (uc_i > 0) { // if chroma, then double values
670                uc_h_scale <<= 1;
671                ui16_comp_width <<= 1;
672            }
673            break;
674        case LC_UVINTERLEAVE:
675            //Y0UY1V_8888 or Y0VY1U_8888 format
676            ui16_comp_width <<= 1;
677            break;
678        case LC_VUINTERLEAVE:
679            //Y0UY1V_8888 or Y0VY1U_8888 format
680            ui16_comp_width <<= 1;
681            break;
682        default:
683            break;
684        }
685
686        SetupMCUDetails(pContext, uc_i , uc_h_scale, uc_v_scale, ui16_comp_height, ui16_comp_width);
687
688        if (uiBlockCount > BLOCKCOUNTMAXPERCOLOURPLANE) {
689            return IMG_ERR_INVALID_SIZE;
690        }
691
692    }
693
694    return rc;
695}
696
697
698/***********************************************************************************
699  Function Name      : JPGEncodeBegin
700Inputs             : hInstance,psJpegInfo,ui32Quality
701Outputs            :
702Returns            : PVRRC
703Description        : Marks the begining of a JPEG encode and sets up encoder
704 ************************************************************************************/
705
706/*IMG_ERRORCODE JPGEncodeBegin(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext, IMG_FRAME *pTFrame)
707{
708    IMG_UINT32 ReturnCode = 0;
709    ReturnCode = InitializeJpegEncode(pContext, pTFrame);
710
711    return ReturnCode;
712} */
713/*****************************************************************************/
714/*                                                                           */
715/* Function Name : EncodeMarkerSegment                                       */
716/*                                                                           */
717/* Description   : Writes the marker segment of a JPEG stream according to   */
718/*                 the syntax mentioned in section B.2.4 of                  */
719/*                 ISO/IEC 10918-1:1994E                                     */
720/*                                                                           */
721/* Inputs        : Pointer to the JPEG Context and coded output buffer       */
722/*                                                                           */
723/* Processing    : Writes each of the following into the marker segment of   */
724/*                 the JPEG stream                                           */
725/*                 - luminance and chrominance quantization tables           */
726/*                 - huffman tables used for encoding the luminance and      */
727/*                   chrominance AC coefficients                             */
728/*                 - huffman tables used for encoding the luminance and      */
729/*                   chorimance  DC coefficient differences                  */
730/*                                                                           */
731/*                                                                           */
732/*****************************************************************************/
733
734IMG_UINT32 Legacy_EncodeMarkerSegment(LEGACY_JPEG_ENCODER_CONTEXT *pContext,
735                                      IMG_UINT8 *puc_stream_buff)
736{
737    STREAMTYPEW s_streamW;
738    IMG_UINT8 uc_i;
739
740    s_streamW.Offset = 0;
741    s_streamW.Buffer = puc_stream_buff;
742
743    /* Writing the start of image marker */
744    fPutBitsToBuffer(&s_streamW, 2, START_OF_IMAGE);
745
746    /* Writing the quantization table for luminance into the stream */
747    fPutBitsToBuffer(&s_streamW, 2, DQT_MARKER);
748
749    fPutBitsToBuffer(&s_streamW, 3, LQPQ << 4); // 20 bits = LQPQ, 4 bits = 0 (Destination identifier for the luminance quantizer tables)
750
751    for (uc_i = 0; uc_i < PELS_IN_BLOCK; uc_i++) {
752        fPutBitsToBuffer(&s_streamW, 1, pContext->pvLowLevelEncContext->Qmatrix[0][gZigZag[uc_i]]);
753    }
754
755    /* Writing the quantization table for chrominance into the stream */
756    fPutBitsToBuffer(&s_streamW, 2, DQT_MARKER);
757
758    fPutBitsToBuffer(&s_streamW, 3, (LQPQ << 4) | 1); // 20 bits = LQPQ, 4 bits = 1 (Destination identifier for the chrominance quantizer tables)
759
760    for (uc_i = 0; uc_i < PELS_IN_BLOCK; uc_i++) {
761        fPutBitsToBuffer(&s_streamW, 1, pContext->pvLowLevelEncContext->Qmatrix[1][gZigZag[uc_i]]);
762    }
763
764    /* Writing the huffman tables for luminance dc coeffs */
765    /* Write the DHT Marker */
766    fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
767    fPutBitsToBuffer(&s_streamW, 2, LH_DC);
768    for (uc_i = 0; uc_i < LH_DC - 2; uc_i++) {
769        fPutBitsToBuffer(&s_streamW, 1, gMarkerDataLumaDc[uc_i]);
770    }
771    /* Writing the huffman tables for luminance ac coeffs */
772    /* Write the DHT Marker */
773    fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
774    fPutBitsToBuffer(&s_streamW, 2, LH_AC);
775    for (uc_i = 0; uc_i < LH_AC - 2; uc_i++) {
776        fPutBitsToBuffer(&s_streamW, 1, gMarkerDataLumaAc[uc_i]);
777    }
778    /* Writing the huffman tables for chrominance dc coeffs */
779    fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
780    fPutBitsToBuffer(&s_streamW, 2, LH_DC);
781    for (uc_i = 0; uc_i < LH_DC - 2; uc_i++) {
782        fPutBitsToBuffer(&s_streamW, 1, gMarkerDataChromaDc[uc_i]);
783    }
784    /* Writing the huffman tables for luminance ac coeffs */
785    /* Write the DHT Marker */
786    fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
787    fPutBitsToBuffer(&s_streamW, 2, LH_AC);
788    for (uc_i = 0; uc_i < LH_AC - 2; uc_i++) {
789        fPutBitsToBuffer(&s_streamW, 1, gMarkerDataChromaAc[uc_i]);
790    }
791
792
793    return s_streamW.Offset;
794}
795
796/*****************************************************************************/
797/*                                                                           */
798/* Function Name : EncodeMarkerSegment                                       */
799/*                                                                           */
800/* Description   : Writes the marker segment of a JPEG stream according to   */
801/*                 the syntax mentioned in section B.2.4 of                  */
802/*                 ISO/IEC 10918-1:1994E                                     */
803/*                                                                           */
804/* Inputs        : Pointer to the JPEG Context and coded output buffer       */
805/*                                                                           */
806/* Processing    : Writes each of the following into the marker segment of   */
807/*                 the JPEG stream                                           */
808/*                 - luminance and chrominance quantization tables           */
809/*                 - huffman tables used for encoding the luminance and      */
810/*                   chrominance AC coefficients                             */
811/*                 - huffman tables used for encoding the luminance and      */
812/*                   chorimance  DC coefficient differences                  */
813/*                                                                           */
814/*****************************************************************************/
815
816IMG_UINT32 EncodeMarkerSegment(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext,
817                               IMG_UINT8 *puc_stream_buff, IMG_BOOL bIncludeHuffmanTables)
818{
819    STREAMTYPEW s_streamW;
820    IMG_UINT8 uc_i;
821
822    s_streamW.Offset = 0;
823    s_streamW.Buffer = puc_stream_buff;
824
825    /* Writing the start of image marker */
826    fPutBitsToBuffer(&s_streamW, 2, START_OF_IMAGE);
827
828    /* Writing the quantization table for luminance into the stream */
829    fPutBitsToBuffer(&s_streamW, 2, DQT_MARKER);
830
831    fPutBitsToBuffer(&s_streamW, 3, LQPQ << 4); // 20 bits = LQPQ, 4 bits = 0 (Destination identifier for the luminance quantizer tables)
832
833    IMG_ASSERT(PELS_IN_BLOCK <= QUANT_TABLE_SIZE_BYTES);
834    for (uc_i = 0; uc_i < PELS_IN_BLOCK; uc_i++) {
835        // Write zigzag ordered luma quantization values to our JPEG header
836        fPutBitsToBuffer(&s_streamW, 1, pContext->psTablesBlock->aui8LumaQuantParams[gZigZag[uc_i]]);
837    }
838
839    /* Writing the quantization table for chrominance into the stream */
840    fPutBitsToBuffer(&s_streamW, 2, DQT_MARKER);
841
842    fPutBitsToBuffer(&s_streamW, 3, (LQPQ << 4) | 1); // 20 bits = LQPQ, 4 bits = 1 (Destination identifier for the chrominance quantizer tables)
843
844    for (uc_i = 0; uc_i < PELS_IN_BLOCK; uc_i++) {
845        // Write zigzag ordered chroma quantization values to our JPEG header
846        fPutBitsToBuffer(&s_streamW, 1, pContext->psTablesBlock->aui8ChromaQuantParams[gZigZag[uc_i]]);
847    }
848
849    if (bIncludeHuffmanTables) {
850        /* Writing the huffman tables for luminance dc coeffs */
851        /* Write the DHT Marker */
852        fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
853        fPutBitsToBuffer(&s_streamW, 2, LH_DC);
854        for (uc_i = 0; uc_i < LH_DC - 2; uc_i++) {
855            fPutBitsToBuffer(&s_streamW, 1, gMarkerDataLumaDc[uc_i]);
856        }
857        /* Writing the huffman tables for luminance ac coeffs */
858        /* Write the DHT Marker */
859        fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
860        fPutBitsToBuffer(&s_streamW, 2, LH_AC);
861        for (uc_i = 0; uc_i < LH_AC - 2; uc_i++) {
862            fPutBitsToBuffer(&s_streamW, 1, gMarkerDataLumaAc[uc_i]);
863        }
864        /* Writing the huffman tables for chrominance dc coeffs */
865        fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
866        fPutBitsToBuffer(&s_streamW, 2, LH_DC);
867        for (uc_i = 0; uc_i < LH_DC - 2; uc_i++) {
868            fPutBitsToBuffer(&s_streamW, 1, gMarkerDataChromaDc[uc_i]);
869        }
870        /* Writing the huffman tables for luminance ac coeffs */
871        /* Write the DHT Marker */
872        fPutBitsToBuffer(&s_streamW, 2, DHT_MARKER);
873        fPutBitsToBuffer(&s_streamW, 2, LH_AC);
874        for (uc_i = 0; uc_i < LH_AC - 2; uc_i++) {
875            fPutBitsToBuffer(&s_streamW, 1, gMarkerDataChromaAc[uc_i]);
876        }
877    }
878
879    // Activate Restart markers
880    if (pContext->sScan_Encode_Info.ui16CScan > 1) {
881        // Only use restart intervals if we need them (ie. multiple Scan encode and/or parallel CB encode)
882        fPutBitsToBuffer(&s_streamW, 2, 0xFFDD); //Marker header
883        fPutBitsToBuffer(&s_streamW, 2, 4); // Byte size of marker (header not included)
884        fPutBitsToBuffer(&s_streamW, 2, pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan); // Restart Interval (same as MCUs per buffer)
885    }
886
887    return s_streamW.Offset;
888}
889
890/***********************************************************************************
891  Function Name      : JPGEncodeMarker
892Inputs             :    Pointer to JPEG Encoder context
893Pointer to coded buffer stream
894Pointer to pui32BytesWritten value
895Outputs            : ui8BitStreamBuffer,pui32BytesWritten
896Description        : Writes a JPEG marker segment to the bit stream
897 ************************************************************************************/
898
899IMG_UINT32 Legacy_JPGEncodeMarker(/*in */               LEGACY_JPEG_ENCODER_CONTEXT *pContext ,
900        /*in */         IMG_UINT8* pui8BitStreamBuffer ,
901        /*out*/         IMG_UINT32 *pui32BytesWritten)
902{
903#ifdef JPEG_VERBOSE
904    printf("PVRJPGEncodeMarker");
905#endif
906
907    if (pContext->eCurrentActive != LEGACY_JPEG_API_CURRENT_ACTIVE_ENCODE) {
908        /* Cannot be called outside begin and end*/
909        return 2;
910    }
911
912    *pui32BytesWritten += Legacy_EncodeMarkerSegment(pContext, pui8BitStreamBuffer);
913
914    return 0;
915}
916
917/***********************************************************************************
918  Function Name      : JPGEncodeMarker
919Inputs             :    Pointer to JPEG Encoder context
920Pointer to coded buffer stream
921Pointer to Byteswritten value
922bIncludeHuffmanTables - Set to true to include the huffman tables in the stream
923Outputs            : ui8BitStreamBuffer,pui32BytesWritten
924Description        : Writes a JPEG marker segment to the bit stream
925 ************************************************************************************/
926
927IMG_UINT32 JPGEncodeMarker(/*in */              TOPAZSC_JPEG_ENCODER_CONTEXT *pContext ,
928        /*in */         IMG_UINT8* pui8BitStreamBuffer ,
929        /*out*/         IMG_UINT32 *pui32BytesWritten, IMG_BOOL bIncludeHuffmanTables)
930{
931#ifdef JPEG_VERBOSE
932    printf("PVRJPGEncodeMarker");
933#endif
934
935
936    *pui32BytesWritten += EncodeMarkerSegment(pContext, pui8BitStreamBuffer + *pui32BytesWritten, bIncludeHuffmanTables);
937
938    return 0;
939}
940
941
942/*****************************************************************************/
943/*                                                                           */
944/* Function Name : EncodeFrameHeader                                         */
945/*                                                                           */
946/* Description   : Writes the frame header of a JPEG stream according to     */
947/*                 the syntax mentioned in section B.2.2 of                  */
948/*                 ISO/IEC 10918-1:1994E .                                   */
949/*                                                                           */
950/* Inputs        :                                                           */
951/* ps_jpeg_params: Ptr to the JPEG encoder parameter context                 */
952/* ps_jpeg_comp  : Ptr to the JPEG image component context                   */
953/* puc_stream_buff:Ptr to the bistream buffer from where to start writing    */
954/*                                                                           */
955/* Processing    : Writes each of the following into the frame header of     */
956/*                 the JPEG stream                                           */
957/*                 - JPEG image component identifier                         */
958/*                 - Horizontal and vertical sampling factor                 */
959/*                 - Quantization table identifier for each of the components*/
960/*                                                                           */
961/* Returns       : Number of bytes written into the stream                   */
962/*                                                                           */
963/*****************************************************************************/
964
965IMG_UINT32 Legacy_EncodeFrameHeader(LEGACY_JPEGENC_ITTIAM_PARAMS *ps_jpeg_params,
966                                    LEGACY_JPEGENC_ITTIAM_COMPONENT *ps_jpeg_comp,
967                                    IMG_UINT8 *puc_stream_buff)
968{
969    STREAMTYPEW ps_streamW;
970    IMG_UINT16 ui16_i;
971    IMG_UINT8  uc_num_comp_in_img;
972
973    uc_num_comp_in_img = ps_jpeg_comp->uc_num_comp_in_img;
974
975    ps_streamW.Offset = 0;
976    ps_streamW.Buffer = puc_stream_buff;
977
978
979    if (ps_jpeg_params->uc_isAbbreviated != 0)
980        fPutBitsToBuffer(&ps_streamW, 2, START_OF_IMAGE);
981
982    /* Writing the frame header */
983    fPutBitsToBuffer(&ps_streamW, 2, SOF_BASELINE_DCT);
984    /* Frame header length */
985    fPutBitsToBuffer(&ps_streamW, 2, 8 + 3 * uc_num_comp_in_img);
986    /* Precision */
987    fPutBitsToBuffer(&ps_streamW, 1, 8);
988    /* Height : sample lines */
989    fPutBitsToBuffer(&ps_streamW, 2, ps_jpeg_params->ui16_height);
990    /* Width : samples per line */
991    fPutBitsToBuffer(&ps_streamW, 2, ps_jpeg_params->ui16_width);
992    /* Number of image components */
993    fPutBitsToBuffer(&ps_streamW, 1, uc_num_comp_in_img);
994
995    if (uc_num_comp_in_img > MAX_COMP_IN_SCAN)
996        uc_num_comp_in_img = MAX_COMP_IN_SCAN;
997    for (ui16_i = 0; ui16_i < uc_num_comp_in_img; ui16_i++) {
998        /* Component identifier */
999        fPutBitsToBuffer(&ps_streamW, 1, ps_jpeg_comp->puc_comp_id[ui16_i]);
1000
1001        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1002        fPutBitsToBuffer(&ps_streamW, 1, (ps_jpeg_comp->puc_horiz_scale[ui16_i] << 4) | ps_jpeg_comp->puc_vert_scale[ui16_i]);
1003
1004        /* Quantization table destination selector */
1005        fPutBitsToBuffer(&ps_streamW, 1, ps_jpeg_comp->puc_q_table_id[ui16_i]);
1006
1007        ps_jpeg_comp->CompIdtoIndex[ ps_jpeg_comp->puc_comp_id[ui16_i] ] = (IMG_UINT8) ui16_i;
1008    }
1009
1010    //Use if you want start of scan (image data) to align to 32
1011    fPutBitsToBuffer(&ps_streamW, 1, 0xFF);
1012
1013    return ps_streamW.Offset;
1014}
1015
1016
1017/*****************************************************************************/
1018/*                                                                           */
1019/* Function Name : EncodeFrameHeader                                         */
1020/*                                                                           */
1021/* Description   : Writes the frame header of a JPEG stream according to     */
1022/*                 the syntax mentioned in section B.2.2 of                  */
1023/*                 ISO/IEC 10918-1:1994E .                                   */
1024/*                                                                           */
1025/* Inputs        :                                                           */
1026/*                                      pContext                        - Ptr to the JPEG encoder context        */
1027/*                                      puc_stream_buff         - Ptr to the bistream buffer from        */
1028/*                                                                                      where to start writing                   */
1029/*                                                                           */
1030/* Processing    : Writes each of the following into the frame header of     */
1031/*                 the JPEG stream                                           */
1032/*                 - JPEG image component identifier                         */
1033/*                 - Horizontal and vertical sampling factor                 */
1034/*                 - Quantization table identifier for each of the components*/
1035/*                                                                           */
1036/* Returns       : Number of bytes written into the stream                   */
1037/*                                                                           */
1038/*****************************************************************************/
1039
1040IMG_UINT32 EncodeFrameHeader(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext,
1041                             IMG_UINT8 *puc_stream_buff)
1042{
1043    STREAMTYPEW ps_streamW;
1044    IMG_UINT8  uc_num_comp_in_img;
1045
1046    uc_num_comp_in_img = pContext->pMTXSetup->ui32ComponentsInScan;
1047
1048    ps_streamW.Offset = 0;
1049    ps_streamW.Buffer = puc_stream_buff;
1050
1051
1052    //if(ps_jpeg_params->uc_isAbbreviated != 0)
1053    //   fPutBitsToBuffer(&ps_streamW, 2, START_OF_IMAGE);
1054
1055    /* Writing the frame header */
1056    fPutBitsToBuffer(&ps_streamW, 2, SOF_BASELINE_DCT);
1057    /* Frame header length */
1058    fPutBitsToBuffer(&ps_streamW, 2, 8 + 3 * uc_num_comp_in_img);
1059    /* Precision */
1060    fPutBitsToBuffer(&ps_streamW, 1, 8);
1061    /* Height : sample lines */
1062    fPutBitsToBuffer(&ps_streamW, 2, pContext->ui32OutputHeight);
1063    /* Width : samples per line */
1064    fPutBitsToBuffer(&ps_streamW, 2, pContext->ui32OutputWidth);
1065    /* Number of image components */
1066    fPutBitsToBuffer(&ps_streamW, 1, uc_num_comp_in_img);
1067
1068    //Luma Details
1069    /* Component identifier */
1070    fPutBitsToBuffer(&ps_streamW, 1, 1); //CompId 0 = 1, 1 = 2, 2 = 3
1071    fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[0].ui32WidthBlocks >> 3) << 4) | (pContext->pMTXSetup->MCUComponent[0].ui32HeightBlocks >> 3));
1072    fPutBitsToBuffer(&ps_streamW, 1, 0); // 0 = Luma(0), 1,2 = Chroma(1)
1073
1074    //Chroma Details
1075    if (pContext->pMTXSetup->ui32DataInterleaveStatus < C_INTERLEAVE) { //Chroma planar
1076        fPutBitsToBuffer(&ps_streamW, 1, 2); //CompId 0 = 1, 1 = 2, 2 = 3
1077        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1078        fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[1].ui32WidthBlocks >> 3) << 4) | (pContext->pMTXSetup->MCUComponent[1].ui32HeightBlocks >> 3));
1079        fPutBitsToBuffer(&ps_streamW, 1, 1); // 0 = Luma(0), 1,2 = Chroma(1)
1080        fPutBitsToBuffer(&ps_streamW, 1, 3); //CompId 0 = 1, 1 = 2, 2 = 3
1081        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1082        fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[2].ui32WidthBlocks >> 3) << 4) | (pContext->pMTXSetup->MCUComponent[2].ui32HeightBlocks >> 3));
1083        fPutBitsToBuffer(&ps_streamW, 1, 1); // 0 = Luma(0), 1,2 = Chroma(1)
1084    } else if (pContext->pMTXSetup->ui32DataInterleaveStatus == C_INTERLEAVE) { // Chroma Interleaved
1085        fPutBitsToBuffer(&ps_streamW, 1, 2); //CompId 0 = 1, 1 = 2, 2 = 3
1086        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1087        fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[1].ui32WidthBlocks >> 3) << 3) | (pContext->pMTXSetup->MCUComponent[1].ui32HeightBlocks >> 3));
1088        fPutBitsToBuffer(&ps_streamW, 1, 1); // 0 = Luma(0), 1,2 = Chroma(1)
1089        fPutBitsToBuffer(&ps_streamW, 1, 3); //CompId 0 = 1, 1 = 2, 2 = 3
1090        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1091        fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[2].ui32WidthBlocks >> 3) << 3) | (pContext->pMTXSetup->MCUComponent[2].ui32HeightBlocks >> 3));
1092        fPutBitsToBuffer(&ps_streamW, 1, 1); // 0 = Luma(0), 1,2 = Chroma(1)
1093    } else { //Chroma YUYV - Special case
1094        fPutBitsToBuffer(&ps_streamW, 1, 2); //CompId 0 = 1, 1 = 2, 2 = 3
1095        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1096        fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[1].ui32WidthBlocks >> 3) << 4) | (pContext->pMTXSetup->MCUComponent[1].ui32HeightBlocks >> 3));
1097        fPutBitsToBuffer(&ps_streamW, 1, 1); // 0 = Luma(0), 1,2 = Chroma(1)
1098        fPutBitsToBuffer(&ps_streamW, 1, 3); //CompId 0 = 1, 1 = 2, 2 = 3
1099        /* 4 bit Horizontal and 4 bit vertical sampling factors */
1100        fPutBitsToBuffer(&ps_streamW, 1, ((pContext->pMTXSetup->MCUComponent[2].ui32WidthBlocks >> 3) << 4) | (pContext->pMTXSetup->MCUComponent[2].ui32HeightBlocks >> 3));
1101        fPutBitsToBuffer(&ps_streamW, 1, 1); // 0 = Luma(0), 1,2 = Chroma(1)
1102    }
1103
1104
1105    //Use if you want start of scan (image data) to align to 32
1106    fPutBitsToBuffer(&ps_streamW, 1, 0xFF);
1107
1108    return ps_streamW.Offset;
1109}
1110
1111
1112/***********************************************************************************
1113  Function Name      : JPGEncodeHeader
1114Inputs             : Pointer to JPEG Context
1115Outputs            : ui8BitStreamBuffer,pui32BytesWritten
1116Returns            : PVRRC
1117Description        : Writes a frame header to the bit stream
1118Max written 21 bytes
1119 ************************************************************************************/
1120
1121IMG_UINT32 Legacy_JPGEncodeHeader(/*in */               LEGACY_JPEG_ENCODER_CONTEXT *pContext,
1122        /*out */        IMG_UINT8*              pui8BitStreamBuffer ,
1123        /*out*/         IMG_UINT32*             pui32BytesWritten)
1124{
1125#ifdef JPEG_VERBOSE
1126    printf("PVRJPGEncodeHeader");
1127#endif
1128
1129    if (pContext->eCurrentActive != LEGACY_JPEG_API_CURRENT_ACTIVE_ENCODE) {
1130        /* Cannot be called outside begin and end*/
1131        return 2;
1132    }
1133
1134    *pui32BytesWritten += Legacy_EncodeFrameHeader(&pContext->JPEGEncoderParams,
1135                          &pContext->sJPEGEncoderComp,
1136                          pui8BitStreamBuffer + *pui32BytesWritten);
1137    return 0;
1138}
1139
1140/***********************************************************************************
1141  Function Name      : JPGEncodeHeader
1142Inputs             : Pointer to JPEG context
1143Outputs            : ui8BitStreamBuffer,pui32BytesWritten
1144Description        : Writes a frame header to the bit stream
1145Max written 21 bytes
1146 ************************************************************************************/
1147
1148IMG_UINT32 JPGEncodeHeader(/*in */              TOPAZSC_JPEG_ENCODER_CONTEXT *pContext,
1149        /*out */        IMG_UINT8*              pui8BitStreamBuffer ,
1150        /*out*/         IMG_UINT32*             pui32BytesWritten)
1151{
1152#ifdef JPEG_VERBOSE
1153    printf("JPGEncodeHeader");
1154#endif
1155
1156    *pui32BytesWritten += EncodeFrameHeader(pContext, pui8BitStreamBuffer + *pui32BytesWritten);
1157
1158    return 0;
1159}
1160
1161
1162/***********************************************************************************
1163 * Function Name      : SetupIssueSetup
1164 * Inputs             :
1165 pContext - Pointer to JPEG context
1166 ui32ComponentsInScan - Number of components to be encoded in a scan
1167 aui8Planes - Array of 3 bytes indexing YUV colour planes
1168 pTFrame - Pointer to source data
1169 ui32TableA, ui32TableB - Quantization table index values
1170 * Outputs            :
1171 * Returns            : PVRRC
1172 * Description        : Issues the Setup structure to MTX
1173 ************************************************************************************/
1174
1175IMG_UINT32 SetupIssueSetup(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext, const IMG_UINT32 ui32ComponentsInScan, IMG_UINT8* aui8Planes,  object_surface_p pTFrame, const IMG_UINT32 ui32TableA , const IMG_UINT32 ui32TableB)
1176{
1177    IMG_UINT32 ReturnCode = 0;
1178    IMG_INT32 i32Lp;
1179    //COMPONENTPLANE* pSrcPlane;
1180    IMG_UINT32 srf_buf_offset;
1181    context_ENC_p ctx = (context_ENC_p)pContext->ctx;
1182    pnw_cmdbuf_p cmdbuf = ctx->obj_context->pnw_cmdbuf;
1183    /*TOPAZSC_JPEG_ENCODER_CONTEXT *pContext = pEncContext->psJpegHC;*/
1184
1185#ifdef JPEG_VERBOSE
1186    printf("\nSetupIssueSetup");
1187#endif
1188
1189    pContext->pMTXSetup->ui32ComponentsInScan = ui32ComponentsInScan;
1190    pContext->pMTXSetup->ui32DataInterleaveStatus = ISCHROMAINTERLEAVED(pContext->eFormat);
1191    pContext->pMTXSetup->ui32TableA = ui32TableA;
1192
1193    /*MMUpdateDeviceMemory( pContext->pMemInfoMTXSetup )*/;
1194    // we want to process the handles that have been placed into the buffer
1195    /*for(n=0;n<pContext->pMTXSetup->ui32ComponentsInScan;n++)
1196    {
1197    pSrcPlane = &pContext->pMTXSetup->ComponentPlane[n];
1198    TIMER_START(hardwareduration,"");
1199    MMDeviceMemWriteDeviceMemRef(pContext->pMemInfoMTXSetup->iu32MemoryRegionID, pContext->pMemInfoMTXSetup->hShadowMem, (IMG_UINT32)   ((IMG_BYTE*)&pSrcPlane->ui32PhysAddr - (IMG_BYTE*)pContext->pMTXSetup),TAL_NULL_MANGLER_ID,(IMG_HANDLE) pTFrame->psBuffer->pMemInfo->hShadowMem, pTFrame->aui32ComponentOffset[aui8Planes[n]]);
1200    TIMER_END("HW - MMDeviceMemWriteDeviceMemRef in SetupIssueSetup (hostjpeg.c)");
1201    }*/
1202    /*Support PL12/NV12, YV12/IYUV, YV16*/
1203    srf_buf_offset = pTFrame->psb_surface->buf.buffer_ofs;
1204    RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[0].ui32PhysAddr, srf_buf_offset , &pTFrame->psb_surface->buf);
1205    switch (pContext->eFormat) {
1206    case IMG_CODEC_IYUV:
1207    case IMG_CODEC_PL8:
1208        RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[1].ui32PhysAddr,
1209                             srf_buf_offset + pTFrame->psb_surface->stride * pTFrame->height,
1210                             &pTFrame->psb_surface->buf);
1211        RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[2].ui32PhysAddr,
1212                             srf_buf_offset + pTFrame->psb_surface->stride * pTFrame->height
1213                             + (pTFrame->psb_surface->stride / 2) *(pTFrame->height / 2),
1214                             &pTFrame->psb_surface->buf);
1215        break;
1216    case IMG_CODEC_IMC2:
1217    case IMG_CODEC_PL12:
1218    case IMG_CODEC_NV12:
1219        RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[1].ui32PhysAddr,
1220                             srf_buf_offset + pTFrame->psb_surface->stride * pTFrame->height,
1221                             &pTFrame->psb_surface->buf);
1222        //Byte interleaved surface, so need to force chroma to use single surface by fooling it into
1223        //thinking it's dealing with standard 8x8 planaerblocks
1224        RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[2].ui32PhysAddr,
1225                             srf_buf_offset + pTFrame->psb_surface->stride * pTFrame->height
1226                             + 8,
1227                             &pTFrame->psb_surface->buf);
1228        break;
1229    case IMG_CODEC_YV16:
1230        /*V*/
1231        RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[2].ui32PhysAddr,
1232                             srf_buf_offset + pTFrame->psb_surface->stride * pTFrame->height,
1233                             &pTFrame->psb_surface->buf);
1234        /*U*/
1235        RELOC_PIC_PARAMS_PNW(&pContext->pMTXSetup->ComponentPlane[1].ui32PhysAddr,
1236                             srf_buf_offset + pTFrame->psb_surface->stride * pTFrame->height
1237                             + (pTFrame->psb_surface->stride) *(pTFrame->height) / 2,
1238                             &pTFrame->psb_surface->buf);
1239        break;
1240    default:
1241        psb__error_message(" Not supported FOURCC %x!\n", pContext->eFormat);
1242        return -1;
1243
1244    }
1245
1246
1247    psb__information_message("TOPAZ_PDUMP: ui32DataInterleaveStatus %x\n", pContext->pMTXSetup->ui32DataInterleaveStatus);
1248    psb__information_message("TOPAZ_PDUMP: ui32TableA %x \n", pContext->pMTXSetup->ui32TableA);
1249    psb__information_message("TOPAZ_PDUMP:ui32ComponentsInScan %x\n", pContext->pMTXSetup->ui32ComponentsInScan);
1250    for (i32Lp = 0; i32Lp < 3; i32Lp++) {
1251        psb__information_message("TOPAZ_PDUMP: ComponentPlane[%d]: 0x%x, %d, %d\n",
1252                                 i32Lp, pContext->pMTXSetup->ComponentPlane[i32Lp].ui32PhysAddr, pContext->pMTXSetup->ComponentPlane[i32Lp].ui32Stride, pContext->pMTXSetup->ComponentPlane[i32Lp].ui32Height);
1253        psb__information_message("TOPAZ_PDUMP: MCUComponent[%d]: %d, %d, %d, %d\n", i32Lp, pContext->pMTXSetup->MCUComponent[i32Lp].ui32WidthBlocks, pContext->pMTXSetup->MCUComponent[i32Lp].ui32HeightBlocks, pContext->pMTXSetup->MCUComponent[i32Lp].ui32XLimit, pContext->pMTXSetup->MCUComponent[i32Lp].ui32YLimit);
1254    }
1255
1256    i32Lp = ctx->NumCores;
1257    while (--i32Lp > -1) {
1258        /*TOPAZ_InsertCommand(
1259                pEncContext,
1260                i32Lp,
1261                MTX_CMDID_SETUP,
1262                IMG_FALSE,
1263                IMG_NULL,
1264                pContext->pMemInfoMTXSetup );*/
1265
1266        pnw_cmdbuf_insert_command_package(ctx->obj_context,
1267                                          i32Lp,
1268                                          MTX_CMDID_SETUP,
1269                                          &(ctx->obj_context->pnw_cmdbuf->header_mem),
1270                                          0);
1271    }
1272
1273    return ReturnCode;
1274}
1275
1276
1277IMG_UINT32 Legacy_JPGEncodeSOSHeader(LEGACY_JPEG_ENCODER_CONTEXT *pContext, IMG_CODED_BUFFER *pCBuffer)
1278{
1279    IMG_UINT32  ui32TableIndex ;
1280    IMG_UINT8 uc_comp_id, ui8Comp;
1281    STREAMTYPEW s_streamW;
1282    IMG_UINT8 *puc_stream_buff;
1283
1284    puc_stream_buff = (IMG_UINT8 *)(pCBuffer->pMemInfo) + pCBuffer->ui32BytesWritten;
1285
1286    s_streamW.Offset = 0;
1287    s_streamW.Buffer = puc_stream_buff;
1288    s_streamW.Limit = (pCBuffer->ui32Size - pCBuffer->ui32BytesWritten);
1289
1290    /* Start of scan */
1291    fPutBitsToBuffer(&s_streamW, 2, START_OF_SCAN);
1292    /* Scan header length */
1293    fPutBitsToBuffer(&s_streamW, 2, 6 + (pContext->JPEGEncoderParams.uc_num_comp_in_scan << 1));
1294    /* Number of image components in scan */
1295    fPutBitsToBuffer(&s_streamW, 1, pContext->JPEGEncoderParams.uc_num_comp_in_scan);
1296
1297    if (pContext->JPEGEncoderParams.uc_num_comp_in_scan > MAX_COMP_IN_SCAN)
1298        pContext->JPEGEncoderParams.uc_num_comp_in_scan = MAX_COMP_IN_SCAN;
1299    for (ui8Comp = 0; ui8Comp < pContext->JPEGEncoderParams.uc_num_comp_in_scan; ui8Comp++) {
1300        uc_comp_id = pContext->JPEGEncoderParams.puc_comp_id[ui8Comp];
1301        if (uc_comp_id >= MAX_COMP_IN_SCAN) {
1302            psb__error_message("Invalide component index %d\n", uc_comp_id);
1303            uc_comp_id = MAX_COMP_IN_SCAN - 1;
1304        }
1305
1306        ui32TableIndex  = pContext->sJPEGEncoderComp.CompIdtoIndex[uc_comp_id];
1307
1308        /* Scan component selector */
1309        fPutBitsToBuffer(&s_streamW, 1, uc_comp_id);
1310
1311        /*4 Bits Dc entropy coding table destination selector */
1312        /*4 Bits Ac entropy coding table destination selector */
1313        ui32TableIndex %= 255;
1314        fPutBitsToBuffer(&s_streamW, 1, (pContext->sJPEGEncoderComp.puc_huff_table_id[ui32TableIndex] << 4) | pContext->sJPEGEncoderComp.puc_huff_table_id[ui32TableIndex]);
1315    }
1316
1317    /* Start of spectral or predictor selection  */
1318    fPutBitsToBuffer(&s_streamW, 1, 0);
1319    /* End of spectral selection */
1320    fPutBitsToBuffer(&s_streamW, 1, 63);
1321    /*4 Bits Successive approximation bit position high (0)*/
1322    /*4 Bits Successive approximation bit position low or point transform (0)*/
1323    fPutBitsToBuffer(&s_streamW, 1, 0);
1324
1325    pCBuffer->ui32BytesWritten += s_streamW.Offset;
1326
1327    return 0;
1328}
1329
1330
1331/***********************************************************************************
1332 * Function Name      : JPGEncodeSOSHeader
1333 * Inputs             : PContext - Pointer to JPEG context
1334 * Inputs             : pui8BitStreamBuffer start of the coded output buffer
1335 * Inputs             : pui32BytesWritten pointer to offset into the coded output buffer at which to write
1336 * Outputs            : pui8BitStreamBuffer - Start of Scan header written to the coded buffer
1337 * Returns            : Bytes writtren
1338 * Description        : This function writes the Start of Scan Header
1339 ************************************************************************************/
1340
1341IMG_UINT32 JPGEncodeSOSHeader(/*in */           TOPAZSC_JPEG_ENCODER_CONTEXT *pContext,
1342        /*out */        IMG_UINT8*              pui8BitStreamBuffer ,
1343        /*out*/         IMG_UINT32*             pui32BytesWritten)
1344{
1345    IMG_UINT8 uc_comp_id, ui8Comp;
1346    STREAMTYPEW s_streamW;
1347
1348    s_streamW.Offset = 0;
1349    s_streamW.Buffer = pui8BitStreamBuffer + *pui32BytesWritten;
1350
1351    /* Start of scan */
1352    fPutBitsToBuffer(&s_streamW, 2, START_OF_SCAN);
1353    /* Scan header length */
1354    fPutBitsToBuffer(&s_streamW, 2, 6 + (pContext->pMTXSetup->ui32ComponentsInScan << 1));
1355    /* Number of image components in scan */
1356    fPutBitsToBuffer(&s_streamW, 1, pContext->pMTXSetup->ui32ComponentsInScan);
1357    for (ui8Comp = 0; ui8Comp < pContext->pMTXSetup->ui32ComponentsInScan; ui8Comp++) {
1358        uc_comp_id = ui8Comp + 1;
1359
1360        /* Scan component selector */
1361        fPutBitsToBuffer(&s_streamW, 1, uc_comp_id);
1362
1363        /*4 Bits Dc entropy coding table destination selector */
1364        /*4 Bits Ac entropy coding table destination selector */
1365        fPutBitsToBuffer(&s_streamW, 1, ((ui8Comp != 0 ? 1 : 0) << 4) | (ui8Comp != 0 ? 1 : 0)); // Huffman table refs = 0 Luma 1 Chroma
1366    }
1367
1368    /* Start of spectral or predictor selection  */
1369    fPutBitsToBuffer(&s_streamW, 1, 0);
1370    /* End of spectral selection */
1371    fPutBitsToBuffer(&s_streamW, 1, 63);
1372    /*4 Bits Successive approximation bit position high (0)*/
1373    /*4 Bits Successive approximation bit position low or point transform (0)*/
1374    fPutBitsToBuffer(&s_streamW, 1, 0);
1375
1376    *pui32BytesWritten += s_streamW.Offset;
1377
1378    return 0;
1379}
1380
1381
1382/*****************************************************************************/
1383/*                                                                           */
1384/* Function Name : EncodeMJPEGAPP1Marker                                     */
1385/*                                                                           */
1386/* Description   : Writes a Quicktime MJPEG (A) marker                                       */
1387/*                                                                           */
1388/* Inputs        :                                                           */
1389/*                                      pContext                        - Ptr to the JPEG encoder context        */
1390/*                                      puc_stream_buff         - Ptr to the bistream buffer from        */
1391/*                                                                                      where to start writing                   */
1392/*                                                                           */
1393/* Processing    :                                                                                                                       */
1394/*                                                                           */
1395/* Returns       : Number of bytes written into the stream                   */
1396/*                                                                           */
1397/*****************************************************************************/
1398IMG_UINT32 Insert_QT_MJPEGA_APP1Marker(IMG_CODED_BUFFER *pCBuffer, IMG_UINT8 *pui8BitStreamBuffer, IMG_UINT32 ui32OffsetBytes, IMG_BOOL bIsFirstField)
1399{
1400    STREAMTYPEW ps_streamW;
1401#ifdef JPEG_VERBOSE
1402    printf("Insert_QT_MJPEGA_APP1Marker");
1403#endif
1404
1405    ps_streamW.Offset = 0;
1406    ps_streamW.Buffer = &pui8BitStreamBuffer[ui32OffsetBytes];
1407
1408    /* Writing the start of image marker */
1409    fPutBitsToBuffer(&ps_streamW, 2, START_OF_IMAGE);
1410    /* Writing the Motion-JPEG APP1 marker */
1411    fPutBitsToBuffer(&ps_streamW, 2, MJPEG_APP1);
1412    /* Marker content length */
1413    fPutBitsToBuffer(&ps_streamW, 2, 0x002A);
1414    /* Reserved, set to zero */
1415    fPutBitsToBuffer(&ps_streamW, 4, 0x00000000);
1416    /* Motion-JPEG tag = "mjpg"*/
1417    fPutBitsToBuffer(&ps_streamW, 4, 0x6D6A7067);
1418    /* Field size*/
1419    fPutBitsToBuffer(&ps_streamW, 4, pCBuffer->ui32BytesWritten + 2 - ui32OffsetBytes); // +2 because the EOI marker not written yet
1420    /* Padded Field size*/
1421    fPutBitsToBuffer(&ps_streamW, 4, pCBuffer->ui32BytesWritten + 2 - ui32OffsetBytes);
1422    /* Offset to next field*/
1423    if (bIsFirstField)
1424        fPutBitsToBuffer(&ps_streamW, 4, pCBuffer->ui32BytesWritten + 2 - ui32OffsetBytes); // Points to start of next field
1425    else
1426        fPutBitsToBuffer(&ps_streamW, 4, 0); // Set to zero for second field
1427
1428    /* Quantization Table Offset*/
1429    // May be able to leave this at zero
1430    fPutBitsToBuffer(&ps_streamW, 4, H_QT_OFFSET);
1431    /* Huffman Table Offset*/
1432    // May be able to leave this at zero
1433    fPutBitsToBuffer(&ps_streamW, 4, H_HT_OFFSET);
1434    /* Start Of Frame Offset*/
1435    fPutBitsToBuffer(&ps_streamW, 4, H_SOF_OFFSET);
1436    /* Start Of Scan Offset*/
1437    fPutBitsToBuffer(&ps_streamW, 4, H_SOS_OFFSET);
1438    /* Start of data offset*/
1439    fPutBitsToBuffer(&ps_streamW, 4, H_SOI_OFFSET);
1440
1441    return 0;
1442}
1443
1444/* JPEG Start picture function. Sets up all context information, Quantization details, Header output and MTX ready for the main encode loop*/
1445IMG_ERRORCODE SetupJPEGTables(TOPAZSC_JPEG_ENCODER_CONTEXT * pContext, IMG_CODED_BUFFER *pCBuffer,  object_surface_p pTFrame)
1446{
1447    /*IMG_UINT32 rc = 0;
1448    const IMG_UINT8* StandardQuantLuma;
1449    const IMG_UINT8* StandardQuantChroma;
1450    IMG_UINT8* QuantLumaTableOnHost;
1451    IMG_UINT8* QuantChromaTableOnHost;
1452    JPEG_MTX_QUANT_TABLE * psQuantTables;*/
1453    IMG_UINT16 ui16Lp;
1454    IMG_UINT8 ui8Planes[MAX_COMP_IN_SCAN];
1455    /*IMG_ENC_CONTEXT * pEncContext = (IMG_ENC_CONTEXT*)hEncContext;*/
1456    /*TOPAZSC_JPEG_ENCODER_CONTEXT * pContext = pEncContext->psJpegHC;*/
1457    IMG_INT8 i;
1458    context_ENC_p ctx = (context_ENC_p)pContext->ctx;
1459
1460    // Lets add a pointer from our context to the source surface structure (remember we still need to use GETBUFFER commands if we want to get shared image memory, but info data structures are on host)
1461    pContext->pSourceSurface = pTFrame;
1462
1463    //Try setting MCU details from here
1464    /*JPGEncodeBegin(pContext, pTFrame);*/
1465    InitializeJpegEncode(pContext, pTFrame);
1466
1467    // Special case for YUYV format
1468    if (ISCHROMAINTERLEAVED(pContext->eFormat) > C_INTERLEAVE)
1469        pContext->sScan_Encode_Info.ui32NumberMCUsX = (pContext->pMTXSetup->MCUComponent[0].ui32XLimit + ((pContext->pMTXSetup->MCUComponent[0].ui32WidthBlocks * 2) - 1)) / (pContext->pMTXSetup->MCUComponent[0].ui32WidthBlocks * 2);
1470    else
1471        pContext->sScan_Encode_Info.ui32NumberMCUsX = (pContext->pMTXSetup->MCUComponent[0].ui32XLimit + (pContext->pMTXSetup->MCUComponent[0].ui32WidthBlocks - 1)) / pContext->pMTXSetup->MCUComponent[0].ui32WidthBlocks;
1472
1473    pContext->sScan_Encode_Info.ui32NumberMCUsY = (pContext->pMTXSetup->MCUComponent[0].ui32YLimit + (pContext->pMTXSetup->MCUComponent[0].ui32HeightBlocks - 1)) / pContext->pMTXSetup->MCUComponent[0].ui32HeightBlocks;
1474    pContext->sScan_Encode_Info.ui32NumberMCUsToEncode = pContext->sScan_Encode_Info.ui32NumberMCUsX * pContext->sScan_Encode_Info.ui32NumberMCUsY;
1475
1476    pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan =
1477        JPEG_MCU_PER_SCAN(ctx->Width, ctx->Height, ctx->NumCores, pContext->eFormat);
1478
1479    psb__information_message("MCUs To Encode %dx%d\n",
1480                             pContext->sScan_Encode_Info.ui32NumberMCUsX,
1481                             pContext->sScan_Encode_Info.ui32NumberMCUsY);
1482    psb__information_message("Total MCU %d, per scan %d\n", pContext->sScan_Encode_Info.ui32NumberMCUsToEncode, pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan);
1483
1484    //Allocate our coded data buffers here now we know the number of MCUs we're encoding
1485    /*Use slice parameter buffer*/
1486    if (AllocateCodedDataBuffers(pContext) != IMG_ERR_OK) return IMG_ERR_MEMORY;
1487    // Send Setup message to MTX to initialise it
1488    /*EncodeInitMTX(pEncContext);        Set predictors to zero */
1489
1490    for (i = ctx->NumCores - 1; i >= 0; i--) {
1491        pnw_cmdbuf_insert_command_package(
1492            ((context_ENC_p)pContext->ctx)->obj_context,
1493            i,
1494            MTX_CMDID_RESET_ENCODE,
1495            NULL,
1496            0);
1497    }
1498    //CODE HERE SIMPLIFIED AS WE KNOW THERE WILL ONLY EVER BE 3 IMAGE COMPONENTS
1499    /* Set up Source panes for HW */
1500    // Reverse colour plane pointers fed to MTX when required by format
1501
1502    switch (pContext->eFormat) {
1503    case IMG_CODEC_YV16:
1504        pContext->pMTXSetup->ComponentPlane[0].ui32Stride = pTFrame->psb_surface->stride;
1505        pContext->pMTXSetup->ComponentPlane[1].ui32Stride = pTFrame->psb_surface->stride / 2;
1506        pContext->pMTXSetup->ComponentPlane[2].ui32Stride = pTFrame->psb_surface->stride / 2;
1507
1508        pContext->pMTXSetup->ComponentPlane[0].ui32Height = pTFrame->height;
1509        pContext->pMTXSetup->ComponentPlane[1].ui32Height = pTFrame->height;
1510        pContext->pMTXSetup->ComponentPlane[2].ui32Height = pTFrame->height;
1511
1512        /*YV16's plane order is Y, V, U*/
1513        ui8Planes[0] = 0;
1514        ui8Planes[2] = 1;
1515        ui8Planes[1] = 2;
1516        break;
1517    case IMG_CODEC_IYUV:
1518    case IMG_CODEC_IMC2:
1519        /*case IMG_CODEC_422_IMC2:
1520            SetupYUVPlaneDetails(&(pContext->pMTXSetup->ComponentPlane[0]),
1521                    &(pTFrame->aui32ComponentInfo[0]));
1522
1523            SetupYUVPlaneDetails(&(pContext->pMTXSetup->ComponentPlane[2]),
1524                    &(pTFrame->aui32ComponentInfo[1]));
1525
1526            SetupYUVPlaneDetails(&(pContext->pMTXSetup->ComponentPlane[1]),
1527                    &(pTFrame->aui32ComponentInfo[2]));*/
1528        pContext->pMTXSetup->ComponentPlane[0].ui32Stride = pTFrame->psb_surface->stride;
1529        pContext->pMTXSetup->ComponentPlane[1].ui32Stride = pTFrame->psb_surface->stride / 2;
1530        pContext->pMTXSetup->ComponentPlane[2].ui32Stride = pTFrame->psb_surface->stride / 2;
1531
1532        pContext->pMTXSetup->ComponentPlane[0].ui32Height = pTFrame->height;
1533        pContext->pMTXSetup->ComponentPlane[1].ui32Height = pTFrame->height / 2;
1534        pContext->pMTXSetup->ComponentPlane[2].ui32Height = pTFrame->height / 2;
1535
1536        //ui8Planes[0]=0;ui8Planes[1]=2;ui8Planes[2]=1;
1537        /*IYUV don't need to swap UV color space. Not sure about IMC12*/
1538        ui8Planes[0] = 0;
1539        ui8Planes[1] = 1;
1540        ui8Planes[2] = 2;
1541        break;
1542    default:
1543        /*SetupYUVPlaneDetails(&(pContext->pMTXSetup->ComponentPlane[0]),
1544            &(pTFrame->aui32ComponentInfo[0]));
1545
1546        SetupYUVPlaneDetails(&(pContext->pMTXSetup->ComponentPlane[1]),
1547            &(pTFrame->aui32ComponentInfo[1]));
1548
1549        SetupYUVPlaneDetails(&(pContext->pMTXSetup->ComponentPlane[2]),
1550            &(pTFrame->aui32ComponentInfo[2]));*/
1551        /* It's for NV12*/
1552        pContext->pMTXSetup->ComponentPlane[0].ui32Stride = pTFrame->psb_surface->stride;
1553        pContext->pMTXSetup->ComponentPlane[1].ui32Stride = pTFrame->psb_surface->stride;
1554        pContext->pMTXSetup->ComponentPlane[2].ui32Stride = pTFrame->psb_surface->stride;
1555
1556        pContext->pMTXSetup->ComponentPlane[0].ui32Height = pTFrame->height;
1557        pContext->pMTXSetup->ComponentPlane[1].ui32Height = pTFrame->height / 2;
1558        pContext->pMTXSetup->ComponentPlane[2].ui32Height = pTFrame->height / 2;
1559
1560        ui8Planes[0] = 0;
1561        ui8Planes[1] = 1;
1562        ui8Planes[2] = 2;
1563        break;
1564    };
1565
1566
1567    SetupIssueSetup(pContext, pContext->pMTXSetup->ui32ComponentsInScan, ui8Planes, pTFrame, 0 , 1);
1568
1569    if (pContext->pMTXSetup->ui32ComponentsInScan > MAX_COMP_IN_SCAN) {
1570        return IMG_ERR_UNDEFINED;
1571    }
1572
1573    if ((pCBuffer->ui32Size - pCBuffer->ui32BytesWritten) < 9 + 6 + (4 *(IMG_UINT32)pContext->pMTXSetup->ui32ComponentsInScan)) {
1574        return  IMG_ERR_MEMORY;
1575    }
1576
1577    // Reset Scan Encode structures - just in case
1578    for (ui16Lp = 0; ui16Lp < pContext->sScan_Encode_Info.ui8NumberOfCodedBuffers; ui16Lp++) {
1579        BUFFER_HEADER *pbh;
1580
1581        pContext->sScan_Encode_Info.aBufferTable[ui16Lp].i8MTXNumber = 0; // Indicates buffer is idle
1582        pContext->sScan_Encode_Info.aBufferTable[ui16Lp].ui16ScanNumber = 0; // Indicates buffer is idle
1583
1584        pContext->sScan_Encode_Info.aBufferTable[ui16Lp].ui32DataBufferUsedBytes = 0;
1585
1586        //pbh = MMGetHostLinAddress(pContext->sScan_Encode_Info.aBufferTable[ui16Lp].pMemInfo );
1587        pbh = (BUFFER_HEADER *)(pContext->sScan_Encode_Info.aBufferTable[ui16Lp].pMemInfo);
1588        pbh->ui32BytesEncoded = 0;
1589        pbh->ui32BytesUsed = sizeof(BUFFER_HEADER);
1590    }
1591
1592    //Prefill out MTXIdleTable with MTX references (0 is the Master, and will be the last sent)
1593    for (pContext->sScan_Encode_Info.ui8MTXIdleCnt = 0; pContext->sScan_Encode_Info.ui8MTXIdleCnt < ctx->NumCores; pContext->sScan_Encode_Info.ui8MTXIdleCnt++) {
1594        pContext->sScan_Encode_Info.aui8MTXIdleTable[pContext->sScan_Encode_Info.ui8MTXIdleCnt] = pContext->sScan_Encode_Info.ui8MTXIdleCnt + 1;
1595    }
1596
1597
1598    //Need to set up CB Output slicenumber to equal number of slices required to encode image
1599    // Set current CB scan to maximum scan number (will count down as scans are output)
1600    pContext->sScan_Encode_Info.ui16CScan = (pContext->sScan_Encode_Info.ui32NumberMCUsToEncode + (pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan - 1)) / pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan;
1601    pContext->sScan_Encode_Info.ui16ScansInImage = pContext->sScan_Encode_Info.ui16CScan;
1602    // Set next scan to send to MTX to maximum scan number
1603    pContext->sScan_Encode_Info.ui16SScan = pContext->sScan_Encode_Info.ui16CScan;
1604    pContext->ui32InitialCBOffset = 0;
1605
1606    return IMG_ERR_OK;
1607}
1608
1609IMG_ERRORCODE Legacy_PrepareHeader(LEGACY_JPEG_ENCODER_CONTEXT * pContext, IMG_CODED_BUFFER *pCBuffer)
1610{
1611    IMG_ERRORCODE rc;
1612    IMG_UINT8 *ui8OutputBuffer;
1613
1614    ui8OutputBuffer = pCBuffer->pMemInfo;
1615    //Lock our JPEG Coded buffer
1616    /* if (IMG_JPEG_GetBuffer(pCBuffer, (IMG_VOID **) &ui8OutputBuffer)!=IMG_ERR_OK)
1617     return IMG_ERR_SURFACE_LOCKED;*/
1618
1619    pCBuffer->ui32BytesWritten = 0;
1620    *((IMG_UINT32*) ui8OutputBuffer) = 0;
1621
1622    // JPGEncodeMarker - Currently misses out the APP0 header
1623    rc = Legacy_JPGEncodeMarker(pContext, (IMG_UINT8 *) ui8OutputBuffer,  &pCBuffer->ui32BytesWritten);
1624    if (rc) return rc;
1625
1626    rc = Legacy_JPGEncodeHeader(pContext , (IMG_UINT8 *) ui8OutputBuffer ,  &pCBuffer->ui32BytesWritten);
1627    if (rc) return rc;
1628
1629    //  JPGEncodeDRIMarker(pContext,pCBuffer);
1630    Legacy_JPGEncodeSOSHeader(pContext, pCBuffer);
1631
1632    //IMG_JPEG_ReleaseBuffer( pCBuffer);
1633
1634
1635    return IMG_ERR_OK;
1636}
1637/* Send header will work for each type of header*/
1638
1639/***********************************************************************************
1640 * Function Name      : PrepareHeader
1641 * Inputs             : Pointer to JPEG Context, Point to coded buffer
1642 * Outputs            :
1643 * Returns            : IMG_ERRORCODE
1644 * Description        : Writes required JPEG Header elements to the coded buffer
1645 ************************************************************************************/
1646IMG_ERRORCODE PrepareHeader(TOPAZSC_JPEG_ENCODER_CONTEXT * pContext, IMG_CODED_BUFFER *pCBuffer, IMG_UINT32 ui32StartOffset, IMG_BOOL bIncludeHuffmanTables)
1647{
1648    IMG_ERRORCODE rc;
1649    IMG_UINT8 *ui8OutputBuffer;
1650
1651    //Lock our JPEG Coded buffer
1652    /*if (IMG_C_GetBuffer((IMG_HENC_CONTEXT) pContext, pCBuffer, (IMG_VOID **) &ui8OutputBuffer)!=IMG_ERR_OK)
1653    return IMG_ERR_SURFACE_LOCKED;*/
1654
1655    ui8OutputBuffer = (IMG_UINT8 *)pCBuffer->pMemInfo;
1656    pCBuffer->ui32BytesWritten = ui32StartOffset;
1657    *((IMG_UINT32*) ui8OutputBuffer + pCBuffer->ui32BytesWritten) = 0;
1658
1659
1660    // JPGEncodeMarker - Currently misses out the APP0 header
1661    rc = JPGEncodeMarker(pContext, (IMG_UINT8 *) ui8OutputBuffer,  &pCBuffer->ui32BytesWritten, bIncludeHuffmanTables);
1662    if (rc) return rc;
1663
1664    psb__information_message("Current bytes of coded buf used: %d\n", pCBuffer->ui32BytesWritten);
1665    rc = JPGEncodeHeader(pContext , (IMG_UINT8 *) ui8OutputBuffer ,  &pCBuffer->ui32BytesWritten);
1666    if (rc) return rc;
1667
1668    psb__information_message("Current bytes of coded buf used: %d\n", pCBuffer->ui32BytesWritten);
1669    rc = JPGEncodeSOSHeader(pContext, (IMG_UINT8 *) ui8OutputBuffer, &pCBuffer->ui32BytesWritten);
1670    if (rc) return rc;
1671
1672    psb__information_message("Current bytes of coded buf used: %d\n", pCBuffer->ui32BytesWritten);
1673    /*IMG_C_ReleaseBuffer((IMG_HENC_CONTEXT) pContext, pCBuffer);*/
1674    return IMG_ERR_OK;
1675}
1676
1677
1678
1679
1680/***********************************************************************************
1681 * Function Name      : IMG_JPEG_ISSUEBUFFERTOHW
1682 * Inputs             :
1683 * Outputs            : pui32MCUsToProccess
1684 * Returns            :
1685 * Description        : Issues a buffer to MTX to recieve coded data.
1686 *
1687 ************************************************************************************/
1688
1689IMG_ERRORCODE IssueBufferToHW(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext, TOPAZSC_JPEG_BUFFER_INFO* pWriteBuf, IMG_UINT16 ui16BCnt, IMG_UINT32 ui32NoMCUsToEncode, IMG_INT8 i8MTXNumber)
1690{
1691    MTX_ISSUE_BUFFERS *psBufferCmd;
1692    context_ENC_p ctx = (context_ENC_p)pContext->ctx;
1693    /*IMG_ENC_CONTEXT * pEncContext = (IMG_ENC_CONTEXT*)hContext;
1694    TOPAZSC_JPEG_ENCODER_CONTEXT *pContext = pEncContext->psJpegHC;*/
1695
1696#ifdef JPEG_VERBOSE
1697    printf("\n**************************************************************************\n");
1698    printf("** HOST SENDING Scan:%i (%i MCUs) to MTX %i, using Buffer %i\n", pWriteBuf->ui16ScanNumber, ui32NoMCUsToEncode, i8MTXNumber - 1, ui16BCnt);
1699#endif
1700    psb__information_message("HOST SENDING Scan:%d (%d MCUs, offset %d MCUs)"
1701                             " to MTX %d, using Buffer %d\n",
1702                             pWriteBuf->ui16ScanNumber, ui32NoMCUsToEncode,
1703                             pContext->sScan_Encode_Info.ui32CurMCUsOffset,
1704                             i8MTXNumber, ui16BCnt);
1705
1706    // Issue to MTX ////////////////////////////
1707    ASSERT(pWriteBuf->pMemInfo);
1708
1709    // Lets send our input parameters using the device memory allocated for the coded output
1710    psBufferCmd = (MTX_ISSUE_BUFFERS *)(pWriteBuf->pMemInfo);
1711
1712    // We've disabled size bound checking in firmware, so can use the full 31 bits for NoMCUsToEncode instead
1713    //psBufferCmd->ui32MCUCntAndResetFlag       = ( DATA_BUFFER_SIZE(pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan) << 16) | (ui32NoMCUsToEncode << 1) | 0x1;
1714
1715    psBufferCmd->ui32MCUCntAndResetFlag = (ui32NoMCUsToEncode << 1) | 0x1;
1716    psBufferCmd->ui32CurrentMTXScanMCUPosition = pContext->sScan_Encode_Info.ui32CurMCUsOffset;
1717    psb__information_message("TOPAZ_PDUMP: ui32MCUCntAndResetFlag 0x%x\n", psBufferCmd->ui32MCUCntAndResetFlag);
1718    psb__information_message("TOPAZ_PDUMP: ui32CurrentMTXScanMCUPosition 0x%x\n", psBufferCmd->ui32CurrentMTXScanMCUPosition);
1719    /* We do not need to do this but in order for params to match on HW we need to know whats in the buffer*/
1720    /*MMUpdateDeviceMemory(pWriteBuf->pMemInfo );*/
1721
1722    /*TOPAZ_InsertCommand(
1723        pEncContext,
1724        (IMG_INT32) (i8MTXNumber-1),
1725        MTX_CMDID_ISSUEBUFF,
1726        IMG_FALSE,
1727        &pWriteBuf->ui32WriteBackVal,
1728        pWriteBuf->pMemInfo );*/
1729    pnw_cmdbuf_insert_command_package(ctx->obj_context,
1730                                      (IMG_INT32)(i8MTXNumber) ,
1731                                      MTX_CMDID_ISSUEBUFF,
1732                                      ctx->coded_buf->psb_buffer,
1733                                      ui16BCnt * pContext->ui32SizePerCodedBuffer + PNW_JPEG_HEADER_MAX_SIZE);
1734
1735    return IMG_ERR_OK;
1736}
1737
1738/***********************************************************************************
1739 * Function Name      : SubmitScanToMTX
1740 * Inputs             :
1741 *                                              pContext - Pointer to JPEG context
1742 *                                              ui16BCnt - Index of the buffer to associate with the MTX
1743 *                                              i8MTXNumber - The ID number of the MTX that will have a scan sent to it
1744 * Outputs            : Status update to current buffer, MTX is activated
1745 * Returns            : Errorcode
1746 * Description        : Associates the empty buffer with the inactive MTX and then
1747 *                                              starts a scan, with output to be sent to the buffer.
1748 ************************************************************************************/
1749
1750IMG_ERRORCODE SubmitScanToMTX(TOPAZSC_JPEG_ENCODER_CONTEXT *pContext,
1751                              IMG_UINT16 ui16BCnt,
1752                              IMG_INT8 i8MTXNumber,
1753                              IMG_UINT32 ui32NoMCUsToEncode)
1754{
1755    /*IMG_ENC_CONTEXT * pEncContext = (IMG_ENC_CONTEXT*)hContext;
1756    TOPAZSC_JPEG_ENCODER_CONTEXT *pContext = pEncContext->psJpegHC;*/
1757
1758
1759#if 0
1760    // Submit a scan and buffer to the appropriate MTX unit
1761    IMG_UINT32 ui32NoMCUsToEncode;
1762
1763    if (pContext->sScan_Encode_Info.ui16SScan == 0) {
1764        // Final scan, may need fewer MCUs than buffer size, calculate the remainder
1765        ui32NoMCUsToEncode = pContext->sScan_Encode_Info.ui32NumberMCUsToEncode % pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan;
1766        if (ui32NoMCUsToEncode == 0)    ui32NoMCUsToEncode = pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan;
1767    } else
1768        ui32NoMCUsToEncode = pContext->sScan_Encode_Info.ui32NumberMCUsToEncodePerScan;
1769#endif
1770    //Set the buffer returned size to -1
1771    pContext->sScan_Encode_Info.aBufferTable[ui16BCnt].ui32DataBufferUsedBytes = ((BUFFER_HEADER*)(pContext->sScan_Encode_Info.aBufferTable[ui16BCnt].pMemInfo))->ui32BytesUsed = -1; // Won't be necessary with SC Peek commands enabled
1772    IssueBufferToHW(pContext, &(pContext->sScan_Encode_Info.aBufferTable[ui16BCnt]), ui16BCnt, ui32NoMCUsToEncode, i8MTXNumber);
1773
1774    psb__information_message("Submitting scan %i to MTX %i and Buffer %i\n", pContext->sScan_Encode_Info.aBufferTable[ui16BCnt].ui16ScanNumber, i8MTXNumber, ui16BCnt);
1775    return IMG_ERR_OK;
1776}
1777
1778
1779void pnw_jpeg_set_default_qmatix(void *pMemInfoTableBlock)
1780{
1781    JPEG_MTX_QUANT_TABLE *pQTable =  pMemInfoTableBlock;
1782    memcpy(pQTable->aui8LumaQuantParams, gQuantLuma, QUANT_TABLE_SIZE_BYTES);
1783    memcpy(pQTable->aui8ChromaQuantParams, gQuantChroma, QUANT_TABLE_SIZE_BYTES);
1784    return;
1785}
1786