Main Page | Class List | Directories | File List | Class Members | File Members

png-module.c

Go to the documentation of this file.
00001 /* -*- mode: C; mode: fold; -*- */
00002 /*
00003 Copyright (C) 2005, 2006 John E. Davis
00004 
00005 This file is part of the S-Lang Library.
00006 
00007 The S-Lang Library is free software; you can redistribute it and/or
00008 modify it under the terms of the GNU General Public License as
00009 published by the Free Software Foundation; either version 2 of the
00010 License, or (at your option) any later version.
00011 
00012 The S-Lang Library is distributed in the hope that it will be useful,
00013 but WITHOUT ANY WARRANTY; without even the implied warranty of
00014 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015 General Public License for more details.
00016 
00017 You should have received a copy of the GNU General Public License
00018 along with this library; if not, write to the Free Software
00019 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
00020 USA.  
00021 */
00022 
00023 #include "config.h"
00024 
00025 #include <stdio.h>
00026 #include <errno.h>
00027 #include <slang.h>
00028 
00029 #include <png.h>
00030 
00031 SLANG_MODULE(png);
00032 
00033 static char *Module_Version_String = "0.1.1";
00034 #define MODULE_VERSION_NUMBER  (0*10000 + 1*100 + 1)
00035 
00036 /*{{{ Byte-swapping routines */
00037 
00038 static int Is_Little_Endian;
00039 
00040 static void byte_swap32 (unsigned char *p, unsigned char *t, unsigned int n)
00041 {
00042    unsigned char *pmax, ch;
00043 
00044    /* t and p could point to the same buffer */
00045    pmax = p + 4 * n;
00046    while (p < pmax)
00047      {
00048         ch = *p;
00049         *t = *(p + 3);
00050         *(t + 3) = ch;
00051 
00052         ch = *(p + 1);
00053         *(t + 1) = *(p + 2);
00054         *(t + 2) = ch;
00055         p += 4;
00056         t += 4;
00057      }
00058 }
00059 
00060 static void byte_swap16 (unsigned char *p, unsigned char *t, unsigned int n)
00061 {
00062    unsigned char *pmax, ch;
00063 
00064    pmax = p + 2 * n;
00065    while (p < pmax)
00066      {
00067         ch = *p;
00068         *t = *(p + 1);
00069         *(t + 1) = ch;
00070         p += 2;
00071         t += 2;
00072      }
00073 }
00074 
00075 /*}}}*/
00076 
00077 /*{{{ Png_Type */
00078 
00079 typedef struct 
00080 {
00081    FILE *fp;
00082    int mode;                           /* 'r' or 'w' */
00083    png_struct *png;
00084    png_info *info;
00085 }
00086 Png_Type;
00087 
00088 static void free_png_type (Png_Type *p)
00089 {
00090    if (p == NULL)
00091      return;
00092    if (p->png != NULL)
00093      {
00094         if (p->mode == 'r')
00095           {
00096              if (p->info != NULL)
00097                png_destroy_read_struct (&p->png, &p->info, NULL);
00098              else
00099                png_destroy_read_struct (&p->png, NULL, NULL);
00100           }
00101         else
00102           {
00103              if (p->info != NULL)
00104                png_destroy_write_struct (&p->png, &p->info);
00105              else
00106                png_destroy_write_struct (&p->png, NULL);
00107           }
00108      }
00109 
00110    if (p->fp != NULL)
00111      fclose (p->fp);
00112 
00113    SLfree ((char *) p);
00114 }
00115 
00116 static Png_Type *alloc_png_type (int mode)
00117 {
00118    Png_Type *p;
00119 
00120    if (NULL != (p = (Png_Type *)SLmalloc (sizeof (Png_Type))))
00121      {
00122         memset ((char *) p, 0, sizeof (Png_Type));
00123         p->mode = mode;
00124      }
00125    return p;
00126 }
00127 
00128 
00129 /*}}}*/
00130 
00131 static png_byte **allocate_image_pointers (png_uint_32 height, png_byte *data, png_uint_32 rowbytes, int flip)
00132 {
00133    png_byte **image_pointers;
00134    png_uint_32 i;
00135 
00136    if (NULL == (image_pointers = (png_byte **) SLmalloc (height * sizeof (png_byte *))))
00137      return NULL;
00138 
00139    if (flip)
00140      {
00141         i = height;
00142         while (i != 0)
00143           {
00144              i--;
00145              image_pointers[i] = data;
00146              data += rowbytes;
00147           }
00148         return image_pointers;
00149      }
00150    for (i = 0; i < height; i++)
00151      {
00152         image_pointers[i] = data;
00153         data += rowbytes;
00154      }
00155    return image_pointers;
00156 }
00157 
00158 static void free_image_pointers (png_byte **image_pointers)
00159 {
00160    if (image_pointers == NULL)
00161      return;
00162 
00163    SLfree ((char *) image_pointers);
00164 }
00165 
00166 /*{{{ png read functions */
00167 
00168 static Png_Type *open_png_file (char *file)
00169 {
00170    png_byte header[8];
00171    Png_Type *p;
00172    
00173    if (NULL == (p = alloc_png_type ('r')))
00174      return NULL;
00175 
00176    if ((NULL == (p->fp = fopen (file, "rb")))
00177        || (8 != fread (header, 1, 8, p->fp))
00178        || (0 != png_sig_cmp(header, 0, 8)))
00179      {
00180         SLang_verror (SL_Open_Error, "Unable to open %s as a png file", file);
00181         free_png_type (p);
00182         return NULL;
00183      }
00184    
00185    if (NULL == (p->png = png_create_read_struct (PNG_LIBPNG_VER_STRING, NULL, NULL, NULL)))
00186      {
00187         SLang_verror (SL_Open_Error, "Unable to read png structure from %s", file);
00188         free_png_type (p);
00189         return NULL;
00190      }
00191 
00192    if (NULL == (p->info = png_create_info_struct (p->png)))
00193      {
00194         SLang_verror (SL_Read_Error, "Unable to create info struct for %s", file);
00195         free_png_type (p);
00196         return NULL;
00197      }
00198    
00199    return p;
00200 }
00201 
00202 static void fixup_array_rgb (SLang_Array_Type *at)
00203 {
00204    SLindex_Type num_rows, num_cols, row;
00205    unsigned char *data;
00206 
00207    num_rows = at->dims[0];
00208    num_cols = at->dims[1];
00209    data = (unsigned char *) at->data;
00210 
00211    /* Convert RGBRGBRGB....  to 0RGB0RGB0RGB ... */
00212    for (row = 0; row < num_rows; row++)
00213      {
00214         unsigned char *p = data + 3*num_cols;
00215         unsigned char *q = p + num_cols;
00216         while (p != data)
00217           {
00218              *(--q) = *(--p);
00219              *(--q) = *(--p);
00220              *(--q) = *(--p);
00221              *(--q) = 0;               /* or 0xFF */
00222           }
00223         data += 4*num_cols;
00224      }
00225 
00226    if (Is_Little_Endian)
00227      byte_swap32 ((unsigned char *)at->data, (unsigned char *)at->data, at->num_elements);
00228 }
00229 
00230 static void fixup_array_rgba (SLang_Array_Type *at)
00231 {
00232    unsigned char *data, *data_max;
00233 
00234    data = (unsigned char *) at->data;
00235    data_max = data + at->num_elements;
00236 
00237    /* RGBARGBA -> ARGBARGB */
00238    while (data < data_max)
00239      {
00240         unsigned char a = data[3];
00241         data[3] = data[2];
00242         data[2] = data[1];
00243         data[1] = data[0];
00244         data[0] = a;
00245         data += 4;
00246      }
00247    if (Is_Little_Endian)
00248      byte_swap32 ((unsigned char *)at->data, (unsigned char *)at->data, at->num_elements);
00249 }
00250 
00251 static void fixup_array_ga (SLang_Array_Type *at)
00252 {
00253    if (Is_Little_Endian)
00254      byte_swap16 ((unsigned char *)at->data, (unsigned char *) at->data, at->num_elements);
00255 }
00256 
00257 /* For little endian systems, ARGB is equivalent to the int32 BGRA.
00258  * So, to read the image as RGB
00259  */
00260 static SLang_Array_Type *read_image_internal (char *file, int flip, int *color_typep)
00261 {
00262    Png_Type *p;
00263    png_uint_32 width, height, rowbytes;
00264    png_struct *png;
00265    png_info *info;
00266    int bit_depth;
00267    int interlace_type;
00268    int color_type;
00269    unsigned int sizeof_type;
00270    SLindex_Type dims[2];
00271    SLtype data_type;
00272    png_byte **image_pointers = NULL;
00273    png_byte *data = NULL;
00274    SLang_Array_Type *at;
00275    void (*fixup_array_fun) (SLang_Array_Type *);
00276 
00277    if (NULL == (p = open_png_file (file)))
00278      return NULL;
00279    
00280    png = p->png;
00281    if (setjmp (png_jmpbuf (png)))
00282      {
00283         free_png_type (p);
00284         if (data != NULL) SLfree ((char *) data);
00285         free_image_pointers (image_pointers);
00286         SLang_verror (SL_Read_Error, "Error encountered during I/O to %s", file);
00287         return NULL;
00288      }
00289    
00290    png_init_io (png, p->fp);
00291    png_set_sig_bytes (png, 8);
00292    info = p->info;
00293    png_read_info(png, info);
00294 
00295    width = png_get_image_width (png, info);
00296    height = png_get_image_height (png, info);
00297    interlace_type = png_get_interlace_type (png, info);
00298    bit_depth = png_get_bit_depth (png, info);
00299 
00300    if (bit_depth == 16)
00301      png_set_strip_16 (png);
00302 
00303    switch (png_get_color_type (png, info))
00304      {
00305       case PNG_COLOR_TYPE_GRAY:
00306         if (bit_depth < 8) png_set_gray_1_2_4_to_8 (png);
00307         break;
00308       case PNG_COLOR_TYPE_GRAY_ALPHA:
00309         /* png_set_gray_to_rgb (png); */
00310         break;
00311         
00312       case PNG_COLOR_TYPE_PALETTE:
00313         png_set_palette_to_rgb (png);
00314         break;
00315      }
00316    
00317    if (png_get_valid(png, info, PNG_INFO_tRNS))
00318      png_set_tRNS_to_alpha(png);
00319 
00320    png_read_update_info (png, info);
00321 
00322    color_type = png_get_color_type (png, info);
00323    switch (color_type)
00324      {
00325       case PNG_COLOR_TYPE_RGBA:
00326         sizeof_type = 4;
00327         fixup_array_fun = fixup_array_rgba;
00328         data_type = SLang_get_int_type (32);
00329         break;
00330 
00331       case PNG_COLOR_TYPE_RGB:
00332         sizeof_type = 4;
00333         fixup_array_fun = fixup_array_rgb;
00334         data_type = SLang_get_int_type (32);
00335         break;
00336 
00337       case PNG_COLOR_TYPE_GRAY_ALPHA:
00338         sizeof_type = 2;
00339         fixup_array_fun = fixup_array_ga;
00340         data_type = SLang_get_int_type (16);
00341         break;
00342 
00343       case PNG_COLOR_TYPE_GRAY:
00344         sizeof_type = 1;
00345         fixup_array_fun = NULL;
00346         data_type = SLANG_UCHAR_TYPE;
00347         break;
00348 
00349       default:
00350         SLang_verror (SL_Read_Error, "Unsupported PNG color-type");
00351         free_png_type (p);
00352         return NULL;
00353      }
00354    *color_typep = color_type;
00355 
00356    /* Use the high-level interface */
00357    rowbytes = png_get_rowbytes (png, info);
00358    if (rowbytes > width * sizeof_type)
00359      {
00360         SLang_verror (SL_INTERNAL_ERROR, "Unexpected value returned from png_get_rowbytes");
00361         free_png_type (p);
00362         return NULL;
00363      }
00364 
00365    if (NULL == (data = (png_byte *) SLmalloc (height * width * sizeof_type)))
00366      {
00367         free_png_type (p);
00368         return NULL;
00369      }
00370 
00371    if (NULL == (image_pointers = allocate_image_pointers (height, data, width * sizeof_type, flip)))
00372      {
00373         SLfree ((char *) data);
00374         free_png_type (p);
00375         return NULL;
00376      }
00377    png_read_image(png, image_pointers);
00378 
00379    dims[0] = height;
00380    dims[1] = width;
00381 
00382    if (NULL == (at = SLang_create_array (data_type, 0, (VOID_STAR) data, dims, 2)))
00383      {
00384         SLfree ((char *) data);
00385         free_image_pointers (image_pointers);
00386         free_png_type (p);
00387         return NULL;
00388      }
00389    free_png_type (p);
00390    free_image_pointers (image_pointers);
00391    if (fixup_array_fun != NULL) 
00392      (*fixup_array_fun) (at);
00393    return at;
00394 }
00395 
00396 static void read_image (int flipped)
00397 {
00398    int color_type;
00399    char *file;
00400    SLang_Ref_Type *ref = NULL;
00401    SLang_Array_Type *at;
00402 
00403    if ((SLang_Num_Function_Args == 2)
00404        && (-1 == SLang_pop_ref (&ref)))
00405      return;
00406 
00407    if (-1 == SLang_pop_slstring (&file))
00408      {
00409         file = NULL;
00410         goto free_return;
00411      }
00412    
00413    if (NULL == (at = read_image_internal (file, flipped, &color_type)))
00414      goto free_return;
00415 
00416    if ((ref != NULL)
00417        && (-1 == SLang_assign_to_ref (ref, SLANG_INT_TYPE, &color_type)))
00418      {
00419         SLang_free_array (at);
00420         goto free_return;
00421      }
00422 
00423    (void) SLang_push_array (at, 1);
00424 
00425    free_return:
00426    SLang_free_slstring (file);
00427    if (ref != NULL)
00428      SLang_free_ref (ref);
00429 }
00430 
00431 /*}}}*/
00432 
00433 static void write_gray_to_gray (png_struct *png, png_byte *data, SLindex_Type num_cols, png_byte *tmpbuf)
00434 {
00435    (void) num_cols;
00436    (void) tmpbuf;
00437    png_write_row (png, data);
00438 }
00439 
00440 static void write_gray_to_gray_alpha (png_struct *png, png_byte *data, SLindex_Type num_cols, png_byte *tmpbuf)
00441 {
00442    SLindex_Type i, j;
00443    
00444    j = 0;
00445    for (i = 0; i < num_cols; i++)
00446      {
00447         tmpbuf[j] = data[i];
00448         tmpbuf[j+1] = 0xFF;
00449         j += 2;
00450      }
00451    png_write_row (png, tmpbuf);
00452 }
00453 
00454 static void write_gray_alpha_to_gray (png_struct *png, png_byte *data, SLindex_Type num_cols, png_byte *tmpbuf)
00455 {
00456    SLindex_Type i;
00457 
00458    if (Is_Little_Endian == 0)
00459      data++; /* AGAGAG... -> GAGAGA... */
00460 
00461    for (i = 0; i < num_cols; i++)
00462      {
00463         tmpbuf[i] = *data;
00464         data += 2;
00465      }
00466    png_write_row (png, tmpbuf);
00467 }
00468 
00469 static void write_gray_alpha_to_gray_alpha (png_struct *png, png_byte *data, SLindex_Type num_cols, png_byte *tmpbuf)
00470 {
00471    if (Is_Little_Endian == 0)
00472      {     
00473         png_write_row (png, data);
00474         return;
00475      }
00476 
00477    byte_swap16 ((unsigned char *) data, (unsigned char *) tmpbuf, num_cols);
00478    png_write_row (png, tmpbuf);
00479 }
00480 
00481 static void write_rgb_alpha_to_rgb_alpha (png_struct *png, png_byte *data, SLindex_Type num_cols, png_byte *tmpbuf)
00482 {
00483    unsigned char *data_max;
00484    unsigned char *p;
00485 
00486    if (Is_Little_Endian)
00487      {
00488         byte_swap32 ((unsigned char *) data, (unsigned char *) tmpbuf, num_cols);
00489         data = tmpbuf;
00490      }
00491    data_max = data + 4 * num_cols;
00492    p = tmpbuf;
00493    /* Change ARGBARGB... to RGBARGBA... */
00494    while (data < data_max)
00495      {
00496         unsigned char a = data[0];
00497         p[0] = data[1];
00498         p[1] = data[2];
00499         p[2] = data[3];
00500         p[3] = a;
00501         data += 4;
00502         p += 4;
00503      }
00504    png_write_row (png, tmpbuf);
00505 }
00506 
00507 static void write_rgb_to_rgb (png_struct *png, png_byte *data, SLindex_Type num_cols, png_byte *tmpbuf)
00508 {
00509    SLindex_Type i;
00510    png_byte *p, *q;
00511 
00512    if (Is_Little_Endian)
00513      {
00514         byte_swap32 ((unsigned char *) data, (unsigned char *) tmpbuf, num_cols);
00515         p = tmpbuf;
00516      }
00517    else p = data;
00518 
00519    /* ARGBARGB... -> RGBRGBRGB */
00520    q = tmpbuf;
00521    for (i = 0; i < num_cols; i++)
00522      {
00523         p++;
00524         *q++ = *p++;
00525         *q++ = *p++;
00526         *q++ = *p++;
00527      }
00528    png_write_row (png, tmpbuf);
00529 }
00530 
00531 
00532 static int write_array (png_struct *png, png_byte **image_pointers, SLindex_Type num_rows, SLindex_Type num_cols,
00533                         void (*write_row_func) (png_struct *, png_byte *, SLindex_Type, png_byte *),
00534                         png_byte *tmpbuf)
00535 {
00536    int num_pass;
00537    SLindex_Type i;
00538 
00539    num_pass = png_set_interlace_handling(png);
00540    while (num_pass > 0)
00541      {
00542         num_pass--;
00543         for (i = 0; i < num_rows; i++)
00544           (*write_row_func) (png, image_pointers[i], num_cols, tmpbuf);
00545      }
00546    return 0;
00547 }
00548 
00549 static int write_image_internal (char *file, SLang_Array_Type *at,
00550                                  int color_type,
00551                                  void (*write_fun)(png_struct *, png_byte *p, SLindex_Type, png_byte *),
00552                                  int flip)
00553 {
00554    FILE *fp;
00555    Png_Type *p = NULL;
00556    png_struct *png;
00557    png_info *info;
00558    SLindex_Type width, height;
00559    png_byte **image_pointers;
00560    int bit_depth;
00561    int status = -1;
00562    png_byte *tmpbuf;
00563 
00564    bit_depth = 8;
00565 
00566    height = at->dims[0];
00567    width = at->dims[1];
00568 
00569    if (NULL == (image_pointers = allocate_image_pointers (height, (png_byte *)at->data, width * at->sizeof_type, flip)))
00570      return -1;
00571 
00572    if (NULL == (tmpbuf = (png_byte *)SLmalloc (4*width)))
00573      {
00574         free_image_pointers (image_pointers);
00575         return -1;
00576      }
00577 
00578    if (NULL == (fp = fopen (file, "wb")))
00579      {
00580         (void)SLerrno_set_errno (errno);
00581         SLang_verror (SL_Open_Error, "Unable to open %s", file);
00582         goto return_error;
00583      }
00584 
00585    if (NULL == (p = alloc_png_type ('w')))
00586      goto return_error;
00587 
00588    p->fp = fp;
00589 
00590    if (NULL == (p->png = png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL)))
00591      {
00592         SLang_verror (SL_Open_Error, "png_create_write_struct failed");
00593         goto return_error;
00594      }
00595    png = p->png;
00596    if (NULL == (p->info = png_create_info_struct (png)))
00597      {
00598         SLang_verror (SL_Open_Error, "png_create_info_struct failed");
00599         goto return_error;
00600      }
00601    info = p->info;
00602    if (setjmp(png_jmpbuf(png)))
00603      {
00604         SLang_verror (SL_Write_Error, "PNG I/O error");
00605         goto return_error;
00606      }
00607    png_init_io(png, fp);
00608 
00609    png_set_IHDR (png, info, width, height,
00610                  bit_depth, color_type, PNG_INTERLACE_NONE,
00611                  PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);
00612    png_write_info(png, info);
00613 
00614    if (-1 == write_array (png, image_pointers, height, width, write_fun, tmpbuf))
00615      goto return_error;
00616 
00617    png_write_end(png, NULL);
00618    if (EOF == fclose (p->fp))
00619      {
00620         SLang_verror (SL_Write_Error, "Error closing %s", file);
00621         SLerrno_set_errno (errno);
00622      }
00623    else status = 0;
00624 
00625    p->fp = NULL;
00626    /* drop */
00627    return_error:
00628    if (tmpbuf != NULL) 
00629      SLfree ((char *) tmpbuf);
00630    free_image_pointers (image_pointers);
00631    if (p != NULL)
00632      free_png_type (p);
00633 
00634    return status;
00635 }
00636 
00637 
00638 static void write_image (int flip)
00639 {
00640    char *file;
00641    SLang_Array_Type *at;
00642    int with_alpha = 0;
00643    int has_with_alpha = 0;
00644    int color_type;
00645    void (*write_fun) (png_struct *, png_byte *, SLindex_Type, png_byte *);
00646 
00647    if (SLang_Num_Function_Args == 3)
00648      {
00649         if (-1 == SLang_pop_int (&with_alpha))
00650           return;
00651         has_with_alpha = 1;
00652      }
00653 
00654    if (-1 == SLang_pop_array (&at, 0))
00655      return;
00656    
00657    if (at->num_dims != 2)
00658      {
00659         SLang_verror (SL_InvalidParm_Error, "Expecting a 2-d array");
00660         SLang_free_array (at);
00661         return;
00662      }
00663    
00664    switch (SLang_get_int_size (at->data_type))
00665      {
00666       case -8:
00667       case 8:
00668         if (with_alpha)
00669           {
00670              write_fun = write_gray_to_gray_alpha;
00671              color_type = PNG_COLOR_TYPE_GRAY_ALPHA;
00672           }
00673         else
00674           {
00675              write_fun = write_gray_to_gray;
00676              color_type = PNG_COLOR_TYPE_GRAY;
00677           }
00678         break;
00679       case -16:
00680       case 16:
00681         if (has_with_alpha && (with_alpha == 0))
00682           {
00683              write_fun = write_gray_alpha_to_gray;
00684              color_type = PNG_COLOR_TYPE_GRAY;
00685           }
00686         else
00687           {
00688              write_fun = write_gray_alpha_to_gray_alpha;
00689              color_type = PNG_COLOR_TYPE_GRAY_ALPHA;
00690           }
00691         break;
00692       case -32:
00693       case 32:
00694         if (with_alpha)
00695           {
00696              write_fun = write_rgb_alpha_to_rgb_alpha;
00697              color_type = PNG_COLOR_TYPE_RGBA;
00698           }
00699         else
00700           {
00701              write_fun = write_rgb_to_rgb;
00702              color_type = PNG_COLOR_TYPE_RGB;
00703           }
00704         break;
00705       default:
00706         SLang_verror (SL_InvalidParm_Error, "Expecting an 8, 16, or 32 bit integer array");
00707         SLang_free_array (at);
00708         return;
00709      }
00710      
00711    if (-1 == SLang_pop_slstring (&file))
00712      {
00713         SLang_free_array (at);
00714         return;
00715      }
00716    (void) write_image_internal (file, at, color_type, write_fun, flip);
00717    SLang_free_slstring (file);
00718    SLang_free_array (at);
00719 }
00720 
00721        
00722 static void read_intrin (void)
00723 {
00724    read_image (0);
00725 }
00726 static void read_flipped_intrin (void)
00727 {
00728    read_image (1);
00729 }
00730 
00731 static void write_intrin (void)
00732 {
00733    write_image (0);
00734 }
00735 static void write_flipped_intrin (void)
00736 {
00737    write_image (1);
00738 }
00739 
00740 static SLang_Intrin_Fun_Type Module_Intrinsics [] =
00741 {
00742    MAKE_INTRINSIC_0("png_read", read_intrin, SLANG_VOID_TYPE),
00743    MAKE_INTRINSIC_0("png_read_flipped", read_flipped_intrin, SLANG_VOID_TYPE),
00744    MAKE_INTRINSIC_0("png_write", write_intrin, SLANG_VOID_TYPE),
00745    MAKE_INTRINSIC_0("png_write_flipped", write_flipped_intrin, SLANG_VOID_TYPE),
00746    SLANG_END_INTRIN_FUN_TABLE
00747 };
00748 
00749 static SLang_Intrin_Var_Type Module_Variables [] =
00750 {
00751    MAKE_VARIABLE("_png_module_version_string", &Module_Version_String, SLANG_STRING_TYPE, 1),
00752    SLANG_END_INTRIN_VAR_TABLE
00753 };
00754 
00755 static SLang_IConstant_Type Module_IConstants [] =
00756 {
00757    MAKE_ICONSTANT("PNG_COLOR_TYPE_GRAY", PNG_COLOR_TYPE_GRAY),
00758    MAKE_ICONSTANT("PNG_COLOR_TYPE_GRAY_ALPHA", PNG_COLOR_TYPE_GRAY_ALPHA),
00759    MAKE_ICONSTANT("PNG_COLOR_TYPE_RGB", PNG_COLOR_TYPE_RGB),
00760    MAKE_ICONSTANT("PNG_COLOR_TYPE_RGBA", PNG_COLOR_TYPE_RGBA),
00761 
00762    MAKE_ICONSTANT("_png_module_version", MODULE_VERSION_NUMBER),
00763    SLANG_END_ICONST_TABLE
00764 };
00765 
00766 int init_png_module_ns (char *ns_name)
00767 {
00768    unsigned short x;
00769 
00770    SLang_NameSpace_Type *ns = SLns_create_namespace (ns_name);
00771    if (ns == NULL)
00772      return -1;
00773 
00774    x = 0xFF;
00775    Is_Little_Endian = (*(unsigned char *)&x == 0xFF);
00776 
00777    if (
00778        (-1 == SLns_add_intrin_var_table (ns, Module_Variables, NULL))
00779        || (-1 == SLns_add_intrin_fun_table (ns, Module_Intrinsics, NULL))
00780        || (-1 == SLns_add_iconstant_table (ns, Module_IConstants, NULL))
00781        )
00782      return -1;
00783 
00784    return 0;
00785 }
00786 
00787 /* This function is optional */
00788 void deinit_png_module (void)
00789 {
00790 }

© sourcejam.com 2005-2008