home *** CD-ROM | disk | FTP | other *** search
/ Crawly Crypt Collection 1 / crawlyvol1.bin / program / grfx_snd / tifflib / source / tif_open.c < prev    next >
C/C++ Source or Header  |  1993-01-13  |  8KB  |  260 lines

  1. #pragma warn -use
  2. static char     *sccsid = "@(#)TIFF/tif_open.c 1.19, Copyright (c) Sam Leffler, Dieter Linde, "__DATE__;
  3. #pragma warn .use
  4. /*
  5.  * Copyright (c) 1988, 1990 by Sam Leffler, Nov 15 1990
  6.  * All rights reserved.
  7.  *
  8.  * This file is provided for unrestricted use provided that this legend is included on all tape media and as a part of the
  9.  * software program in whole or part.  Users may copy, modify or distribute this file at will.
  10.  *
  11.  * TIFF Library.
  12.  */
  13. #include <stdlib.h>
  14. #include "tiffio.h"
  15.  
  16. #ifndef TRUE
  17. #define TRUE       1
  18. #define FALSE      0
  19. #endif
  20.  
  21. #define ord(e)    ((int)e)
  22.  
  23. /****************************************************************************
  24.  * Initialize the bit fill order, the shift & mask tables, and the byte
  25.  * swapping state according to the file contents and the machine architecture.
  26.  */
  27. static void
  28. TIFFInitOrder(
  29.            register TIFF    *tif,
  30.         int         magic, 
  31.         int        bigendian
  32.         )
  33. {
  34.  
  35.         /*** XXX how can we deduce this dynamically? ***/
  36.         tif->tif_fillorder = FILLORDER_MSB2LSB;
  37.  
  38.         tif->tif_typemask[0] = 0;
  39.         tif->tif_typemask[ord(TIFF_BYTE)] = 0xff;
  40.         tif->tif_typemask[ord(TIFF_SHORT)] = 0xffff;
  41.         tif->tif_typemask[ord(TIFF_LONG)] = 0xffffffffL;
  42.         tif->tif_typemask[ord(TIFF_RATIONAL)] = 0xffffffffL;
  43.         tif->tif_typeshift[0] = 0;
  44.         tif->tif_typeshift[ord(TIFF_LONG)] = 0;
  45.         tif->tif_typeshift[ord(TIFF_RATIONAL)] = 0;
  46.         if (magic == TIFF_BIGENDIAN) {
  47.                 tif->tif_typeshift[ord(TIFF_BYTE)] = 24;
  48.                 tif->tif_typeshift[ord(TIFF_SHORT)] = 16;
  49.                 if (!bigendian)
  50.                         tif->tif_flags |= TIFF_SWAB;
  51.         } 
  52.         else {
  53.                 tif->tif_typeshift[ord(TIFF_BYTE)] = 0;
  54.                 tif->tif_typeshift[ord(TIFF_SHORT)] = 0;
  55.                 if (bigendian)
  56.                         tif->tif_flags |= TIFF_SWAB;
  57.         }
  58. }
  59.  
  60. /****************************************************************************
  61.  *
  62.  */
  63. static int
  64. getMode(
  65.            char     *mode, 
  66.            char    *module
  67.            )
  68. {
  69.         int     m = -1;
  70.  
  71.         switch (mode[0]) {
  72.             case 'r':
  73.                     m = O_RDONLY;
  74.                     if (mode[1] == '+')
  75.                             m = O_RDWR;
  76.                     break;
  77.             case 'w':
  78.             case 'a':
  79.                     m = O_RDWR | O_CREAT;
  80.                     if (mode[0] == 'w')
  81.                             m |= O_TRUNC;
  82.                     break;
  83.             default:
  84.                     TIFFError(module, "bad mode '%s'", mode);
  85.                     break;
  86.         }
  87.         return(m);
  88. }
  89.  
  90. /****************************************************************************
  91.  * Open a TIFF file descriptor for read/writing.
  92.  */
  93. TIFF *
  94. TIFFFdOpen(
  95.         int     fd,
  96.         char     *name, 
  97.         char    *mode
  98.         )
  99. {
  100.         static char    *module = "TIFFFdOpen";
  101.         TIFF         *tif;
  102.         int         m, bigendian;
  103.  
  104.         if ((m = getMode(mode, module)) == -1)
  105.                 goto bad2;
  106.         if ((tif = (TIFF *)malloc(sizeof(TIFF) + strlen(name) + 1)) == NULL) {
  107.                 TIFFError(module, "out of memory allocating TIFF structure");
  108.                 goto bad2;
  109.         }
  110.         bzero(tif, sizeof(*tif));
  111.         tif->tif_name = (char *)tif + sizeof(TIFF);
  112.         strcpy(tif->tif_name, name);
  113.         tif->tif_fd = fd;
  114.         tif->tif_mode = m & ~(O_CREAT | O_TRUNC);
  115.         tif->tif_curoff = 0;
  116.         tif->tif_curstrip = -1;            /* invalid strip */
  117.         tif->tif_row = -1;                 /* read/write pre-increment */
  118.         bigendian = TRUE;
  119.  
  120.         /*
  121.          * Read in TIFF header.
  122.          */
  123.         if (!ReadOK(fd, &tif->tif_header, sizeof(TIFFHeader))) {
  124.                 if (tif->tif_mode == O_RDONLY) {
  125.                         TIFFError(module, "can't read TIFF header");
  126.                         goto bad;
  127.                 }
  128.  
  129.     /*
  130.          * Setup header and write.
  131.          */
  132.                 tif->tif_header.tiff_magic =  bigendian ? TIFF_BIGENDIAN : TIFF_LITTLEENDIAN;
  133.                 tif->tif_header.tiff_version = TIFF_VERSION;
  134.                 tif->tif_header.tiff_diroff = 0;           /* filled in later */
  135.                 if (!WriteOK(fd, &tif->tif_header, sizeof(TIFFHeader))) {
  136.                         TIFFError(module, "error writing TIFF header");
  137.                         goto bad;
  138.                 }
  139.  
  140.     /*
  141.          * Setup the byte order handling.
  142.          */
  143.                 TIFFInitOrder(tif, tif->tif_header.tiff_magic, bigendian);
  144.  
  145.     /*
  146.          * Setup default directory.
  147.          */
  148.                 if (!TIFFDefaultDirectory(tif))
  149.                         goto bad;
  150.                 tif->tif_diroff = 0;
  151.                 return(tif);
  152.         }
  153.  
  154.           /*
  155.          * Setup the byte order handling.
  156.          */
  157.         if (tif->tif_header.tiff_magic != TIFF_BIGENDIAN && tif->tif_header.tiff_magic != TIFF_LITTLEENDIAN) {
  158.                    TIFFError(module,  "\"%s\" isn't a TIFF file, bad magic number 0x%04x", name, tif->tif_header.tiff_magic);
  159.                 goto bad;
  160.         }
  161.         TIFFInitOrder(tif, tif->tif_header.tiff_magic, bigendian);
  162.  
  163.         /*
  164.          * Swap header if required.
  165.          */
  166.         if (tif->tif_flags & TIFF_SWAB) {
  167.                 TIFFSwabShort(&tif->tif_header.tiff_version);
  168.                 TIFFSwabLong(&tif->tif_header.tiff_diroff);
  169.         }
  170.  
  171.         /*
  172.          * Now check version (if needed, it's been byte-swapped).
  173.          *
  174.          * Note that this isn't actually a version number, it's a magic number that doesn't change (stupid).
  175.          */
  176.         if (tif->tif_header.tiff_version != TIFF_VERSION) {
  177.                 TIFFError(module, "\"%s\" isn't a TIFF file, bad version number 0x%04x", name, tif->tif_header.tiff_version);
  178.                 goto bad;
  179.         }
  180.  
  181.         /*
  182.          * Setup initial directory.
  183.          */
  184.         switch (mode[0]) {
  185.             case 'r':
  186.                     tif->tif_nextdiroff = tif->tif_header.tiff_diroff;
  187.                     if (TIFFReadDirectory(tif)) {
  188.                             tif->tif_rawcc = -1;
  189.                             tif->tif_flags |= TIFF_BUFFERSETUP;
  190.                             return(tif);
  191.                     }
  192.                     break;
  193.             case 'a':
  194.  
  195.          /*
  196.          * Don't append to file that has information byte swapped -- we will write data that is
  197.          * in the opposite order.
  198.          */
  199.                        if (tif->tif_flags & TIFF_SWAB) {
  200.                                TIFFError(module, "can't append to a file that has opposite byte ordering");
  201.                             goto bad;
  202.                     }
  203.  
  204.            /*
  205.          * New directories are automatically append to the end of the directory chain when they
  206.          * are written out (see TIFFWriteDirectory).
  207.          */
  208.                        if (!TIFFDefaultDirectory(tif))
  209.                             goto bad;
  210.                     return(tif);
  211.         }
  212. bad:
  213.         tif->tif_mode = O_RDONLY;          /* XXX avoid flush */
  214.            TIFFClose(tif);
  215.         return(NULL);
  216. bad2:
  217.            close(fd);
  218.         return(NULL);
  219. }
  220.  
  221. /****************************************************************************
  222.  * Open a TIFF file for read/writing.
  223.  */
  224. TIFF *
  225. TIFFOpen(
  226.         char     *name, 
  227.         char    *mode
  228.         )
  229. {
  230.         static char    *module = "TIFFOpen";
  231.         int         m, fd;
  232.  
  233.         m = getMode(mode, module);
  234.         if (m == -1)
  235.                 return(NULL);
  236.         if ((fd = TIFFOpenFile(name, m, 0666)) < 0) {
  237.                 TIFFError(module, "can't open file \"%s\"", name);
  238.                 return(NULL);
  239.         }
  240.         return(TIFFFdOpen(fd, name, mode));
  241. }
  242.  
  243. /****************************************************************************
  244.  *
  245.  */
  246. int
  247. TIFFScanlineSize(
  248.            TIFF     *tif
  249.            )
  250. {
  251.         TIFFDirectory    *td = &tif->tif_dir;
  252.         long         scanline;
  253.  
  254.         scanline = td->td_bitspersample * td->td_imagewidth;
  255.         if (td->td_planarconfig == PLANARCONFIG_CONTIG)
  256.                 scanline *= td->td_samplesperpixel;
  257. #define    howmany(x, y)    (((x) + ((y) - 1)) / (y))
  258.         return((int)howmany(scanline, 8));
  259. }
  260.