void gxpport_destroy_immutable(gxpport_image_native_handle imagePtr) {

    _Platform_ImmutableImage* immutableImage = 
        (_Platform_ImmutableImage*)imagePtr;

    if (NULL != immutableImage) {
        if (NULL != immutableImage->qimage) {
            int rscSize = ImgRscSize(immutableImage->qimage);

            /* Update the resource count */
            if (midpDecResourceCount(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) {
                REPORT_ERROR(LC_LOWUI,"Error in updating resource limit for"
                             " Immutable image");
            }

            delete immutableImage->qimage;
        }

        if (NULL != immutableImage->qpixmap) {
            delete immutableImage->qpixmap;
        }

	midpFree(immutableImage);
    }
}
extern "C" void
gxpport_destroy_mutable(gxpport_mutableimage_native_handle imagePtr) {

    /* we know : 
       non-null QPixmap object has been allocated */  
    QPixmap* qpixmap = (QPixmap *)(imagePtr);

    /* make sure there is a valid qpixmap */
    if (qpixmap == NULL) {
	return;
    }

    MScreen * mscreen = qteapp_get_mscreen();
    if (mscreen->isCurrentPaintDevice(qpixmap)) { 
        // remove pixmap as the current painting device 
        short clip[] = {0, 0, 0, 0}; 
        mscreen->setupGC(-1, -1, clip, NULL, 0); 
    } 

    /* Update the resource count */
    if (midpDecResourceCount(RSC_TYPE_IMAGE_MUT, ImgRscSize(qpixmap)) == 0) {
        REPORT_INFO(LC_LOWUI,"Error in updating resource limit for" 
                             " Mutable image");
    }

    /* RELEASE QT RESOURCES HELD */
    delete qpixmap;
}
extern "C" void gxpport_createimmutable_from_mutable
(gxpport_mutableimage_native_handle srcMutableImagePtr,
 gxpport_image_native_handle *newImmutableImagePtr,
 gxutl_native_image_error_codes* creationErrorPtr) {

    /* Convert from source QPixmap to destination QImage */
    QPixmap* srcPixmap = gxpportqt_get_mutableimage_pixmap(srcMutableImagePtr);

    int rscSize = ImgRscSize(srcPixmap); /* new img is the same size */

    /* Check resource limit before copying */
    if (midpCheckResourceLimit(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) {
        /* Exceeds resource limit */
        *creationErrorPtr  = GXUTL_NATIVE_IMAGE_RESOURCE_LIMIT;
        return;
    }

    _Platform_ImmutableImage* immutableImage =
        (_Platform_ImmutableImage*)midpMalloc(sizeof(_Platform_ImmutableImage));
    if (immutableImage == NULL) {
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
        return;
    }

    immutableImage->qimage = new QImage(srcPixmap->convertToImage());
    if (NULL == immutableImage->qimage) {
	midpFree(immutableImage);
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
        return;
    }

    if (immutableImage->qimage->isNull()) {
        delete immutableImage->qimage;
	midpFree(immutableImage);
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
        return;    
    }

    /* Copying succeeds */
    if (midpIncResourceCount(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) {
        REPORT_ERROR(LC_LOWUI, "Error in updating resource limit"
                     " for Immutable image");
    }

    immutableImage->marker = 1;
    immutableImage->qpixmap = NULL;

    *newImmutableImagePtr = immutableImage;
    *creationErrorPtr = GXUTL_NATIVE_IMAGE_NO_ERROR;
}
extern "C" void
gxpport_create_mutable(gxpport_mutableimage_native_handle *newImagePtr,
		       int width, int height,
		       gxutl_native_image_error_codes* creationErrorPtr) {
  /* set optimization for all QPixmaps
     move this to startup/initialization code. */
  QPixmap::setDefaultOptimization(QPixmap::BestOptim);

  /*
   * Populate Java data pointer before calling checkResourceLimit
   * because it might trigger GC and makes the Java pointer invalid.
   */  
  QPixmap* qpixmap = new QPixmap(); /* Start with a NULL image object */
  if (NULL == qpixmap) {
     *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
     return;
  }

  /* Check resource limit before really creating image memory */
  if (midpCheckResourceLimit(RSC_TYPE_IMAGE_MUT,
                             ImgRegionRscSize(width, height)) == 0) {
     *creationErrorPtr = GXUTL_NATIVE_IMAGE_RESOURCE_LIMIT;
     delete qpixmap;
     return;
  }

  /* ALLOCATE MEMORY FOR QT IMAGE DATA */
  qpixmap->resize(width, height);

  /* INITIALIZE CONTENTS TO WHITE */
  qpixmap->fill();

  /* Update the resource count */
  if (midpIncResourceCount(RSC_TYPE_IMAGE_MUT, ImgRscSize(qpixmap)) == 0) {
      REPORT_INFO(LC_LOWUI,"Error in updating resource"
                  " limit for Mutable image");
  }

  /* return the qpixmap pointer */
  *newImagePtr = qpixmap;

  *creationErrorPtr = GXUTL_NATIVE_IMAGE_NO_ERROR;
}
extern "C" void gxpport_decodeimmutable_from_argb
(jint* srcBuffer,
 int width, int height,
 jboolean processAlpha,
 gxpport_image_native_handle* newImmutableImagePtr,
 gxutl_native_image_error_codes* creationErrorPtr) {

    // use bytes as is, QT images have the same binary data layout
    QImage qimage = QImage((unsigned char*)srcBuffer, 
                           width, height, 
                           IMAGE_DEPTH,
                           NULL, 0, 
                           QImage::IgnoreEndian);

    if (qimage.isNull()) {
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_DECODING_ERROR;
        return;
    }

    /* Check Resource limit */
    int rscSize = ImgRscSize(&qimage);

    if (midpCheckResourceLimit(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) {
        /* Exceed Resource limit */
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_RESOURCE_LIMIT;
        return;
    }

    qimage.setAlphaBuffer(processAlpha == KNI_TRUE?TRUE:FALSE);

    _Platform_ImmutableImage* immutableImage =
        (_Platform_ImmutableImage*)midpMalloc(sizeof(_Platform_ImmutableImage));
    if (immutableImage == NULL) {
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
        return;
    }

    // make a deep copy of the image
    immutableImage->qimage = new QImage(qimage.copy());
    if (NULL == immutableImage->qimage) {
	midpFree(immutableImage);
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
        return;
    }

    if (immutableImage->qimage->isNull()) {
        delete immutableImage->qimage;
	midpFree(immutableImage);
        *creationErrorPtr = GXUTL_NATIVE_IMAGE_OUT_OF_MEMORY_ERROR;
        return;
    }

    /* Image creation succeeds */
    if (midpIncResourceCount(RSC_TYPE_IMAGE_IMMUT, rscSize) == 0) {
        REPORT_ERROR(LC_LOWUI, "Error in updating "
                     "resource limit for Immutable image");
    }

    immutableImage->marker = 6;
    immutableImage->qpixmap = NULL;

    *newImmutableImagePtr = immutableImage;
    *creationErrorPtr = GXUTL_NATIVE_IMAGE_NO_ERROR;
}