File indexing completed on 2025-01-05 03:57:08

0001 /* -*- C++ -*-
0002  * Copyright 2019-2021 LibRaw LLC (info@libraw.org)
0003  *
0004  LibRaw uses code from dcraw.c -- Dave Coffin's raw photo decoder,
0005  dcraw.c is copyright 1997-2018 by Dave Coffin, dcoffin a cybercom o net.
0006  LibRaw do not use RESTRICTED code from dcraw.c
0007 
0008  LibRaw is free software; you can redistribute it and/or modify
0009  it under the terms of the one of two licenses as you choose:
0010 
0011 1. GNU LESSER GENERAL PUBLIC LICENSE version 2.1
0012    (See file LICENSE.LGPL provided in LibRaw distribution archive for details).
0013 
0014 2. COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) Version 1.0
0015    (See file LICENSE.CDDL provided in LibRaw distribution archive for details).
0016 
0017  */
0018 
0019 #include "../../internal/dcraw_defs.h"
0020 
0021 ushort LibRaw::sget2Rev(uchar *s) // specific to some Canon Makernotes fields,
0022                                   // where they have endian in reverse
0023 {
0024   if (order == 0x4d4d) /* "II" means little-endian, and we reverse to "MM" - big
0025                           endian */
0026     return s[0] | s[1] << 8;
0027   else /* "MM" means big-endian... */
0028     return s[0] << 8 | s[1];
0029 }
0030 
0031 ushort libraw_sget2_static(short _order, uchar *s)
0032 {
0033     if (_order == 0x4949) /* "II" means little-endian */
0034         return s[0] | s[1] << 8;
0035     else /* "MM" means big-endian */
0036         return s[0] << 8 | s[1];
0037 }
0038 
0039 ushort LibRaw::sget2(uchar *s)
0040 {
0041     return libraw_sget2_static(order, s);
0042 }
0043 
0044 
0045 ushort LibRaw::get2()
0046 {
0047   uchar str[2] = {0xff, 0xff};
0048   fread(str, 1, 2, ifp);
0049   return sget2(str);
0050 }
0051 
0052 unsigned LibRaw::sget4(uchar *s)
0053 {
0054     return libraw_sget4_static(order, s);
0055 }
0056 
0057 
0058 unsigned libraw_sget4_static(short _order, uchar *s)
0059 {
0060   if (_order == 0x4949)
0061     return s[0] | s[1] << 8 | s[2] << 16 | s[3] << 24;
0062   else
0063     return s[0] << 24 | s[1] << 16 | s[2] << 8 | s[3];
0064 }
0065 
0066 unsigned LibRaw::get4()
0067 {
0068   uchar str[4] = {0xff, 0xff, 0xff, 0xff};
0069   fread(str, 1, 4, ifp);
0070   return sget4(str);
0071 }
0072 
0073 unsigned LibRaw::getint(int type) { return tagtypeIs(LIBRAW_EXIFTAG_TYPE_SHORT) ? get2() : get4(); }
0074 
0075 float libraw_int_to_float(int i)
0076 {
0077   union {
0078     int i;
0079     float f;
0080   } u;
0081   u.i = i;
0082   return u.f;
0083 }
0084 
0085 float LibRaw::int_to_float(int i) { return libraw_int_to_float(i); }
0086 
0087 double LibRaw::getreal(int type)
0088 {
0089   union {
0090     char c[8];
0091     double d;
0092   } u, v;
0093   int i, rev;
0094 
0095   switch (type)
0096   {
0097   case LIBRAW_EXIFTAG_TYPE_SHORT:
0098     return (unsigned short)get2();
0099   case LIBRAW_EXIFTAG_TYPE_LONG:
0100     return (unsigned int)get4();
0101   case LIBRAW_EXIFTAG_TYPE_RATIONAL: // (unsigned, unsigned)
0102     u.d = (unsigned int)get4();
0103     v.d = (unsigned int)get4();
0104     return u.d / (v.d ? v.d : 1);
0105   case LIBRAW_EXIFTAG_TYPE_SSHORT:
0106     return (signed short)get2();
0107   case LIBRAW_EXIFTAG_TYPE_SLONG:
0108     return (signed int)get4();
0109   case LIBRAW_EXIFTAG_TYPE_SRATIONAL: // (int, int)
0110     u.d = (signed int)get4();
0111     v.d = (signed int)get4();
0112     return u.d / (v.d ? v.d : 1);
0113   case LIBRAW_EXIFTAG_TYPE_FLOAT:
0114     return int_to_float(get4());
0115   case LIBRAW_EXIFTAG_TYPE_DOUBLE:
0116     rev = 7 * ((order == 0x4949) == (ntohs(0x1234) == 0x1234));
0117     for (i = 0; i < 8; i++)
0118       u.c[i ^ rev] = fgetc(ifp);
0119     return u.d;
0120   default:
0121     return fgetc(ifp);
0122   }
0123 }
0124 
0125 double LibRaw::sgetreal(int type, uchar *s)
0126 {
0127     return libraw_sgetreal_static(order, type, s);
0128 }
0129 
0130 
0131 double libraw_sgetreal_static(short _order, int type, uchar *s)
0132 {
0133   union {
0134     char c[8];
0135     double d;
0136   } u, v;
0137   int i, rev;
0138 
0139   switch (type)
0140   {
0141   case LIBRAW_EXIFTAG_TYPE_SHORT:
0142     return (unsigned short) libraw_sget2_static(_order,s);
0143   case LIBRAW_EXIFTAG_TYPE_LONG:
0144       return (unsigned int)libraw_sget4_static(_order, s);
0145   case LIBRAW_EXIFTAG_TYPE_RATIONAL: // (unsigned, unsigned)
0146     u.d = (unsigned int)libraw_sget4_static(_order,s);
0147     v.d = (unsigned int)libraw_sget4_static(_order,s+4);
0148     return u.d / (v.d ? v.d : 1);
0149   case LIBRAW_EXIFTAG_TYPE_SSHORT:
0150     return (signed short)libraw_sget2_static(_order,s);
0151   case LIBRAW_EXIFTAG_TYPE_SLONG:
0152     return (signed int) libraw_sget4_static(_order,s);
0153   case LIBRAW_EXIFTAG_TYPE_SRATIONAL: // (int, int)
0154     u.d = (signed int)libraw_sget4_static(_order,s);
0155     v.d = (signed int)libraw_sget4_static(_order,s+4);
0156     return u.d / (v.d ? v.d : 1);
0157   case LIBRAW_EXIFTAG_TYPE_FLOAT:
0158     return libraw_int_to_float(libraw_sget4_static(_order,s));
0159   case LIBRAW_EXIFTAG_TYPE_DOUBLE:
0160     rev = 7 * ((_order == 0x4949) == (ntohs(0x1234) == 0x1234));
0161     for (i = 0; i < 8; i++)
0162       u.c[i ^ rev] = *(s+1);
0163     return u.d;
0164   default:
0165     return *(s+1);
0166   }
0167 }
0168 
0169 
0170 void LibRaw::read_shorts(ushort *pixel, unsigned count)
0171 {
0172   if ((unsigned)fread(pixel, 2, count, ifp) < count)
0173     derror();
0174   if ((order == 0x4949) == (ntohs(0x1234) == 0x1234))
0175     libraw_swab(pixel, count * 2);
0176 }