pngget.c 31 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124
  1. /* pngget.c - retrieval of values from info struct
  2. *
  3. * Last changed in libpng 1.5.7 [December 15, 2011]
  4. * Copyright (c) 1998-2011 Glenn Randers-Pehrson
  5. * (Version 0.96 Copyright (c) 1996, 1997 Andreas Dilger)
  6. * (Version 0.88 Copyright (c) 1995, 1996 Guy Eric Schalnat, Group 42, Inc.)
  7. *
  8. * This code is released under the libpng license.
  9. * For conditions of distribution and use, see the disclaimer
  10. * and license in png.h
  11. *
  12. */
  13. #include "pngpriv.h"
  14. #if defined(PNG_READ_SUPPORTED) || defined(PNG_WRITE_SUPPORTED)
  15. png_uint_32 PNGAPI
  16. png_get_valid(png_const_structp png_ptr, png_const_infop info_ptr,
  17. png_uint_32 flag)
  18. {
  19. if (png_ptr != NULL && info_ptr != NULL)
  20. return(info_ptr->valid & flag);
  21. return(0);
  22. }
  23. png_size_t PNGAPI
  24. png_get_rowbytes(png_const_structp png_ptr, png_const_infop info_ptr)
  25. {
  26. if (png_ptr != NULL && info_ptr != NULL)
  27. return(info_ptr->rowbytes);
  28. return(0);
  29. }
  30. #ifdef PNG_INFO_IMAGE_SUPPORTED
  31. png_bytepp PNGAPI
  32. png_get_rows(png_const_structp png_ptr, png_const_infop info_ptr)
  33. {
  34. if (png_ptr != NULL && info_ptr != NULL)
  35. return(info_ptr->row_pointers);
  36. return(0);
  37. }
  38. #endif
  39. #ifdef PNG_EASY_ACCESS_SUPPORTED
  40. /* Easy access to info, added in libpng-0.99 */
  41. png_uint_32 PNGAPI
  42. png_get_image_width(png_const_structp png_ptr, png_const_infop info_ptr)
  43. {
  44. if (png_ptr != NULL && info_ptr != NULL)
  45. return info_ptr->width;
  46. return (0);
  47. }
  48. png_uint_32 PNGAPI
  49. png_get_image_height(png_const_structp png_ptr, png_const_infop info_ptr)
  50. {
  51. if (png_ptr != NULL && info_ptr != NULL)
  52. return info_ptr->height;
  53. return (0);
  54. }
  55. png_byte PNGAPI
  56. png_get_bit_depth(png_const_structp png_ptr, png_const_infop info_ptr)
  57. {
  58. if (png_ptr != NULL && info_ptr != NULL)
  59. return info_ptr->bit_depth;
  60. return (0);
  61. }
  62. png_byte PNGAPI
  63. png_get_color_type(png_const_structp png_ptr, png_const_infop info_ptr)
  64. {
  65. if (png_ptr != NULL && info_ptr != NULL)
  66. return info_ptr->color_type;
  67. return (0);
  68. }
  69. png_byte PNGAPI
  70. png_get_filter_type(png_const_structp png_ptr, png_const_infop info_ptr)
  71. {
  72. if (png_ptr != NULL && info_ptr != NULL)
  73. return info_ptr->filter_type;
  74. return (0);
  75. }
  76. png_byte PNGAPI
  77. png_get_interlace_type(png_const_structp png_ptr, png_const_infop info_ptr)
  78. {
  79. if (png_ptr != NULL && info_ptr != NULL)
  80. return info_ptr->interlace_type;
  81. return (0);
  82. }
  83. png_byte PNGAPI
  84. png_get_compression_type(png_const_structp png_ptr, png_const_infop info_ptr)
  85. {
  86. if (png_ptr != NULL && info_ptr != NULL)
  87. return info_ptr->compression_type;
  88. return (0);
  89. }
  90. png_uint_32 PNGAPI
  91. png_get_x_pixels_per_meter(png_const_structp png_ptr, png_const_infop info_ptr)
  92. {
  93. #ifdef PNG_pHYs_SUPPORTED
  94. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs))
  95. {
  96. png_debug1(1, "in %s retrieval function",
  97. "png_get_x_pixels_per_meter");
  98. if (info_ptr->phys_unit_type == PNG_RESOLUTION_METER)
  99. return (info_ptr->x_pixels_per_unit);
  100. }
  101. #endif
  102. return (0);
  103. }
  104. png_uint_32 PNGAPI
  105. png_get_y_pixels_per_meter(png_const_structp png_ptr, png_const_infop info_ptr)
  106. {
  107. #ifdef PNG_pHYs_SUPPORTED
  108. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs))
  109. {
  110. png_debug1(1, "in %s retrieval function",
  111. "png_get_y_pixels_per_meter");
  112. if (info_ptr->phys_unit_type == PNG_RESOLUTION_METER)
  113. return (info_ptr->y_pixels_per_unit);
  114. }
  115. #endif
  116. return (0);
  117. }
  118. png_uint_32 PNGAPI
  119. png_get_pixels_per_meter(png_const_structp png_ptr, png_const_infop info_ptr)
  120. {
  121. #ifdef PNG_pHYs_SUPPORTED
  122. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs))
  123. {
  124. png_debug1(1, "in %s retrieval function", "png_get_pixels_per_meter");
  125. if (info_ptr->phys_unit_type == PNG_RESOLUTION_METER &&
  126. info_ptr->x_pixels_per_unit == info_ptr->y_pixels_per_unit)
  127. return (info_ptr->x_pixels_per_unit);
  128. }
  129. #endif
  130. return (0);
  131. }
  132. #ifdef PNG_FLOATING_POINT_SUPPORTED
  133. float PNGAPI
  134. png_get_pixel_aspect_ratio(png_const_structp png_ptr, png_const_infop info_ptr)
  135. {
  136. #ifdef PNG_READ_pHYs_SUPPORTED
  137. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs))
  138. {
  139. png_debug1(1, "in %s retrieval function", "png_get_aspect_ratio");
  140. if (info_ptr->x_pixels_per_unit != 0)
  141. return ((float)((float)info_ptr->y_pixels_per_unit
  142. /(float)info_ptr->x_pixels_per_unit));
  143. }
  144. #endif
  145. return ((float)0.0);
  146. }
  147. #endif
  148. #ifdef PNG_FIXED_POINT_SUPPORTED
  149. png_fixed_point PNGAPI
  150. png_get_pixel_aspect_ratio_fixed(png_const_structp png_ptr,
  151. png_const_infop info_ptr)
  152. {
  153. #ifdef PNG_READ_pHYs_SUPPORTED
  154. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs)
  155. && info_ptr->x_pixels_per_unit > 0 && info_ptr->y_pixels_per_unit > 0
  156. && info_ptr->x_pixels_per_unit <= PNG_UINT_31_MAX
  157. && info_ptr->y_pixels_per_unit <= PNG_UINT_31_MAX)
  158. {
  159. png_fixed_point res;
  160. png_debug1(1, "in %s retrieval function", "png_get_aspect_ratio_fixed");
  161. /* The following casts work because a PNG 4 byte integer only has a valid
  162. * range of 0..2^31-1; otherwise the cast might overflow.
  163. */
  164. if (png_muldiv(&res, (png_int_32)info_ptr->y_pixels_per_unit, PNG_FP_1,
  165. (png_int_32)info_ptr->x_pixels_per_unit))
  166. return res;
  167. }
  168. #endif
  169. return 0;
  170. }
  171. #endif
  172. png_int_32 PNGAPI
  173. png_get_x_offset_microns(png_const_structp png_ptr, png_const_infop info_ptr)
  174. {
  175. #ifdef PNG_oFFs_SUPPORTED
  176. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_oFFs))
  177. {
  178. png_debug1(1, "in %s retrieval function", "png_get_x_offset_microns");
  179. if (info_ptr->offset_unit_type == PNG_OFFSET_MICROMETER)
  180. return (info_ptr->x_offset);
  181. }
  182. #endif
  183. return (0);
  184. }
  185. png_int_32 PNGAPI
  186. png_get_y_offset_microns(png_const_structp png_ptr, png_const_infop info_ptr)
  187. {
  188. #ifdef PNG_oFFs_SUPPORTED
  189. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_oFFs))
  190. {
  191. png_debug1(1, "in %s retrieval function", "png_get_y_offset_microns");
  192. if (info_ptr->offset_unit_type == PNG_OFFSET_MICROMETER)
  193. return (info_ptr->y_offset);
  194. }
  195. #endif
  196. return (0);
  197. }
  198. png_int_32 PNGAPI
  199. png_get_x_offset_pixels(png_const_structp png_ptr, png_const_infop info_ptr)
  200. {
  201. #ifdef PNG_oFFs_SUPPORTED
  202. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_oFFs))
  203. {
  204. png_debug1(1, "in %s retrieval function", "png_get_x_offset_pixels");
  205. if (info_ptr->offset_unit_type == PNG_OFFSET_PIXEL)
  206. return (info_ptr->x_offset);
  207. }
  208. #endif
  209. return (0);
  210. }
  211. png_int_32 PNGAPI
  212. png_get_y_offset_pixels(png_const_structp png_ptr, png_const_infop info_ptr)
  213. {
  214. #ifdef PNG_oFFs_SUPPORTED
  215. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_oFFs))
  216. {
  217. png_debug1(1, "in %s retrieval function", "png_get_y_offset_pixels");
  218. if (info_ptr->offset_unit_type == PNG_OFFSET_PIXEL)
  219. return (info_ptr->y_offset);
  220. }
  221. #endif
  222. return (0);
  223. }
  224. #ifdef PNG_INCH_CONVERSIONS_SUPPORTED
  225. static png_uint_32
  226. ppi_from_ppm(png_uint_32 ppm)
  227. {
  228. #if 0
  229. /* The conversion is *(2.54/100), in binary (32 digits):
  230. * .00000110100000001001110101001001
  231. */
  232. png_uint_32 t1001, t1101;
  233. ppm >>= 1; /* .1 */
  234. t1001 = ppm + (ppm >> 3); /* .1001 */
  235. t1101 = t1001 + (ppm >> 1); /* .1101 */
  236. ppm >>= 20; /* .000000000000000000001 */
  237. t1101 += t1101 >> 15; /* .1101000000000001101 */
  238. t1001 >>= 11; /* .000000000001001 */
  239. t1001 += t1001 >> 12; /* .000000000001001000000001001 */
  240. ppm += t1001; /* .000000000001001000001001001 */
  241. ppm += t1101; /* .110100000001001110101001001 */
  242. return (ppm + 16) >> 5;/* .00000110100000001001110101001001 */
  243. #else
  244. /* The argument is a PNG unsigned integer, so it is not permitted
  245. * to be bigger than 2^31.
  246. */
  247. png_fixed_point result;
  248. if (ppm <= PNG_UINT_31_MAX && png_muldiv(&result, (png_int_32)ppm, 127,
  249. 5000))
  250. return result;
  251. /* Overflow. */
  252. return 0;
  253. #endif
  254. }
  255. png_uint_32 PNGAPI
  256. png_get_pixels_per_inch(png_const_structp png_ptr, png_const_infop info_ptr)
  257. {
  258. return ppi_from_ppm(png_get_pixels_per_meter(png_ptr, info_ptr));
  259. }
  260. png_uint_32 PNGAPI
  261. png_get_x_pixels_per_inch(png_const_structp png_ptr, png_const_infop info_ptr)
  262. {
  263. return ppi_from_ppm(png_get_x_pixels_per_meter(png_ptr, info_ptr));
  264. }
  265. png_uint_32 PNGAPI
  266. png_get_y_pixels_per_inch(png_const_structp png_ptr, png_const_infop info_ptr)
  267. {
  268. return ppi_from_ppm(png_get_y_pixels_per_meter(png_ptr, info_ptr));
  269. }
  270. #ifdef PNG_FIXED_POINT_SUPPORTED
  271. static png_fixed_point
  272. png_fixed_inches_from_microns(png_structp png_ptr, png_int_32 microns)
  273. {
  274. /* Convert from metres * 1,000,000 to inches * 100,000, meters to
  275. * inches is simply *(100/2.54), so we want *(10/2.54) == 500/127.
  276. * Notice that this can overflow - a warning is output and 0 is
  277. * returned.
  278. */
  279. return png_muldiv_warn(png_ptr, microns, 500, 127);
  280. }
  281. png_fixed_point PNGAPI
  282. png_get_x_offset_inches_fixed(png_structp png_ptr,
  283. png_const_infop info_ptr)
  284. {
  285. return png_fixed_inches_from_microns(png_ptr,
  286. png_get_x_offset_microns(png_ptr, info_ptr));
  287. }
  288. #endif
  289. #ifdef PNG_FIXED_POINT_SUPPORTED
  290. png_fixed_point PNGAPI
  291. png_get_y_offset_inches_fixed(png_structp png_ptr,
  292. png_const_infop info_ptr)
  293. {
  294. return png_fixed_inches_from_microns(png_ptr,
  295. png_get_y_offset_microns(png_ptr, info_ptr));
  296. }
  297. #endif
  298. #ifdef PNG_FLOATING_POINT_SUPPORTED
  299. float PNGAPI
  300. png_get_x_offset_inches(png_const_structp png_ptr, png_const_infop info_ptr)
  301. {
  302. /* To avoid the overflow do the conversion directly in floating
  303. * point.
  304. */
  305. return (float)(png_get_x_offset_microns(png_ptr, info_ptr) * .00003937);
  306. }
  307. #endif
  308. #ifdef PNG_FLOATING_POINT_SUPPORTED
  309. float PNGAPI
  310. png_get_y_offset_inches(png_const_structp png_ptr, png_const_infop info_ptr)
  311. {
  312. /* To avoid the overflow do the conversion directly in floating
  313. * point.
  314. */
  315. return (float)(png_get_y_offset_microns(png_ptr, info_ptr) * .00003937);
  316. }
  317. #endif
  318. #ifdef PNG_pHYs_SUPPORTED
  319. png_uint_32 PNGAPI
  320. png_get_pHYs_dpi(png_const_structp png_ptr, png_const_infop info_ptr,
  321. png_uint_32 *res_x, png_uint_32 *res_y, int *unit_type)
  322. {
  323. png_uint_32 retval = 0;
  324. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pHYs))
  325. {
  326. png_debug1(1, "in %s retrieval function", "pHYs");
  327. if (res_x != NULL)
  328. {
  329. *res_x = info_ptr->x_pixels_per_unit;
  330. retval |= PNG_INFO_pHYs;
  331. }
  332. if (res_y != NULL)
  333. {
  334. *res_y = info_ptr->y_pixels_per_unit;
  335. retval |= PNG_INFO_pHYs;
  336. }
  337. if (unit_type != NULL)
  338. {
  339. *unit_type = (int)info_ptr->phys_unit_type;
  340. retval |= PNG_INFO_pHYs;
  341. if (*unit_type == 1)
  342. {
  343. if (res_x != NULL) *res_x = (png_uint_32)(*res_x * .0254 + .50);
  344. if (res_y != NULL) *res_y = (png_uint_32)(*res_y * .0254 + .50);
  345. }
  346. }
  347. }
  348. return (retval);
  349. }
  350. #endif /* PNG_pHYs_SUPPORTED */
  351. #endif /* PNG_INCH_CONVERSIONS_SUPPORTED */
  352. /* png_get_channels really belongs in here, too, but it's been around longer */
  353. #endif /* PNG_EASY_ACCESS_SUPPORTED */
  354. png_byte PNGAPI
  355. png_get_channels(png_const_structp png_ptr, png_const_infop info_ptr)
  356. {
  357. if (png_ptr != NULL && info_ptr != NULL)
  358. return(info_ptr->channels);
  359. return (0);
  360. }
  361. png_const_bytep PNGAPI
  362. png_get_signature(png_const_structp png_ptr, png_infop info_ptr)
  363. {
  364. if (png_ptr != NULL && info_ptr != NULL)
  365. return(info_ptr->signature);
  366. return (NULL);
  367. }
  368. #ifdef PNG_bKGD_SUPPORTED
  369. png_uint_32 PNGAPI
  370. png_get_bKGD(png_const_structp png_ptr, png_infop info_ptr,
  371. png_color_16p *background)
  372. {
  373. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_bKGD)
  374. && background != NULL)
  375. {
  376. png_debug1(1, "in %s retrieval function", "bKGD");
  377. *background = &(info_ptr->background);
  378. return (PNG_INFO_bKGD);
  379. }
  380. return (0);
  381. }
  382. #endif
  383. #ifdef PNG_cHRM_SUPPORTED
  384. /* The XYZ APIs were added in 1.5.5 to take advantage of the code added at the
  385. * same time to correct the rgb grayscale coefficient defaults obtained from the
  386. * cHRM chunk in 1.5.4
  387. */
  388. png_uint_32 PNGFAPI
  389. png_get_cHRM_XYZ_fixed(png_structp png_ptr, png_const_infop info_ptr,
  390. png_fixed_point *int_red_X, png_fixed_point *int_red_Y,
  391. png_fixed_point *int_red_Z, png_fixed_point *int_green_X,
  392. png_fixed_point *int_green_Y, png_fixed_point *int_green_Z,
  393. png_fixed_point *int_blue_X, png_fixed_point *int_blue_Y,
  394. png_fixed_point *int_blue_Z)
  395. {
  396. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_cHRM))
  397. {
  398. png_xy xy;
  399. png_XYZ XYZ;
  400. png_debug1(1, "in %s retrieval function", "cHRM_XYZ");
  401. xy.whitex = info_ptr->x_white;
  402. xy.whitey = info_ptr->y_white;
  403. xy.redx = info_ptr->x_red;
  404. xy.redy = info_ptr->y_red;
  405. xy.greenx = info_ptr->x_green;
  406. xy.greeny = info_ptr->y_green;
  407. xy.bluex = info_ptr->x_blue;
  408. xy.bluey = info_ptr->y_blue;
  409. /* The *_checked function handles error reporting, so just return 0 if
  410. * there is a failure here.
  411. */
  412. if (png_XYZ_from_xy_checked(png_ptr, &XYZ, xy))
  413. {
  414. if (int_red_X != NULL)
  415. *int_red_X = XYZ.redX;
  416. if (int_red_Y != NULL)
  417. *int_red_Y = XYZ.redY;
  418. if (int_red_Z != NULL)
  419. *int_red_Z = XYZ.redZ;
  420. if (int_green_X != NULL)
  421. *int_green_X = XYZ.greenX;
  422. if (int_green_Y != NULL)
  423. *int_green_Y = XYZ.greenY;
  424. if (int_green_Z != NULL)
  425. *int_green_Z = XYZ.greenZ;
  426. if (int_blue_X != NULL)
  427. *int_blue_X = XYZ.blueX;
  428. if (int_blue_Y != NULL)
  429. *int_blue_Y = XYZ.blueY;
  430. if (int_blue_Z != NULL)
  431. *int_blue_Z = XYZ.blueZ;
  432. return (PNG_INFO_cHRM);
  433. }
  434. }
  435. return (0);
  436. }
  437. # ifdef PNG_FLOATING_POINT_SUPPORTED
  438. png_uint_32 PNGAPI
  439. png_get_cHRM(png_const_structp png_ptr, png_const_infop info_ptr,
  440. double *white_x, double *white_y, double *red_x, double *red_y,
  441. double *green_x, double *green_y, double *blue_x, double *blue_y)
  442. {
  443. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_cHRM))
  444. {
  445. png_debug1(1, "in %s retrieval function", "cHRM");
  446. if (white_x != NULL)
  447. *white_x = png_float(png_ptr, info_ptr->x_white, "cHRM white X");
  448. if (white_y != NULL)
  449. *white_y = png_float(png_ptr, info_ptr->y_white, "cHRM white Y");
  450. if (red_x != NULL)
  451. *red_x = png_float(png_ptr, info_ptr->x_red, "cHRM red X");
  452. if (red_y != NULL)
  453. *red_y = png_float(png_ptr, info_ptr->y_red, "cHRM red Y");
  454. if (green_x != NULL)
  455. *green_x = png_float(png_ptr, info_ptr->x_green, "cHRM green X");
  456. if (green_y != NULL)
  457. *green_y = png_float(png_ptr, info_ptr->y_green, "cHRM green Y");
  458. if (blue_x != NULL)
  459. *blue_x = png_float(png_ptr, info_ptr->x_blue, "cHRM blue X");
  460. if (blue_y != NULL)
  461. *blue_y = png_float(png_ptr, info_ptr->y_blue, "cHRM blue Y");
  462. return (PNG_INFO_cHRM);
  463. }
  464. return (0);
  465. }
  466. png_uint_32 PNGAPI
  467. png_get_cHRM_XYZ(png_structp png_ptr, png_const_infop info_ptr,
  468. double *red_X, double *red_Y, double *red_Z, double *green_X,
  469. double *green_Y, double *green_Z, double *blue_X, double *blue_Y,
  470. double *blue_Z)
  471. {
  472. png_XYZ XYZ;
  473. if (png_get_cHRM_XYZ_fixed(png_ptr, info_ptr,
  474. &XYZ.redX, &XYZ.redY, &XYZ.redZ, &XYZ.greenX, &XYZ.greenY, &XYZ.greenZ,
  475. &XYZ.blueX, &XYZ.blueY, &XYZ.blueZ) & PNG_INFO_cHRM)
  476. {
  477. if (red_X != NULL)
  478. *red_X = png_float(png_ptr, XYZ.redX, "cHRM red X");
  479. if (red_Y != NULL)
  480. *red_Y = png_float(png_ptr, XYZ.redY, "cHRM red Y");
  481. if (red_Z != NULL)
  482. *red_Z = png_float(png_ptr, XYZ.redZ, "cHRM red Z");
  483. if (green_X != NULL)
  484. *green_X = png_float(png_ptr, XYZ.greenX, "cHRM green X");
  485. if (green_Y != NULL)
  486. *green_Y = png_float(png_ptr, XYZ.greenY, "cHRM green Y");
  487. if (green_Z != NULL)
  488. *green_Z = png_float(png_ptr, XYZ.greenZ, "cHRM green Z");
  489. if (blue_X != NULL)
  490. *blue_X = png_float(png_ptr, XYZ.blueX, "cHRM blue X");
  491. if (blue_Y != NULL)
  492. *blue_Y = png_float(png_ptr, XYZ.blueY, "cHRM blue Y");
  493. if (blue_Z != NULL)
  494. *blue_Z = png_float(png_ptr, XYZ.blueZ, "cHRM blue Z");
  495. return (PNG_INFO_cHRM);
  496. }
  497. return (0);
  498. }
  499. # endif
  500. # ifdef PNG_FIXED_POINT_SUPPORTED
  501. png_uint_32 PNGAPI
  502. png_get_cHRM_fixed(png_const_structp png_ptr, png_const_infop info_ptr,
  503. png_fixed_point *white_x, png_fixed_point *white_y, png_fixed_point *red_x,
  504. png_fixed_point *red_y, png_fixed_point *green_x, png_fixed_point *green_y,
  505. png_fixed_point *blue_x, png_fixed_point *blue_y)
  506. {
  507. png_debug1(1, "in %s retrieval function", "cHRM");
  508. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_cHRM))
  509. {
  510. if (white_x != NULL)
  511. *white_x = info_ptr->x_white;
  512. if (white_y != NULL)
  513. *white_y = info_ptr->y_white;
  514. if (red_x != NULL)
  515. *red_x = info_ptr->x_red;
  516. if (red_y != NULL)
  517. *red_y = info_ptr->y_red;
  518. if (green_x != NULL)
  519. *green_x = info_ptr->x_green;
  520. if (green_y != NULL)
  521. *green_y = info_ptr->y_green;
  522. if (blue_x != NULL)
  523. *blue_x = info_ptr->x_blue;
  524. if (blue_y != NULL)
  525. *blue_y = info_ptr->y_blue;
  526. return (PNG_INFO_cHRM);
  527. }
  528. return (0);
  529. }
  530. # endif
  531. #endif
  532. #ifdef PNG_gAMA_SUPPORTED
  533. png_uint_32 PNGFAPI
  534. png_get_gAMA_fixed(png_const_structp png_ptr, png_const_infop info_ptr,
  535. png_fixed_point *file_gamma)
  536. {
  537. png_debug1(1, "in %s retrieval function", "gAMA");
  538. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_gAMA)
  539. && file_gamma != NULL)
  540. {
  541. *file_gamma = info_ptr->gamma;
  542. return (PNG_INFO_gAMA);
  543. }
  544. return (0);
  545. }
  546. # ifdef PNG_FLOATING_POINT_SUPPORTED
  547. png_uint_32 PNGAPI
  548. png_get_gAMA(png_const_structp png_ptr, png_const_infop info_ptr,
  549. double *file_gamma)
  550. {
  551. png_fixed_point igamma;
  552. png_uint_32 ok = png_get_gAMA_fixed(png_ptr, info_ptr, &igamma);
  553. if (ok)
  554. *file_gamma = png_float(png_ptr, igamma, "png_get_gAMA");
  555. return ok;
  556. }
  557. # endif
  558. #endif
  559. #ifdef PNG_sRGB_SUPPORTED
  560. png_uint_32 PNGAPI
  561. png_get_sRGB(png_const_structp png_ptr, png_const_infop info_ptr,
  562. int *file_srgb_intent)
  563. {
  564. png_debug1(1, "in %s retrieval function", "sRGB");
  565. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_sRGB)
  566. && file_srgb_intent != NULL)
  567. {
  568. *file_srgb_intent = (int)info_ptr->srgb_intent;
  569. return (PNG_INFO_sRGB);
  570. }
  571. return (0);
  572. }
  573. #endif
  574. #ifdef PNG_iCCP_SUPPORTED
  575. png_uint_32 PNGAPI
  576. png_get_iCCP(png_const_structp png_ptr, png_const_infop info_ptr,
  577. png_charpp name, int *compression_type,
  578. png_bytepp profile, png_uint_32 *proflen)
  579. {
  580. png_debug1(1, "in %s retrieval function", "iCCP");
  581. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_iCCP)
  582. && name != NULL && compression_type != NULL && profile != NULL &&
  583. proflen != NULL)
  584. {
  585. *name = info_ptr->iccp_name;
  586. *profile = info_ptr->iccp_profile;
  587. /* Compression_type is a dummy so the API won't have to change
  588. * if we introduce multiple compression types later.
  589. */
  590. *proflen = info_ptr->iccp_proflen;
  591. *compression_type = info_ptr->iccp_compression;
  592. return (PNG_INFO_iCCP);
  593. }
  594. return (0);
  595. }
  596. #endif
  597. #ifdef PNG_sPLT_SUPPORTED
  598. png_uint_32 PNGAPI
  599. png_get_sPLT(png_const_structp png_ptr, png_const_infop info_ptr,
  600. png_sPLT_tpp spalettes)
  601. {
  602. if (png_ptr != NULL && info_ptr != NULL && spalettes != NULL)
  603. {
  604. *spalettes = info_ptr->splt_palettes;
  605. return ((png_uint_32)info_ptr->splt_palettes_num);
  606. }
  607. return (0);
  608. }
  609. #endif
  610. #ifdef PNG_hIST_SUPPORTED
  611. png_uint_32 PNGAPI
  612. png_get_hIST(png_const_structp png_ptr, png_const_infop info_ptr,
  613. png_uint_16p *hist)
  614. {
  615. png_debug1(1, "in %s retrieval function", "hIST");
  616. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_hIST)
  617. && hist != NULL)
  618. {
  619. *hist = info_ptr->hist;
  620. return (PNG_INFO_hIST);
  621. }
  622. return (0);
  623. }
  624. #endif
  625. png_uint_32 PNGAPI
  626. png_get_IHDR(png_structp png_ptr, png_infop info_ptr,
  627. png_uint_32 *width, png_uint_32 *height, int *bit_depth,
  628. int *color_type, int *interlace_type, int *compression_type,
  629. int *filter_type)
  630. {
  631. png_debug1(1, "in %s retrieval function", "IHDR");
  632. if (png_ptr == NULL || info_ptr == NULL || width == NULL ||
  633. height == NULL || bit_depth == NULL || color_type == NULL)
  634. return (0);
  635. *width = info_ptr->width;
  636. *height = info_ptr->height;
  637. *bit_depth = info_ptr->bit_depth;
  638. *color_type = info_ptr->color_type;
  639. if (compression_type != NULL)
  640. *compression_type = info_ptr->compression_type;
  641. if (filter_type != NULL)
  642. *filter_type = info_ptr->filter_type;
  643. if (interlace_type != NULL)
  644. *interlace_type = info_ptr->interlace_type;
  645. /* This is redundant if we can be sure that the info_ptr values were all
  646. * assigned in png_set_IHDR(). We do the check anyhow in case an
  647. * application has ignored our advice not to mess with the members
  648. * of info_ptr directly.
  649. */
  650. png_check_IHDR (png_ptr, info_ptr->width, info_ptr->height,
  651. info_ptr->bit_depth, info_ptr->color_type, info_ptr->interlace_type,
  652. info_ptr->compression_type, info_ptr->filter_type);
  653. return (1);
  654. }
  655. #ifdef PNG_oFFs_SUPPORTED
  656. png_uint_32 PNGAPI
  657. png_get_oFFs(png_const_structp png_ptr, png_const_infop info_ptr,
  658. png_int_32 *offset_x, png_int_32 *offset_y, int *unit_type)
  659. {
  660. png_debug1(1, "in %s retrieval function", "oFFs");
  661. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_oFFs)
  662. && offset_x != NULL && offset_y != NULL && unit_type != NULL)
  663. {
  664. *offset_x = info_ptr->x_offset;
  665. *offset_y = info_ptr->y_offset;
  666. *unit_type = (int)info_ptr->offset_unit_type;
  667. return (PNG_INFO_oFFs);
  668. }
  669. return (0);
  670. }
  671. #endif
  672. #ifdef PNG_pCAL_SUPPORTED
  673. png_uint_32 PNGAPI
  674. png_get_pCAL(png_const_structp png_ptr, png_const_infop info_ptr,
  675. png_charp *purpose, png_int_32 *X0, png_int_32 *X1, int *type, int *nparams,
  676. png_charp *units, png_charpp *params)
  677. {
  678. png_debug1(1, "in %s retrieval function", "pCAL");
  679. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_pCAL)
  680. && purpose != NULL && X0 != NULL && X1 != NULL && type != NULL &&
  681. nparams != NULL && units != NULL && params != NULL)
  682. {
  683. *purpose = info_ptr->pcal_purpose;
  684. *X0 = info_ptr->pcal_X0;
  685. *X1 = info_ptr->pcal_X1;
  686. *type = (int)info_ptr->pcal_type;
  687. *nparams = (int)info_ptr->pcal_nparams;
  688. *units = info_ptr->pcal_units;
  689. *params = info_ptr->pcal_params;
  690. return (PNG_INFO_pCAL);
  691. }
  692. return (0);
  693. }
  694. #endif
  695. #ifdef PNG_sCAL_SUPPORTED
  696. # ifdef PNG_FIXED_POINT_SUPPORTED
  697. # ifdef PNG_FLOATING_ARITHMETIC_SUPPORTED
  698. png_uint_32 PNGAPI
  699. png_get_sCAL_fixed(png_structp png_ptr, png_const_infop info_ptr,
  700. int *unit, png_fixed_point *width, png_fixed_point *height)
  701. {
  702. if (png_ptr != NULL && info_ptr != NULL &&
  703. (info_ptr->valid & PNG_INFO_sCAL))
  704. {
  705. *unit = info_ptr->scal_unit;
  706. /*TODO: make this work without FP support */
  707. *width = png_fixed(png_ptr, atof(info_ptr->scal_s_width), "sCAL width");
  708. *height = png_fixed(png_ptr, atof(info_ptr->scal_s_height),
  709. "sCAL height");
  710. return (PNG_INFO_sCAL);
  711. }
  712. return(0);
  713. }
  714. # endif /* FLOATING_ARITHMETIC */
  715. # endif /* FIXED_POINT */
  716. # ifdef PNG_FLOATING_POINT_SUPPORTED
  717. png_uint_32 PNGAPI
  718. png_get_sCAL(png_const_structp png_ptr, png_const_infop info_ptr,
  719. int *unit, double *width, double *height)
  720. {
  721. if (png_ptr != NULL && info_ptr != NULL &&
  722. (info_ptr->valid & PNG_INFO_sCAL))
  723. {
  724. *unit = info_ptr->scal_unit;
  725. *width = atof(info_ptr->scal_s_width);
  726. *height = atof(info_ptr->scal_s_height);
  727. return (PNG_INFO_sCAL);
  728. }
  729. return(0);
  730. }
  731. # endif /* FLOATING POINT */
  732. png_uint_32 PNGAPI
  733. png_get_sCAL_s(png_const_structp png_ptr, png_const_infop info_ptr,
  734. int *unit, png_charpp width, png_charpp height)
  735. {
  736. if (png_ptr != NULL && info_ptr != NULL &&
  737. (info_ptr->valid & PNG_INFO_sCAL))
  738. {
  739. *unit = info_ptr->scal_unit;
  740. *width = info_ptr->scal_s_width;
  741. *height = info_ptr->scal_s_height;
  742. return (PNG_INFO_sCAL);
  743. }
  744. return(0);
  745. }
  746. #endif /* sCAL */
  747. #ifdef PNG_pHYs_SUPPORTED
  748. png_uint_32 PNGAPI
  749. png_get_pHYs(png_const_structp png_ptr, png_const_infop info_ptr,
  750. png_uint_32 *res_x, png_uint_32 *res_y, int *unit_type)
  751. {
  752. png_uint_32 retval = 0;
  753. png_debug1(1, "in %s retrieval function", "pHYs");
  754. if (png_ptr != NULL && info_ptr != NULL &&
  755. (info_ptr->valid & PNG_INFO_pHYs))
  756. {
  757. if (res_x != NULL)
  758. {
  759. *res_x = info_ptr->x_pixels_per_unit;
  760. retval |= PNG_INFO_pHYs;
  761. }
  762. if (res_y != NULL)
  763. {
  764. *res_y = info_ptr->y_pixels_per_unit;
  765. retval |= PNG_INFO_pHYs;
  766. }
  767. if (unit_type != NULL)
  768. {
  769. *unit_type = (int)info_ptr->phys_unit_type;
  770. retval |= PNG_INFO_pHYs;
  771. }
  772. }
  773. return (retval);
  774. }
  775. #endif /* pHYs */
  776. png_uint_32 PNGAPI
  777. png_get_PLTE(png_const_structp png_ptr, png_const_infop info_ptr,
  778. png_colorp *palette, int *num_palette)
  779. {
  780. png_debug1(1, "in %s retrieval function", "PLTE");
  781. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_PLTE)
  782. && palette != NULL)
  783. {
  784. *palette = info_ptr->palette;
  785. *num_palette = info_ptr->num_palette;
  786. png_debug1(3, "num_palette = %d", *num_palette);
  787. return (PNG_INFO_PLTE);
  788. }
  789. return (0);
  790. }
  791. #ifdef PNG_sBIT_SUPPORTED
  792. png_uint_32 PNGAPI
  793. png_get_sBIT(png_const_structp png_ptr, png_infop info_ptr,
  794. png_color_8p *sig_bit)
  795. {
  796. png_debug1(1, "in %s retrieval function", "sBIT");
  797. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_sBIT)
  798. && sig_bit != NULL)
  799. {
  800. *sig_bit = &(info_ptr->sig_bit);
  801. return (PNG_INFO_sBIT);
  802. }
  803. return (0);
  804. }
  805. #endif
  806. #ifdef PNG_TEXT_SUPPORTED
  807. png_uint_32 PNGAPI
  808. png_get_text(png_const_structp png_ptr, png_const_infop info_ptr,
  809. png_textp *text_ptr, int *num_text)
  810. {
  811. if (png_ptr != NULL && info_ptr != NULL && info_ptr->num_text > 0)
  812. {
  813. png_debug1(1, "in 0x%lx retrieval function",
  814. (unsigned long)png_ptr->chunk_name);
  815. if (text_ptr != NULL)
  816. *text_ptr = info_ptr->text;
  817. if (num_text != NULL)
  818. *num_text = info_ptr->num_text;
  819. return ((png_uint_32)info_ptr->num_text);
  820. }
  821. if (num_text != NULL)
  822. *num_text = 0;
  823. return(0);
  824. }
  825. #endif
  826. #ifdef PNG_tIME_SUPPORTED
  827. png_uint_32 PNGAPI
  828. png_get_tIME(png_const_structp png_ptr, png_infop info_ptr, png_timep *mod_time)
  829. {
  830. png_debug1(1, "in %s retrieval function", "tIME");
  831. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_tIME)
  832. && mod_time != NULL)
  833. {
  834. *mod_time = &(info_ptr->mod_time);
  835. return (PNG_INFO_tIME);
  836. }
  837. return (0);
  838. }
  839. #endif
  840. #ifdef PNG_tRNS_SUPPORTED
  841. png_uint_32 PNGAPI
  842. png_get_tRNS(png_const_structp png_ptr, png_infop info_ptr,
  843. png_bytep *trans_alpha, int *num_trans, png_color_16p *trans_color)
  844. {
  845. png_uint_32 retval = 0;
  846. if (png_ptr != NULL && info_ptr != NULL && (info_ptr->valid & PNG_INFO_tRNS))
  847. {
  848. png_debug1(1, "in %s retrieval function", "tRNS");
  849. if (info_ptr->color_type == PNG_COLOR_TYPE_PALETTE)
  850. {
  851. if (trans_alpha != NULL)
  852. {
  853. *trans_alpha = info_ptr->trans_alpha;
  854. retval |= PNG_INFO_tRNS;
  855. }
  856. if (trans_color != NULL)
  857. *trans_color = &(info_ptr->trans_color);
  858. }
  859. else /* if (info_ptr->color_type != PNG_COLOR_TYPE_PALETTE) */
  860. {
  861. if (trans_color != NULL)
  862. {
  863. *trans_color = &(info_ptr->trans_color);
  864. retval |= PNG_INFO_tRNS;
  865. }
  866. if (trans_alpha != NULL)
  867. *trans_alpha = NULL;
  868. }
  869. if (num_trans != NULL)
  870. {
  871. *num_trans = info_ptr->num_trans;
  872. retval |= PNG_INFO_tRNS;
  873. }
  874. }
  875. return (retval);
  876. }
  877. #endif
  878. #ifdef PNG_UNKNOWN_CHUNKS_SUPPORTED
  879. int PNGAPI
  880. png_get_unknown_chunks(png_const_structp png_ptr, png_const_infop info_ptr,
  881. png_unknown_chunkpp unknowns)
  882. {
  883. if (png_ptr != NULL && info_ptr != NULL && unknowns != NULL)
  884. {
  885. *unknowns = info_ptr->unknown_chunks;
  886. return info_ptr->unknown_chunks_num;
  887. }
  888. return (0);
  889. }
  890. #endif
  891. #ifdef PNG_READ_RGB_TO_GRAY_SUPPORTED
  892. png_byte PNGAPI
  893. png_get_rgb_to_gray_status (png_const_structp png_ptr)
  894. {
  895. return (png_byte)(png_ptr ? png_ptr->rgb_to_gray_status : 0);
  896. }
  897. #endif
  898. #ifdef PNG_USER_CHUNKS_SUPPORTED
  899. png_voidp PNGAPI
  900. png_get_user_chunk_ptr(png_const_structp png_ptr)
  901. {
  902. return (png_ptr ? png_ptr->user_chunk_ptr : NULL);
  903. }
  904. #endif
  905. png_size_t PNGAPI
  906. png_get_compression_buffer_size(png_const_structp png_ptr)
  907. {
  908. return (png_ptr ? png_ptr->zbuf_size : 0);
  909. }
  910. #ifdef PNG_SET_USER_LIMITS_SUPPORTED
  911. /* These functions were added to libpng 1.2.6 and were enabled
  912. * by default in libpng-1.4.0 */
  913. png_uint_32 PNGAPI
  914. png_get_user_width_max (png_const_structp png_ptr)
  915. {
  916. return (png_ptr ? png_ptr->user_width_max : 0);
  917. }
  918. png_uint_32 PNGAPI
  919. png_get_user_height_max (png_const_structp png_ptr)
  920. {
  921. return (png_ptr ? png_ptr->user_height_max : 0);
  922. }
  923. /* This function was added to libpng 1.4.0 */
  924. png_uint_32 PNGAPI
  925. png_get_chunk_cache_max (png_const_structp png_ptr)
  926. {
  927. return (png_ptr ? png_ptr->user_chunk_cache_max : 0);
  928. }
  929. /* This function was added to libpng 1.4.1 */
  930. png_alloc_size_t PNGAPI
  931. png_get_chunk_malloc_max (png_const_structp png_ptr)
  932. {
  933. return (png_ptr ? png_ptr->user_chunk_malloc_max : 0);
  934. }
  935. #endif /* ?PNG_SET_USER_LIMITS_SUPPORTED */
  936. /* These functions were added to libpng 1.4.0 */
  937. #ifdef PNG_IO_STATE_SUPPORTED
  938. png_uint_32 PNGAPI
  939. png_get_io_state (png_structp png_ptr)
  940. {
  941. return png_ptr->io_state;
  942. }
  943. png_uint_32 PNGAPI
  944. png_get_io_chunk_type (png_const_structp png_ptr)
  945. {
  946. return png_ptr->chunk_name;
  947. }
  948. png_const_bytep PNGAPI
  949. png_get_io_chunk_name (png_structp png_ptr)
  950. {
  951. PNG_CSTRING_FROM_CHUNK(png_ptr->io_chunk_string, png_ptr->chunk_name);
  952. return png_ptr->io_chunk_string;
  953. }
  954. #endif /* ?PNG_IO_STATE_SUPPORTED */
  955. #endif /* PNG_READ_SUPPORTED || PNG_WRITE_SUPPORTED */