X-Git-Url: http://git.megacz.com/?a=blobdiff_plain;f=src%2Forg%2Fxwt%2Fplat%2FGCJ.cc;h=3050a2b617e8f2e668207a3f872bd79a7f256f70;hb=38786988d12f2c48a314ee37c326965ff0bcadb6;hp=b055673ff86ef97b414d6b4ef32c1be5e63e36a3;hpb=ba8770b50fae938f413fee1f178b2ed6f4ca80f1;p=org.ibex.core.git diff --git a/src/org/xwt/plat/GCJ.cc b/src/org/xwt/plat/GCJ.cc index b055673..3050a2b 100644 --- a/src/org/xwt/plat/GCJ.cc +++ b/src/org/xwt/plat/GCJ.cc @@ -1 +1,132 @@ - +// Copyright 2002 Adam Megacz, see the COPYING file for licensing [LGPL] + +// Inclusions ///////////////////////////////////////////////////////// + +#include +#include +extern "C" { + +// hack for broken Solaris headers +#define _WCHAR_T + +#include +#include +#include +#include "jpeglib.h" +} +#include +#include +#include +#include +#include +#include + + + +// builtin.xwar ///////////////////////////////////////////////////////// + +extern unsigned char builtin_bytes[]; +extern int builtin_length; + +java::io::InputStream* org::xwt::plat::GCJ::_getBuiltinInputStream() { + jbyteArray ret = JvNewByteArray(builtin_length); + memcpy(elements(ret), builtin_bytes, builtin_length); + return new java::io::ByteArrayInputStream(ret); +} + + + +// JPEG //////////////////////////////////////////////////////////////// + +#define INPUT_BUF_SIZE (1024 * 16) + +typedef struct { + struct jpeg_source_mgr pub; + org::xwt::plat::GCJ$JPEG* myself; +} source_manager; + +void jpeg_error_handler (j_common_ptr cinfo) { + jstring message = JvNewStringLatin1(cinfo->err->jpeg_message_table[cinfo->err->msg_code]); + throw new java::lang::RuntimeException(message); +} + +void term_source (j_decompress_ptr cinfo) { } +void init_source (j_decompress_ptr cinfo) { } + +boolean fill_input_buffer (j_decompress_ptr cinfo) { + source_manager* src = (source_manager*)cinfo->src; + jint nbytes = src->myself->is->read(src->myself->buffer, 0, INPUT_BUF_SIZE); + if (nbytes <= 0) { + // the JPEG library specifically suggests padding the end with EOF markers + elements(src->myself->buffer)[0] = (jbyte)0xFF; + elements(src->myself->buffer)[1] = (jbyte)JPEG_EOI; + nbytes = 2; + } + src->pub.next_input_byte = (JOCTET*)elements(src->myself->buffer); + src->pub.bytes_in_buffer = nbytes; + return 1; +} + +void skip_input_data (j_decompress_ptr cinfo, long num_bytes) { + source_manager* src = (source_manager*)cinfo->src; + if (num_bytes > 0) { + while (num_bytes > (long) src->pub.bytes_in_buffer) { + num_bytes -= (long) src->pub.bytes_in_buffer; + (void) fill_input_buffer(cinfo); + } + src->pub.next_input_byte += (size_t) num_bytes; + src->pub.bytes_in_buffer -= (size_t) num_bytes; + } +} + +void org::xwt::plat::GCJ$JPEG::nativeDecompress() { + struct jpeg_decompress_struct cinfo; + + // set up our error handler + struct jpeg_error_mgr error_handler; + cinfo.err = jpeg_std_error(&error_handler); + error_handler.error_exit = &jpeg_error_handler; + + jpeg_create_decompress(&cinfo); + try { + source_manager src; + buffer = JvNewByteArray(INPUT_BUF_SIZE); + src.pub.init_source = init_source; + src.pub.fill_input_buffer = fill_input_buffer; + src.pub.skip_input_data = skip_input_data; + src.pub.resync_to_restart = jpeg_resync_to_restart; + src.pub.term_source = term_source; + src.myself = this; + src.pub.next_input_byte = (JOCTET*)elements(buffer); + src.pub.bytes_in_buffer = 0; + cinfo.src = (jpeg_source_mgr*)&src; + + jpeg_read_header(&cinfo, 1); + jpeg_start_decompress(&cinfo); + width = cinfo.output_width; + height = cinfo.output_height; + data = JvNewIntArray(width * height); + + while (cinfo.output_scanline < cinfo.output_height) { + JSAMPLE* dest = (JSAMPLE*)(elements(data) + cinfo.output_scanline * width); + jpeg_read_scanlines(&cinfo, &dest, 1); + } + + jpeg_finish_decompress(&cinfo); + + // fill in the alpha components + for(int i=0; ilength; i++) + elements(data)[i] |= (jint)0xff000000; + + } catch (java::lang::Throwable* t) { + jpeg_destroy_decompress(&cinfo); + throw t; + } + jpeg_destroy_decompress(&cinfo); +} + +// C++ new/delete operators (JvMalloc never fails) +void* operator new(size_t size) { return JvMalloc(size); } +void* operator new[](size_t size) { return JvMalloc(size);} +void operator delete(void *p) { JvFree(p); } +void operator delete[](void *p) { JvFree(p); }