Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygentif_tile.c
Go to the documentation of this file.
00001 /* $Id: tif_tile.c,v 1.12.2.1 2010-06-08 18:50:43 bfriesen Exp $ */ 00002 00003 /* 00004 * Copyright (c) 1991-1997 Sam Leffler 00005 * Copyright (c) 1991-1997 Silicon Graphics, Inc. 00006 * 00007 * Permission to use, copy, modify, distribute, and sell this software and 00008 * its documentation for any purpose is hereby granted without fee, provided 00009 * that (i) the above copyright notices and this permission notice appear in 00010 * all copies of the software and related documentation, and (ii) the names of 00011 * Sam Leffler and Silicon Graphics may not be used in any advertising or 00012 * publicity relating to the software without the specific, prior written 00013 * permission of Sam Leffler and Silicon Graphics. 00014 * 00015 * THE SOFTWARE IS PROVIDED "AS-IS" AND WITHOUT WARRANTY OF ANY KIND, 00016 * EXPRESS, IMPLIED OR OTHERWISE, INCLUDING WITHOUT LIMITATION, ANY 00017 * WARRANTY OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. 00018 * 00019 * IN NO EVENT SHALL SAM LEFFLER OR SILICON GRAPHICS BE LIABLE FOR 00020 * ANY SPECIAL, INCIDENTAL, INDIRECT OR CONSEQUENTIAL DAMAGES OF ANY KIND, 00021 * OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, 00022 * WHETHER OR NOT ADVISED OF THE POSSIBILITY OF DAMAGE, AND ON ANY THEORY OF 00023 * LIABILITY, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE 00024 * OF THIS SOFTWARE. 00025 */ 00026 00027 /* 00028 * TIFF Library. 00029 * 00030 * Tiled Image Support Routines. 00031 */ 00032 #include "tiffiop.h" 00033 00034 static uint32 00035 summarize(TIFF* tif, size_t summand1, size_t summand2, const char* where) 00036 { 00037 /* 00038 * XXX: We are using casting to uint32 here, because sizeof(size_t) 00039 * may be larger than sizeof(uint32) on 64-bit architectures. 00040 */ 00041 uint32 bytes = summand1 + summand2; 00042 00043 if (bytes - summand1 != summand2) { 00044 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, "Integer overflow in %s", where); 00045 bytes = 0; 00046 } 00047 00048 return (bytes); 00049 } 00050 00051 static uint32 00052 multiply(TIFF* tif, size_t nmemb, size_t elem_size, const char* where) 00053 { 00054 uint32 bytes = nmemb * elem_size; 00055 00056 if (elem_size && bytes / elem_size != nmemb) { 00057 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, "Integer overflow in %s", where); 00058 bytes = 0; 00059 } 00060 00061 return (bytes); 00062 } 00063 00064 /* 00065 * Compute which tile an (x,y,z,s) value is in. 00066 */ 00067 ttile_t 00068 TIFFComputeTile(TIFF* tif, uint32 x, uint32 y, uint32 z, tsample_t s) 00069 { 00070 TIFFDirectory *td = &tif->tif_dir; 00071 uint32 dx = td->td_tilewidth; 00072 uint32 dy = td->td_tilelength; 00073 uint32 dz = td->td_tiledepth; 00074 ttile_t tile = 1; 00075 00076 if (td->td_imagedepth == 1) 00077 z = 0; 00078 if (dx == (uint32) -1) 00079 dx = td->td_imagewidth; 00080 if (dy == (uint32) -1) 00081 dy = td->td_imagelength; 00082 if (dz == (uint32) -1) 00083 dz = td->td_imagedepth; 00084 if (dx != 0 && dy != 0 && dz != 0) { 00085 uint32 xpt = TIFFhowmany(td->td_imagewidth, dx); 00086 uint32 ypt = TIFFhowmany(td->td_imagelength, dy); 00087 uint32 zpt = TIFFhowmany(td->td_imagedepth, dz); 00088 00089 if (td->td_planarconfig == PLANARCONFIG_SEPARATE) 00090 tile = (xpt*ypt*zpt)*s + 00091 (xpt*ypt)*(z/dz) + 00092 xpt*(y/dy) + 00093 x/dx; 00094 else 00095 tile = (xpt*ypt)*(z/dz) + xpt*(y/dy) + x/dx; 00096 } 00097 return (tile); 00098 } 00099 00100 /* 00101 * Check an (x,y,z,s) coordinate 00102 * against the image bounds. 00103 */ 00104 int 00105 TIFFCheckTile(TIFF* tif, uint32 x, uint32 y, uint32 z, tsample_t s) 00106 { 00107 TIFFDirectory *td = &tif->tif_dir; 00108 00109 if (x >= td->td_imagewidth) { 00110 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, 00111 "%lu: Col out of range, max %lu", 00112 (unsigned long) x, 00113 (unsigned long) (td->td_imagewidth - 1)); 00114 return (0); 00115 } 00116 if (y >= td->td_imagelength) { 00117 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, 00118 "%lu: Row out of range, max %lu", 00119 (unsigned long) y, 00120 (unsigned long) (td->td_imagelength - 1)); 00121 return (0); 00122 } 00123 if (z >= td->td_imagedepth) { 00124 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, 00125 "%lu: Depth out of range, max %lu", 00126 (unsigned long) z, 00127 (unsigned long) (td->td_imagedepth - 1)); 00128 return (0); 00129 } 00130 if (td->td_planarconfig == PLANARCONFIG_SEPARATE && 00131 s >= td->td_samplesperpixel) { 00132 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, 00133 "%lu: Sample out of range, max %lu", 00134 (unsigned long) s, 00135 (unsigned long) (td->td_samplesperpixel - 1)); 00136 return (0); 00137 } 00138 return (1); 00139 } 00140 00141 /* 00142 * Compute how many tiles are in an image. 00143 */ 00144 ttile_t 00145 TIFFNumberOfTiles(TIFF* tif) 00146 { 00147 TIFFDirectory *td = &tif->tif_dir; 00148 uint32 dx = td->td_tilewidth; 00149 uint32 dy = td->td_tilelength; 00150 uint32 dz = td->td_tiledepth; 00151 ttile_t ntiles; 00152 00153 if (dx == (uint32) -1) 00154 dx = td->td_imagewidth; 00155 if (dy == (uint32) -1) 00156 dy = td->td_imagelength; 00157 if (dz == (uint32) -1) 00158 dz = td->td_imagedepth; 00159 ntiles = (dx == 0 || dy == 0 || dz == 0) ? 0 : 00160 multiply(tif, multiply(tif, TIFFhowmany(td->td_imagewidth, dx), 00161 TIFFhowmany(td->td_imagelength, dy), 00162 "TIFFNumberOfTiles"), 00163 TIFFhowmany(td->td_imagedepth, dz), "TIFFNumberOfTiles"); 00164 if (td->td_planarconfig == PLANARCONFIG_SEPARATE) 00165 ntiles = multiply(tif, ntiles, td->td_samplesperpixel, 00166 "TIFFNumberOfTiles"); 00167 return (ntiles); 00168 } 00169 00170 /* 00171 * Compute the # bytes in each row of a tile. 00172 */ 00173 tsize_t 00174 TIFFTileRowSize(TIFF* tif) 00175 { 00176 TIFFDirectory *td = &tif->tif_dir; 00177 tsize_t rowsize; 00178 00179 if (td->td_tilelength == 0 || td->td_tilewidth == 0) 00180 return ((tsize_t) 0); 00181 rowsize = multiply(tif, td->td_bitspersample, td->td_tilewidth, 00182 "TIFFTileRowSize"); 00183 if (td->td_planarconfig == PLANARCONFIG_CONTIG) 00184 rowsize = multiply(tif, rowsize, td->td_samplesperpixel, 00185 "TIFFTileRowSize"); 00186 return ((tsize_t) TIFFhowmany8(rowsize)); 00187 } 00188 00189 /* 00190 * Compute the # bytes in a variable length, row-aligned tile. 00191 */ 00192 tsize_t 00193 TIFFVTileSize(TIFF* tif, uint32 nrows) 00194 { 00195 TIFFDirectory *td = &tif->tif_dir; 00196 tsize_t tilesize; 00197 00198 if (td->td_tilelength == 0 || td->td_tilewidth == 0 || 00199 td->td_tiledepth == 0) 00200 return ((tsize_t) 0); 00201 if (td->td_planarconfig == PLANARCONFIG_CONTIG && 00202 td->td_photometric == PHOTOMETRIC_YCBCR && 00203 !isUpSampled(tif)) { 00204 /* 00205 * Packed YCbCr data contain one Cb+Cr for every 00206 * HorizontalSampling*VerticalSampling Y values. 00207 * Must also roundup width and height when calculating 00208 * since images that are not a multiple of the 00209 * horizontal/vertical subsampling area include 00210 * YCbCr data for the extended image. 00211 */ 00212 tsize_t w = 00213 TIFFroundup(td->td_tilewidth, td->td_ycbcrsubsampling[0]); 00214 tsize_t rowsize = 00215 TIFFhowmany8(multiply(tif, w, td->td_bitspersample, 00216 "TIFFVTileSize")); 00217 tsize_t samplingarea = 00218 td->td_ycbcrsubsampling[0]*td->td_ycbcrsubsampling[1]; 00219 if (samplingarea == 0) { 00220 TIFFErrorExt(tif->tif_clientdata, tif->tif_name, "Invalid YCbCr subsampling"); 00221 return 0; 00222 } 00223 nrows = TIFFroundup(nrows, td->td_ycbcrsubsampling[1]); 00224 /* NB: don't need TIFFhowmany here 'cuz everything is rounded */ 00225 tilesize = multiply(tif, nrows, rowsize, "TIFFVTileSize"); 00226 tilesize = summarize(tif, tilesize, 00227 multiply(tif, 2, tilesize / samplingarea, 00228 "TIFFVTileSize"), 00229 "TIFFVTileSize"); 00230 } else 00231 tilesize = multiply(tif, nrows, TIFFTileRowSize(tif), 00232 "TIFFVTileSize"); 00233 return ((tsize_t) 00234 multiply(tif, tilesize, td->td_tiledepth, "TIFFVTileSize")); 00235 } 00236 00237 /* 00238 * Compute the # bytes in a row-aligned tile. 00239 */ 00240 tsize_t 00241 TIFFTileSize(TIFF* tif) 00242 { 00243 return (TIFFVTileSize(tif, tif->tif_dir.td_tilelength)); 00244 } 00245 00246 /* 00247 * Compute a default tile size based on the image 00248 * characteristics and a requested value. If a 00249 * request is <1 then we choose a size according 00250 * to certain heuristics. 00251 */ 00252 void 00253 TIFFDefaultTileSize(TIFF* tif, uint32* tw, uint32* th) 00254 { 00255 (*tif->tif_deftilesize)(tif, tw, th); 00256 } 00257 00258 void 00259 _TIFFDefaultTileSize(TIFF* tif, uint32* tw, uint32* th) 00260 { 00261 (void) tif; 00262 if (*(int32*) tw < 1) 00263 *tw = 256; 00264 if (*(int32*) th < 1) 00265 *th = 256; 00266 /* roundup to a multiple of 16 per the spec */ 00267 if (*tw & 0xf) 00268 *tw = TIFFroundup(*tw, 16); 00269 if (*th & 0xf) 00270 *th = TIFFroundup(*th, 16); 00271 } 00272 00273 /* vim: set ts=8 sts=8 sw=8 noet: */ 00274 /* 00275 * Local Variables: 00276 * mode: c 00277 * c-basic-offset: 8 00278 * fill-column: 78 00279 * End: 00280 */ Generated on Sat May 26 2012 04:18:25 for ReactOS by
1.7.6.1
|