diff --git a/pipi/codec.c b/pipi/codec.c
index c1683d1..797107d 100644
--- a/pipi/codec.c
+++ b/pipi/codec.c
@@ -46,12 +46,13 @@ void pipi_free(pipi_image_t *img)
         if(i != img->codec_format && img->p[i].pixels)
             free(img->p[i].pixels);
 
+    if(img->codec_priv)
 #if USE_SDL
-    pipi_free_sdl(img);
+        pipi_free_sdl(img);
 #elif USE_IMLIB2
-    pipi_free_imlib2(img);
+        pipi_free_imlib2(img);
 #elif USE_OPENCV
-    pipi_free_opencv(img);
+        pipi_free_opencv(img);
 #endif
 
     free(img);
diff --git a/pipi/codec/opencv.c b/pipi/codec/opencv.c
index c1a8284..7eac247 100644
--- a/pipi/codec/opencv.c
+++ b/pipi/codec/opencv.c
@@ -34,51 +34,21 @@
 pipi_image_t *pipi_load_opencv(const char *name)
 {
     pipi_image_t *img;
-    IplImage *priv = cvLoadImage(name, -1);
+    IplImage *priv = cvLoadImage(name, 1);
 
     if(!priv)
         return NULL;
 
-    img = (pipi_image_t *)malloc(sizeof(pipi_image_t));
-    memset(img, 0, sizeof(pipi_image_t));
+    img = pipi_new(priv->width, priv->height);
 
-    img->w = priv->width;
-    img->h = priv->height;
-
-    img->p[PIPI_PIXELS_RGBA32].pixels = priv->imageData;
-    img->p[PIPI_PIXELS_RGBA32].w = priv->width;
-    img->p[PIPI_PIXELS_RGBA32].h = priv->height;
-    img->p[PIPI_PIXELS_RGBA32].pitch = priv->widthStep;
-    img->last_modified = PIPI_PIXELS_RGBA32;
+    img->p[PIPI_PIXELS_BGR24].pixels = priv->imageData;
+    img->p[PIPI_PIXELS_BGR24].w = priv->width;
+    img->p[PIPI_PIXELS_BGR24].h = priv->height;
+    img->p[PIPI_PIXELS_BGR24].pitch = priv->widthStep;
+    img->last_modified = PIPI_PIXELS_BGR24;
 
     img->codec_priv = (void *)priv;
-    img->codec_format = PIPI_PIXELS_RGBA32;
-
-    return img;
-}
-
-pipi_image_t *pipi_new_opencv(int width, int height)
-{
-    pipi_image_t *img;
-    IplImage *priv = cvCreateImage(cvSize(width, height), IPL_DEPTH_8U, 4);
-
-    if(!priv)
-        return NULL;
-
-    img = (pipi_image_t *)malloc(sizeof(pipi_image_t));
-    memset(img, 0, sizeof(pipi_image_t));
-
-    img->w = priv->width;
-    img->h = priv->height;
-
-    img->p[PIPI_PIXELS_RGBA32].pixels = priv->imageData;
-    img->p[PIPI_PIXELS_RGBA32].w = priv->width;
-    img->p[PIPI_PIXELS_RGBA32].h = priv->height;
-    img->p[PIPI_PIXELS_RGBA32].pitch = priv->widthStep;
-    img->last_modified = PIPI_PIXELS_RGBA32;
-
-    img->codec_priv = (void *)priv;
-    img->codec_format = PIPI_PIXELS_RGBA32;
+    img->codec_format = PIPI_PIXELS_BGR24;
 
     return img;
 }
@@ -88,12 +58,32 @@ void pipi_free_opencv(pipi_image_t *img)
     IplImage *iplimg;
     iplimg = (IplImage *)img->codec_priv;
     cvReleaseImage(&iplimg);
-
-    free(img);
 }
 
 void pipi_save_opencv(pipi_image_t *img, const char *name)
 {
+    if(!img->codec_priv)
+    {
+        IplImage *priv = cvCreateImage(cvSize(img->w, img->h),
+                                       IPL_DEPTH_8U, 3);
+
+        /* FIXME: check pitch differences here */
+        if(img->last_modified == PIPI_PIXELS_BGR24)
+        {
+            memcpy(priv->imageData, img->p[PIPI_PIXELS_BGR24].pixels,
+                   3 * img->w * img->h);
+            free(img->p[PIPI_PIXELS_BGR24].pixels);
+        }
+
+        img->p[PIPI_PIXELS_BGR24].pixels = priv->imageData;
+        img->p[PIPI_PIXELS_BGR24].w = priv->width;
+        img->p[PIPI_PIXELS_BGR24].h = priv->height;
+        img->p[PIPI_PIXELS_BGR24].pitch = priv->widthStep;
+
+        img->codec_priv = (void *)priv;
+        img->codec_format = PIPI_PIXELS_BGR24;
+    }
+
     pipi_getpixels(img, img->codec_format);
     cvSaveImage(name, img->codec_priv);
 }