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

0001 /* -*- C++ -*-
0002  * Copyright 2019-2021 LibRaw LLC (info@libraw.org)
0003  *
0004  LibRaw is free software; you can redistribute it and/or modify
0005  it under the terms of the one of two licenses as you choose:
0006 
0007 1. GNU LESSER GENERAL PUBLIC LICENSE version 2.1
0008    (See file LICENSE.LGPL provided in LibRaw distribution archive for details).
0009 
0010 2. COMMON DEVELOPMENT AND DISTRIBUTION LICENSE (CDDL) Version 1.0
0011    (See file LICENSE.CDDL provided in LibRaw distribution archive for details).
0012 
0013  */
0014 
0015 #include "../../internal/dcraw_defs.h"
0016 #include "../../internal/libraw_cameraids.h"
0017 
0018 static ushort saneSonyCameraInfo(uchar a, uchar b, uchar c, uchar d, uchar e,
0019                                  uchar f)
0020 {
0021   if ((a >> 4) > 9)
0022     return 0;
0023   else if ((a & 0x0f) > 9)
0024     return 0;
0025   else if ((b >> 4) > 9)
0026     return 0;
0027   else if ((b & 0x0f) > 9)
0028     return 0;
0029   else if ((c >> 4) > 9)
0030     return 0;
0031   else if ((c & 0x0f) > 9)
0032     return 0;
0033   else if ((d >> 4) > 9)
0034     return 0;
0035   else if ((d & 0x0f) > 9)
0036     return 0;
0037   else if ((e >> 4) > 9)
0038     return 0;
0039   else if ((e & 0x0f) > 9)
0040     return 0;
0041   else if ((f >> 4) > 9)
0042     return 0;
0043   else if ((f & 0x0f) > 9)
0044     return 0;
0045   return 1;
0046 }
0047 static float my_roundf(float x)
0048 {
0049   float t;
0050   if (x >= 0.0)
0051   {
0052     t = ceilf(x);
0053     if (t - x > 0.5)
0054       t -= 1.0;
0055     return t;
0056   }
0057   else
0058   {
0059     t = ceilf(-x);
0060     if (t + x > 0.5)
0061       t -= 1.0;
0062     return -t;
0063   }
0064 }
0065 
0066 static ushort bcd2dec(uchar data)
0067 {
0068   if ((data >> 4) > 9)
0069     return 0;
0070   else if ((data & 0x0f) > 9)
0071     return 0;
0072   else
0073     return (data >> 4) * 10 + (data & 0x0f);
0074 }
0075 
0076 static uchar SonySubstitution[257] =
0077     "\x00\x01\x32\xb1\x0a\x0e\x87\x28\x02\xcc\xca\xad\x1b\xdc\x08\xed\x64\x86"
0078     "\xf0\x4f\x8c\x6c\xb8\xcb\x69\xc4\x2c\x03"
0079     "\x97\xb6\x93\x7c\x14\xf3\xe2\x3e\x30\x8e\xd7\x60\x1c\xa1\xab\x37\xec\x75"
0080     "\xbe\x23\x15\x6a\x59\x3f\xd0\xb9\x96\xb5"
0081     "\x50\x27\x88\xe3\x81\x94\xe0\xc0\x04\x5c\xc6\xe8\x5f\x4b\x70\x38\x9f\x82"
0082     "\x80\x51\x2b\xc5\x45\x49\x9b\x21\x52\x53"
0083     "\x54\x85\x0b\x5d\x61\xda\x7b\x55\x26\x24\x07\x6e\x36\x5b\x47\xb7\xd9\x4a"
0084     "\xa2\xdf\xbf\x12\x25\xbc\x1e\x7f\x56\xea"
0085     "\x10\xe6\xcf\x67\x4d\x3c\x91\x83\xe1\x31\xb3\x6f\xf4\x05\x8a\x46\xc8\x18"
0086     "\x76\x68\xbd\xac\x92\x2a\x13\xe9\x0f\xa3"
0087     "\x7a\xdb\x3d\xd4\xe7\x3a\x1a\x57\xaf\x20\x42\xb2\x9e\xc3\x8b\xf2\xd5\xd3"
0088     "\xa4\x7e\x1f\x98\x9c\xee\x74\xa5\xa6\xa7"
0089     "\xd8\x5e\xb0\xb4\x34\xce\xa8\x79\x77\x5a\xc1\x89\xae\x9a\x11\x33\x9d\xf5"
0090     "\x39\x19\x65\x78\x16\x71\xd2\xa9\x44\x63"
0091     "\x40\x29\xba\xa0\x8f\xe4\xd6\x3b\x84\x0d\xc2\x4e\x58\xdd\x99\x22\x6b\xc9"
0092     "\xbb\x17\x06\xe5\x7d\x66\x43\x62\xf6\xcd"
0093     "\x35\x90\x2e\x41\x8d\x6d\xaa\x09\x73\x95\x0c\xf1\x1d\xde\x4c\x2f\x2d\xf7"
0094     "\xd1\x72\xeb\xef\x48\xc7\xf8\xf9\xfa\xfb"
0095     "\xfc\xfd\xfe\xff";
0096 
0097 void LibRaw::sony_decrypt(unsigned *data, int len, int start, int key)
0098 {
0099 #ifndef LIBRAW_NOTHREADS
0100 #define pad tls->sony_decrypt.pad
0101 #define p tls->sony_decrypt.p
0102 #else
0103   static unsigned pad[128], p;
0104 #endif
0105   if (start)
0106   {
0107     for (p = 0; p < 4; p++)
0108       pad[p] = key = key * 48828125ULL + 1;
0109     pad[3] = pad[3] << 1 | (pad[0] ^ pad[2]) >> 31;
0110     for (p = 4; p < 127; p++)
0111       pad[p] = (pad[p - 4] ^ pad[p - 2]) << 1 | (pad[p - 3] ^ pad[p - 1]) >> 31;
0112     for (p = 0; p < 127; p++)
0113       pad[p] = htonl(pad[p]);
0114   }
0115   while (len--)
0116   {
0117     *data++ ^= pad[p & 127] = pad[(p + 1) & 127] ^ pad[(p + 65) & 127];
0118     p++;
0119   }
0120 #ifndef LIBRAW_NOTHREADS
0121 #undef pad
0122 #undef p
0123 #endif
0124 }
0125 void LibRaw::setSonyBodyFeatures(unsigned long long id)
0126 {
0127   static const struct
0128   {
0129     ushort scf[11];
0130     /*
0131     scf[0]  camera id
0132     scf[1]  camera format
0133     scf[2]  camera mount: Minolta A, Sony E, fixed,
0134     scf[3]  camera type: DSLR, NEX, SLT, ILCE, ILCA, DSC
0135     scf[4]  lens mount, LIBRAW_MOUNT_FixedLens or LIBRAW_MOUNT_Unknown
0136     scf[5]  tag 0x2010 group (0 if not used)
0137     scf[6]  offset of Sony ISO in 0x2010 table, 0xffff if not valid
0138     scf[7]  offset of ShutterCount3 in 0x9050 table, 0xffff if not valid
0139     scf[8]  offset of MeteringMode in 0x2010 table, 0xffff if not valid
0140     scf[9]  offset of ExposureProgram in 0x2010 table, 0xffff if not valid
0141     scf[10] offset of ReleaseMode2 in 0x2010 table, 0xffff if not valid
0142     */
0143   } SonyCamFeatures[] = {
0144       {SonyID_DSLR_A100, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0145        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0146       {SonyID_DSLR_A900, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0147        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0148       {SonyID_DSLR_A700, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0149        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0150       {SonyID_DSLR_A200, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0151        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0152       {SonyID_DSLR_A350, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0153        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0154       {SonyID_DSLR_A300, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0155        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0156       {SonyID_DSLR_A900, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0157        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0158       {SonyID_DSLR_A380, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0159        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0160       {SonyID_DSLR_A330, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0161        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0162       {SonyID_DSLR_A230, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0163        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0164       {SonyID_DSLR_A290, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0165        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0166       {SonyID_DSLR_A850, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0167        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0168       {SonyID_DSLR_A850, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0169        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0170       {SonyID_DSLR_A550, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0171        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0172       {SonyID_DSLR_A500, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0173        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0174       {SonyID_DSLR_A450, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0175        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0176       {SonyID_NEX_5, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0177        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0178       {SonyID_NEX_3, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0179        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0180       {SonyID_SLT_A33, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0181        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0182       {SonyID_SLT_A55, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0183        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0184       {SonyID_DSLR_A560, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0185        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0186       {SonyID_DSLR_A580, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_DSLR, LIBRAW_MOUNT_Unknown,
0187        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0188       {SonyID_NEX_C3, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0189        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0190       {SonyID_SLT_A35, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0191        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0192       {SonyID_SLT_A65, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0193        LIBRAW_SONY_Tag2010b, 0x1218, 0x01bd, 0x1178, 0x1179, 0x112c},
0194       {SonyID_SLT_A77, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0195        LIBRAW_SONY_Tag2010b, 0x1218, 0x01bd, 0x1178, 0x1179, 0x112c},
0196       {SonyID_NEX_5N, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0197        LIBRAW_SONY_Tag2010a, 0x113e, 0x01bd, 0x1174, 0x1175, 0x112c},
0198       {SonyID_NEX_7, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0199        LIBRAW_SONY_Tag2010b, 0x1218, 0x01bd, 0x1178, 0x1179, 0x112c},
0200       {SonyID_NEX_VG20, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0201        LIBRAW_SONY_Tag2010b, 0x1218, 0x01bd, 0x1178, 0x1179, 0x112c},
0202       {SonyID_SLT_A37, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0203        LIBRAW_SONY_Tag2010c, 0x11f4, 0x01bd, 0x1154, 0x1155, 0x1108},
0204       {SonyID_SLT_A57, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0205        LIBRAW_SONY_Tag2010c, 0x11f4, 0x01bd, 0x1154, 0x1155, 0x1108},
0206       {SonyID_NEX_F3, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0207        LIBRAW_SONY_Tag2010c, 0x11f4, 0x01bd, 0x1154, 0x1155, 0x1108},
0208       {SonyID_SLT_A99, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0209        LIBRAW_SONY_Tag2010e, 0x1254, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0210       {SonyID_NEX_6, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0211        LIBRAW_SONY_Tag2010e, 0x1254, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0212       {SonyID_NEX_5R, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0213        LIBRAW_SONY_Tag2010e, 0x1254, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0214       {SonyID_DSC_RX100, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0215        LIBRAW_SONY_Tag2010e, 0x1254, 0xffff, 0x11ac, 0x11ad, 0x1160},
0216       {SonyID_DSC_RX1, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0217        LIBRAW_SONY_Tag2010e, 0x1258, 0xffff, 0x11ac, 0x11ad, 0x1160},
0218       {SonyID_NEX_VG900, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0219        LIBRAW_SONY_Tag2010e, 0x1254, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0220       {SonyID_NEX_VG30, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0221        LIBRAW_SONY_Tag2010e, 0x1254, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0222       {SonyID_ILCE_3000, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0223        LIBRAW_SONY_Tag2010e, 0x1280, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0224       {SonyID_SLT_A58, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_SLT, LIBRAW_MOUNT_Unknown,
0225        LIBRAW_SONY_Tag2010e, 0x1280, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0226       {SonyID_NEX_3N, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0227        LIBRAW_SONY_Tag2010e, 0x1280, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0228       {SonyID_ILCE_7, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0229        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0230       {SonyID_NEX_5T, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_NEX, LIBRAW_MOUNT_Unknown,
0231        LIBRAW_SONY_Tag2010e, 0x1254, 0x01aa, 0x11ac, 0x11ad, 0x1160},
0232       {SonyID_DSC_RX100M2, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0233        LIBRAW_SONY_Tag2010f, 0x113c, 0xffff, 0x1064, 0x1065, 0x1018},
0234       {SonyID_DSC_RX10, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0235        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0236       {SonyID_DSC_RX1R, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0237        LIBRAW_SONY_Tag2010e, 0x1258, 0xffff, 0x11ac, 0x11ad, 0x1160},
0238       {SonyID_ILCE_7R, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0239        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0240       {SonyID_ILCE_6000, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0241        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0242       {SonyID_ILCE_5000, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0243        LIBRAW_SONY_Tag2010g, 0x0344, 0x01aa, 0x025c, 0x025d, 0x0210},
0244       {SonyID_DSC_RX100M3, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0245        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0246       {SonyID_ILCE_7S, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0247        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0248       {SonyID_ILCA_77M2, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_ILCA, LIBRAW_MOUNT_Unknown,
0249        LIBRAW_SONY_Tag2010g, 0x0344, 0x01a0, 0x025c, 0x025d, 0x0210},
0250       {SonyID_ILCE_5100, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0251        LIBRAW_SONY_Tag2010g, 0x0344, 0x01a0, 0x025c, 0x025d, 0x0210},
0252       {SonyID_ILCE_7M2, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0253        LIBRAW_SONY_Tag2010g, 0x0344, 0xffff, 0x025c, 0x025d, 0x0210},
0254       {SonyID_DSC_RX100M4, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0255        LIBRAW_SONY_Tag2010h, 0x0346, 0xffff, 0x025c, 0x025d, 0x0210},
0256       {SonyID_DSC_RX10M2, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0257        LIBRAW_SONY_Tag2010h, 0x0346, 0xffff, 0x025c, 0x025d, 0x0210},
0258       {SonyID_DSC_RX1RM2, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0259        LIBRAW_SONY_Tag2010h, 0x0346, 0xffff, 0x025c, 0x025d, 0x0210},
0260       {SonyID_ILCE_QX1, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0261        LIBRAW_SONY_Tag2010g, 0x0344, 0x01a0, 0x025c, 0x025d, 0x0210},
0262       {SonyID_ILCE_7RM2, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0263        LIBRAW_SONY_Tag2010h, 0x0346, 0x01cb, 0x025c, 0x025d, 0x0210},
0264       {SonyID_ILCE_7SM2, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0265        LIBRAW_SONY_Tag2010h, 0x0346, 0x01cb, 0x025c, 0x025d, 0x0210},
0266       {SonyID_ILCA_68, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_ILCA, LIBRAW_MOUNT_Unknown,
0267        LIBRAW_SONY_Tag2010g, 0x0344, 0x01a0, 0x025c, 0x025d, 0x0210},
0268       {SonyID_ILCA_99M2, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Minolta_A, LIBRAW_SONY_ILCA, LIBRAW_MOUNT_Unknown,
0269        LIBRAW_SONY_Tag2010h, 0x0346, 0x01cd, 0x025c, 0x025d, 0x0210},
0270       {SonyID_DSC_RX10M3, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0271        LIBRAW_SONY_Tag2010h, 0x0346, 0xffff, 0x025c, 0x025d, 0x0210},
0272       {SonyID_DSC_RX100M5, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0273        LIBRAW_SONY_Tag2010h, 0x0346, 0xffff, 0x025c, 0x025d, 0x0210},
0274       {SonyID_ILCE_6300, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0275        LIBRAW_SONY_Tag2010h, 0x0346, 0x01cd, 0x025c, 0x025d, 0x0210},
0276       {SonyID_ILCE_9, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0277        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0278       {SonyID_ILCE_6500, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0279        LIBRAW_SONY_Tag2010h, 0x0346, 0x01cd, 0x025c, 0x025d, 0x0210},
0280       {SonyID_ILCE_7RM3, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0281        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0282       {SonyID_ILCE_7M3, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0283        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0284       {SonyID_DSC_RX0, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0285        LIBRAW_SONY_Tag2010h, 0x0346, 0xffff, 0x025c, 0x025d, 0x0210},
0286       {SonyID_DSC_RX10M4, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0287        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0288       {SonyID_DSC_RX100M6, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0289        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0290       {SonyID_DSC_HX99, LIBRAW_FORMAT_1div2p3INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0291        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0292       {SonyID_DSC_RX100M5A, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0293        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0294       {SonyID_ILCE_6400, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0295        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0296       {SonyID_DSC_RX0M2, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0297        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0298       {SonyID_DSC_RX100M7, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0299        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0300       {SonyID_ILCE_7RM4, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0301        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0302       {SonyID_ILCE_9M2, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0303        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0304       {SonyID_ILCE_6600, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0305        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0306       {SonyID_ILCE_6100, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0307        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0308       {SonyID_ZV_1, LIBRAW_FORMAT_1INCH, LIBRAW_MOUNT_FixedLens, LIBRAW_SONY_DSC, LIBRAW_MOUNT_FixedLens,
0309        LIBRAW_SONY_Tag2010i, 0x0320, 0xffff, 0x024b, 0x024c, 0x0208},
0310       {SonyID_ILCE_7C, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0311        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0312 
0313 // a la SonyID_ILCE_6100
0314       {SonyID_ZV_E10, LIBRAW_FORMAT_APSC, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0315        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0316 
0317       {SonyID_ILCE_7SM3, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0318        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0319       {SonyID_ILCE_1, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0320        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0321       {SonyID_ILME_FX3, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0322        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0323       {SonyID_ILCE_7RM3A, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0324        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0325       {SonyID_ILCE_7RM4A, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0326        LIBRAW_SONY_Tag2010i, 0x0320, 0x019f, 0x024b, 0x024c, 0x0208},
0327       {SonyID_ILCE_7M4, LIBRAW_FORMAT_FF, LIBRAW_MOUNT_Sony_E, LIBRAW_SONY_ILCE, LIBRAW_MOUNT_Unknown,
0328        LIBRAW_SONY_Tag2010None, 0xffff, 0xffff, 0xffff, 0xffff, 0xffff},
0329   };
0330   ilm.CamID = id;
0331 
0332   if (id == SonyID_DSC_R1)
0333   {
0334     ilm.CameraMount = ilm.LensMount = LIBRAW_MOUNT_FixedLens;
0335     imSony.CameraType = LIBRAW_SONY_DSC;
0336     imSony.group2010 = LIBRAW_SONY_Tag2010None;
0337     imSony.group9050 = LIBRAW_SONY_Tag9050None;
0338     return;
0339   }
0340 
0341   for (unsigned i = 0; i < (sizeof SonyCamFeatures / sizeof *SonyCamFeatures); i++) {
0342     if (SonyCamFeatures[i].scf[0] == id) {
0343       ilm.CameraFormat = SonyCamFeatures[i].scf[1];
0344       ilm.CameraMount = SonyCamFeatures[i].scf[2];
0345       imSony.CameraType = SonyCamFeatures[i].scf[3];
0346       if (SonyCamFeatures[i].scf[4])
0347         ilm.LensMount = SonyCamFeatures[i].scf[4];
0348       imSony.group2010 = SonyCamFeatures[i].scf[5];
0349       imSony.real_iso_offset = SonyCamFeatures[i].scf[6];
0350       imSony.ImageCount3_offset = SonyCamFeatures[i].scf[7];
0351       imSony.MeteringMode_offset = SonyCamFeatures[i].scf[8];
0352       imSony.ExposureProgram_offset = SonyCamFeatures[i].scf[9];
0353       imSony.ReleaseMode2_offset = SonyCamFeatures[i].scf[10];
0354       break;
0355     }
0356   }
0357 
0358   switch (id) {
0359   case SonyID_ILCE_6100:
0360   case SonyID_ILCE_6300:
0361   case SonyID_ILCE_6400:
0362   case SonyID_ILCE_6500:
0363   case SonyID_ILCE_6600:
0364   case SonyID_ILCE_7C:
0365   case SonyID_ILCE_7M3:
0366   case SonyID_ILCE_7RM2:
0367   case SonyID_ILCE_7RM3A:
0368   case SonyID_ILCE_7RM3:
0369   case SonyID_ILCE_7RM4:
0370   case SonyID_ILCE_7RM4A:
0371   case SonyID_ILCE_7SM2:
0372   case SonyID_ILCE_9:
0373   case SonyID_ILCE_9M2:
0374   case SonyID_ILCA_99M2:
0375   case SonyID_ZV_E10:
0376     imSony.group9050 = LIBRAW_SONY_Tag9050b;
0377     break;
0378   case SonyID_ILCE_7SM3:
0379   case SonyID_ILCE_1:
0380   case SonyID_ILME_FX3:
0381   case SonyID_ILCE_7M4:
0382     imSony.group9050 = LIBRAW_SONY_Tag9050c;
0383     break;
0384   default:
0385     if ((imSony.CameraType != LIBRAW_SONY_DSC) &&
0386         (imSony.CameraType != LIBRAW_SONY_DSLR))
0387       imSony.group9050 = LIBRAW_SONY_Tag9050a;
0388     else
0389       imSony.group9050 = LIBRAW_SONY_Tag9050None;
0390     break;
0391   }
0392 
0393   char *sbstr = strstr(software, " v");
0394   if (sbstr != NULL)
0395   {
0396     sbstr += 2;
0397     strcpy(imCommon.firmware, sbstr);
0398     imSony.firmware = atof(sbstr);
0399 
0400     if ((id == SonyID_ILCE_7) ||
0401         (id == SonyID_ILCE_7R))
0402     {
0403       if (imSony.firmware < 1.2f)
0404         imSony.ImageCount3_offset = 0x01aa;
0405       else
0406         imSony.ImageCount3_offset = 0x01c0;
0407     }
0408     else if (id == SonyID_ILCE_6000)
0409     {
0410       if (imSony.firmware < 2.0f)
0411         imSony.ImageCount3_offset = 0x01aa;
0412       else
0413         imSony.ImageCount3_offset = 0x01c0;
0414     }
0415     else if ((id == SonyID_ILCE_7S) ||
0416              (id == SonyID_ILCE_7M2))
0417     {
0418       if (imSony.firmware < 1.2f)
0419         imSony.ImageCount3_offset = 0x01a0;
0420       else
0421         imSony.ImageCount3_offset = 0x01b6;
0422     }
0423   }
0424 
0425   if ((id == SonyID_ILCE_7SM3) &&
0426       !strcmp(model, "MODEL-NAME")) {
0427     imSony.group9050 = LIBRAW_SONY_Tag9050a;
0428   }
0429 
0430 }
0431 
0432 void LibRaw::parseSonyLensType2(uchar a, uchar b)
0433 {
0434   ushort lid2;
0435   lid2 = (((ushort)a) << 8) | ((ushort)b);
0436   if (!lid2)
0437     return;
0438   if (lid2 < 0x100)
0439   {
0440     if ((ilm.AdapterID != 0x4900) && (ilm.AdapterID != 0xef00))
0441     {
0442       ilm.AdapterID = lid2;
0443       switch (lid2)
0444       {
0445       case     1: // Sony LA-EA1 or Sigma MC-11 Adapter
0446       case     2: // Sony LA-EA2
0447       case     3: // Sony LA-EA3
0448       case     6: // Sony LA-EA4
0449       case     7: // Sony LA-EA5
0450       case 24593: // LA-EA4r MonsterAdapter, id = 0x6011
0451         ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
0452         break;
0453       case  44: // Metabones Canon EF Smart Adapter
0454       case  78: // Metabones Canon EF Smart Adapter Mark III or Other Adapter
0455       case 184: // Metabones Canon EF Speed Booster Ultra
0456       case 234: // Metabones Canon EF Smart Adapter Mark IV
0457       case 239: // Metabones Canon EF Speed Booster
0458         ilm.LensMount = LIBRAW_MOUNT_Canon_EF;
0459         break;
0460       }
0461     }
0462   }
0463   else
0464     ilm.LensID = lid2;
0465 
0466   if ((lid2 >= 50481) &&
0467       (lid2 < 50500)) {
0468     strcpy(ilm.Adapter, "MC-11");
0469     ilm.AdapterID = 0x4900;
0470   } else if ((lid2 > 0xef00) &&
0471              (lid2 < 0xffff) &&
0472              (lid2 != 0xff00)) {
0473     ilm.AdapterID = 0xef00;
0474     ilm.LensID -= ilm.AdapterID;
0475     ilm.LensMount = LIBRAW_MOUNT_Canon_EF;
0476   }
0477 
0478   return;
0479 }
0480 
0481 void LibRaw::parseSonyLensFeatures(uchar a, uchar b)
0482 {
0483 
0484   ushort features;
0485   features = (((ushort)a) << 8) | ((ushort)b);
0486 
0487   if ((ilm.LensMount == LIBRAW_MOUNT_Canon_EF) ||
0488       (ilm.LensMount != LIBRAW_MOUNT_Sigma_X3F) || !features)
0489     return;
0490 
0491   ilm.LensFeatures_pre[0] = 0;
0492   ilm.LensFeatures_suf[0] = 0;
0493   if ((features & 0x0200) && (features & 0x0100))
0494     strcpy(ilm.LensFeatures_pre, "E");
0495   else if (features & 0x0200)
0496     strcpy(ilm.LensFeatures_pre, "FE");
0497   else if (features & 0x0100)
0498     strcpy(ilm.LensFeatures_pre, "DT");
0499 
0500   if (!ilm.LensFormat && !ilm.LensMount)
0501   {
0502     ilm.LensFormat = LIBRAW_FORMAT_FF;
0503     ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
0504 
0505     if ((features & 0x0200) && (features & 0x0100))
0506     {
0507       ilm.LensFormat = LIBRAW_FORMAT_APSC;
0508       ilm.LensMount = LIBRAW_MOUNT_Sony_E;
0509     }
0510     else if (features & 0x0200)
0511     {
0512       ilm.LensMount = LIBRAW_MOUNT_Sony_E;
0513     }
0514     else if (features & 0x0100)
0515     {
0516       ilm.LensFormat = LIBRAW_FORMAT_APSC;
0517     }
0518   }
0519 
0520   if (features & 0x4000)
0521     strnXcat(ilm.LensFeatures_pre, " PZ");
0522 
0523   if (features & 0x0008)
0524     strnXcat(ilm.LensFeatures_suf, " G");
0525   else if (features & 0x0004)
0526     strnXcat(ilm.LensFeatures_suf, " ZA");
0527 
0528   if ((features & 0x0020) && (features & 0x0040))
0529     strnXcat(ilm.LensFeatures_suf, " Macro");
0530   else if (features & 0x0020)
0531     strnXcat(ilm.LensFeatures_suf, " STF");
0532   else if (features & 0x0040)
0533     strnXcat(ilm.LensFeatures_suf, " Reflex");
0534   else if (features & 0x0080)
0535     strnXcat(ilm.LensFeatures_suf, " Fisheye");
0536 
0537   if (features & 0x0001)
0538     strnXcat(ilm.LensFeatures_suf, " SSM");
0539   else if (features & 0x0002)
0540     strnXcat(ilm.LensFeatures_suf, " SAM");
0541 
0542   if (features & 0x8000)
0543     strnXcat(ilm.LensFeatures_suf, " OSS");
0544 
0545   if (features & 0x2000)
0546     strnXcat(ilm.LensFeatures_suf, " LE");
0547 
0548   if (features & 0x0800)
0549     strnXcat(ilm.LensFeatures_suf, " II");
0550 
0551   if (ilm.LensFeatures_suf[0] == ' ')
0552     memmove(ilm.LensFeatures_suf, ilm.LensFeatures_suf + 1,
0553             strbuflen(ilm.LensFeatures_suf) - 1);
0554 
0555   return;
0556 }
0557 
0558 void LibRaw::process_Sony_0x0116(uchar *buf, ushort len, unsigned long long id)
0559 {
0560   int i = 0;
0561 
0562   if (((id == SonyID_DSLR_A900)      ||
0563        (id == SonyID_DSLR_A900_APSC) ||
0564        (id == SonyID_DSLR_A850)      ||
0565        (id == SonyID_DSLR_A850_APSC)) &&
0566       (len >= 2))
0567     i = 1;
0568   else if ((id >= SonyID_DSLR_A550) && (len >= 3))
0569     i = 2;
0570   else
0571     return;
0572 
0573   imCommon.BatteryTemperature = (float)(buf[i] - 32) / 1.8f;
0574 }
0575 
0576 void LibRaw::process_Sony_0x2010(uchar *buf, ushort len)
0577 {
0578 
0579   if (imSony.group2010 == LIBRAW_SONY_Tag2010None) return;
0580 
0581   if ((imSony.real_iso_offset != 0xffff) &&
0582       (len >= (imSony.real_iso_offset + 2)) && (imCommon.real_ISO < 0.1f))
0583   {
0584     uchar s[2];
0585     s[0] = SonySubstitution[buf[imSony.real_iso_offset]];
0586     s[1] = SonySubstitution[buf[imSony.real_iso_offset + 1]];
0587     imCommon.real_ISO =
0588         100.0f * libraw_powf64l(2.0f, (16 - ((float)sget2(s)) / 256.0f));
0589   }
0590 
0591   if ((imSony.MeteringMode_offset != 0xffff) &&
0592       (imSony.ExposureProgram_offset != 0xffff) &&
0593       (len >= (imSony.MeteringMode_offset + 2)))
0594   {
0595     imgdata.shootinginfo.MeteringMode =
0596         SonySubstitution[buf[imSony.MeteringMode_offset]];
0597     imgdata.shootinginfo.ExposureProgram =
0598         SonySubstitution[buf[imSony.ExposureProgram_offset]];
0599   }
0600 
0601   if ((imSony.ReleaseMode2_offset != 0xffff) &&
0602       (len >= (imSony.ReleaseMode2_offset + 2)))
0603   {
0604     imgdata.shootinginfo.DriveMode =
0605         SonySubstitution[buf[imSony.ReleaseMode2_offset]];
0606   }
0607 }
0608 
0609 void LibRaw::process_Sony_0x9050(uchar *buf, ushort len, unsigned long long id)
0610 {
0611   ushort lid;
0612   uchar s[4];
0613   int c;
0614 
0615   if ((imSony.group9050 == LIBRAW_SONY_Tag9050None) &&
0616       (imSony.CameraType != LIBRAW_SONY_DSC) &&
0617       (imSony.CameraType != LIBRAW_SONY_DSLR))
0618     imSony.group9050 = LIBRAW_SONY_Tag9050a;
0619 
0620   if (imSony.group9050 == LIBRAW_SONY_Tag9050None) return;
0621 
0622   if ((ilm.CameraMount != LIBRAW_MOUNT_Sony_E) &&
0623       (imSony.CameraType != LIBRAW_SONY_DSC))
0624   {
0625     if (len < 2)
0626       return;
0627     if (buf[0])
0628       ilm.MaxAp4CurFocal =
0629         my_roundf(
0630           libraw_powf64l(2.0f, ((float)SonySubstitution[buf[0]] / 8.0 - 1.06f) / 2.0f) *
0631              10.0f) / 10.0f;
0632 
0633     if (buf[1])
0634       ilm.MinAp4CurFocal =
0635         my_roundf(
0636           libraw_powf64l(2.0f, ((float)SonySubstitution[buf[1]] / 8.0 - 1.06f) / 2.0f) *
0637              10.0f) / 10.0f;
0638   }
0639 
0640   if ((imSony.group9050 == LIBRAW_SONY_Tag9050b) ||
0641       (imSony.group9050 == LIBRAW_SONY_Tag9050c)) {
0642     if (len <= 0x8d) return;
0643     unsigned long long b88 = SonySubstitution[buf[0x88]];
0644     unsigned long long b89 = SonySubstitution[buf[0x89]];
0645     unsigned long long b8a = SonySubstitution[buf[0x8a]];
0646     unsigned long long b8b = SonySubstitution[buf[0x8b]];
0647     unsigned long long b8c = SonySubstitution[buf[0x8c]];
0648     unsigned long long b8d = SonySubstitution[buf[0x8d]];
0649     sprintf(imgdata.shootinginfo.InternalBodySerial, "%06llx",
0650             (b88 << 40) + (b89 << 32) + (b8a << 24) + (b8b << 16) + (b8c << 8) + b8d);
0651 
0652   } else if (imSony.group9050 == LIBRAW_SONY_Tag9050a) {
0653       if ((ilm.CameraMount == LIBRAW_MOUNT_Sony_E) &&
0654              (id != SonyID_NEX_5N) &&
0655              (id != SonyID_NEX_7)  &&
0656              (id != SonyID_NEX_VG20)) {
0657       if (len <= 0x7f) return;
0658       unsigned b7c = SonySubstitution[buf[0x7c]];
0659       unsigned b7d = SonySubstitution[buf[0x7d]];
0660       unsigned b7e = SonySubstitution[buf[0x7e]];
0661       unsigned b7f = SonySubstitution[buf[0x7f]];
0662       sprintf(imgdata.shootinginfo.InternalBodySerial, "%04x",
0663               (b7c << 24) + (b7d << 16) + (b7e << 8) + b7f);
0664 
0665     } else if (ilm.CameraMount == LIBRAW_MOUNT_Minolta_A) {
0666       if (len <= 0xf4) return;
0667       unsigned long long bf0 = SonySubstitution[buf[0xf0]];
0668       unsigned long long bf1 = SonySubstitution[buf[0xf1]];
0669       unsigned long long bf2 = SonySubstitution[buf[0xf2]];
0670       unsigned long long bf3 = SonySubstitution[buf[0xf3]];
0671       unsigned long long bf4 = SonySubstitution[buf[0xf4]];
0672       sprintf(imgdata.shootinginfo.InternalBodySerial, "%05llx",
0673               (bf0 << 32) + (bf1 << 24) + (bf2 << 16) + (bf3 << 8) + bf4);
0674     }
0675   }
0676 
0677   if (imSony.CameraType != LIBRAW_SONY_DSC)
0678   {
0679     if (len <= 0x106)
0680       return;
0681     if (buf[0x3d] | buf[0x3c])
0682     {
0683       lid = SonySubstitution[buf[0x3d]] << 8 | SonySubstitution[buf[0x3c]];
0684       ilm.CurAp = libraw_powf64l(2.0f, ((float)lid / 256.0f - 16.0f) / 2.0f);
0685     }
0686     if (buf[0x105] &&
0687         (ilm.LensMount != LIBRAW_MOUNT_Canon_EF) &&
0688         (ilm.LensMount != LIBRAW_MOUNT_Sigma_X3F)) {
0689       switch (SonySubstitution[buf[0x105]]) {
0690         case 1:
0691           ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
0692           break;
0693         case 2:
0694           ilm.LensMount = LIBRAW_MOUNT_Sony_E;
0695         break;
0696       }
0697     }
0698     if (buf[0x106]) {
0699       switch (SonySubstitution[buf[0x106]]) {
0700         case 1:
0701           ilm.LensFormat = LIBRAW_FORMAT_APSC;
0702           break;
0703         case 2:
0704           ilm.LensFormat = LIBRAW_FORMAT_FF;
0705         break;
0706       }
0707     }
0708   }
0709 
0710   if (ilm.CameraMount == LIBRAW_MOUNT_Sony_E)
0711   {
0712     if (len <= 0x108)
0713       return;
0714     parseSonyLensType2(
0715         SonySubstitution[buf[0x0108]], // LensType2 - Sony lens ids
0716         SonySubstitution[buf[0x0107]]);
0717   }
0718 
0719   if (len <= 0x10a)
0720     return;
0721   if ((ilm.LensID == LIBRAW_LENS_NOT_SET) &&
0722       (ilm.CameraMount == LIBRAW_MOUNT_Minolta_A) &&
0723       (buf[0x010a] | buf[0x0109]))
0724   {
0725     ilm.LensID = // LensType - Minolta/Sony lens ids
0726         SonySubstitution[buf[0x010a]] << 8 | SonySubstitution[buf[0x0109]];
0727 
0728     if ((ilm.LensID > 0x4900) && (ilm.LensID <= 0x5900))
0729     {
0730       ilm.AdapterID = 0x4900;
0731       ilm.LensID -= ilm.AdapterID;
0732       ilm.LensMount = LIBRAW_MOUNT_Sigma_X3F;
0733       strcpy(ilm.Adapter, "MC-11");
0734     }
0735 
0736     else if ((ilm.LensID > 0xef00) && (ilm.LensID < 0xffff) &&
0737              (ilm.LensID != 0xff00))
0738     {
0739       ilm.AdapterID = 0xef00;
0740       ilm.LensID -= ilm.AdapterID;
0741       ilm.LensMount = LIBRAW_MOUNT_Canon_EF;
0742     }
0743   }
0744 
0745   if ((id >= SonyID_SLT_A65) && (id <= SonyID_NEX_F3))
0746   {
0747     if (len <= 0x116)
0748       return;
0749     // "SLT-A65", "SLT-A77", "NEX-7", "NEX-VG20",
0750     // "SLT-A37", "SLT-A57", "NEX-F3", "Lunar"
0751     parseSonyLensFeatures(SonySubstitution[buf[0x115]],
0752                           SonySubstitution[buf[0x116]]);
0753   }
0754   else if (ilm.CameraMount != LIBRAW_MOUNT_FixedLens)
0755   {
0756     if (len <= 0x117)
0757       return;
0758     parseSonyLensFeatures(SonySubstitution[buf[0x116]],
0759                           SonySubstitution[buf[0x117]]);
0760   }
0761 
0762   if ((imSony.ImageCount3_offset != 0xffff) &&
0763       (len >= (imSony.ImageCount3_offset + 4)))
0764   {
0765     FORC4 s[c] = SonySubstitution[buf[imSony.ImageCount3_offset + c]];
0766     imSony.ImageCount3 = sget4(s);
0767   }
0768 
0769   return;
0770 }
0771 
0772 void LibRaw::process_Sony_0x9400(uchar *buf, ushort len, unsigned long long /*id*/)
0773 {
0774 
0775   uchar s[4];
0776   int c;
0777   uchar bufx = buf[0];
0778 
0779   if (((bufx == 0x23) ||
0780        (bufx == 0x24) ||
0781        (bufx == 0x26) ||
0782        (bufx == 0x28) ||
0783        (bufx == 0x31)) &&
0784       (len >= 0x1f)) // 0x9400 'c' version
0785   {
0786     imSony.Sony0x9400_version = 0xc;
0787     imSony.Sony0x9400_ReleaseMode2 = SonySubstitution[buf[0x09]];
0788 
0789     if ((imSony.group2010 == LIBRAW_SONY_Tag2010g) ||
0790         (imSony.group2010 == LIBRAW_SONY_Tag2010h)) {
0791       FORC4 s[c] = SonySubstitution[buf[0x0a + c]];
0792       imSony.ShotNumberSincePowerUp = sget4(s);
0793     } else {
0794       imSony.ShotNumberSincePowerUp = SonySubstitution[buf[0x0a]];
0795     }
0796 
0797     FORC4 s[c] = SonySubstitution[buf[0x12 + c]];
0798     imSony.Sony0x9400_SequenceImageNumber = sget4(s);
0799 
0800     imSony.Sony0x9400_SequenceLength1 = SonySubstitution[buf[0x16]]; // shots
0801 
0802     FORC4 s[c] = SonySubstitution[buf[0x1a + c]];
0803     imSony.Sony0x9400_SequenceFileNumber = sget4(s);
0804 
0805     imSony.Sony0x9400_SequenceLength2 = SonySubstitution[buf[0x1e]]; // files
0806   }
0807 
0808   else if ((bufx == 0x0c) && (len >= 0x1f)) // 0x9400 'b' version
0809   {
0810     imSony.Sony0x9400_version = 0xb;
0811 
0812     FORC4 s[c] = SonySubstitution[buf[0x08 + c]];
0813     imSony.Sony0x9400_SequenceImageNumber = sget4(s);
0814 
0815     FORC4 s[c] = SonySubstitution[buf[0x0c + c]];
0816     imSony.Sony0x9400_SequenceFileNumber = sget4(s);
0817 
0818     imSony.Sony0x9400_ReleaseMode2 = SonySubstitution[buf[0x10]];
0819 
0820     imSony.Sony0x9400_SequenceLength1 = SonySubstitution[buf[0x1e]];
0821   }
0822 
0823   else if ((bufx == 0x0a) && (len >= 0x23)) // 0x9400 'a' version
0824   {
0825     imSony.Sony0x9400_version = 0xa;
0826 
0827     FORC4 s[c] = SonySubstitution[buf[0x08 + c]];
0828     imSony.Sony0x9400_SequenceImageNumber = sget4(s);
0829 
0830     FORC4 s[c] = SonySubstitution[buf[0x0c + c]];
0831     imSony.Sony0x9400_SequenceFileNumber = sget4(s);
0832 
0833     imSony.Sony0x9400_ReleaseMode2 = SonySubstitution[buf[0x10]];
0834 
0835     imSony.Sony0x9400_SequenceLength1 = SonySubstitution[buf[0x22]];
0836   }
0837 
0838   else
0839     return;
0840 }
0841 
0842 void LibRaw::process_Sony_0x9402(uchar *buf, ushort len)
0843 {
0844 
0845   if (len < 0x17)
0846     return;
0847 
0848   if ((imSony.CameraType == LIBRAW_SONY_SLT)  ||
0849       (imSony.CameraType == LIBRAW_SONY_ILCA) ||
0850       (buf[0x00] == 0x05)                     ||
0851       (buf[0x00] == 0xff))
0852     return;
0853 
0854   if (buf[0x02] == 0xff)
0855   {
0856     imCommon.AmbientTemperature =
0857       (float)((short)SonySubstitution[buf[0x04]]);
0858   }
0859 
0860   if (imgdata.shootinginfo.FocusMode == LIBRAW_SONY_FOCUSMODE_UNKNOWN)
0861   {
0862   imgdata.shootinginfo.FocusMode = SonySubstitution[buf[0x16]]&0x7f;
0863   }
0864   if (len >= 0x18)
0865     imSony.AFAreaMode = (uint16_t)SonySubstitution[buf[0x17]];
0866 
0867   if ((len >= 0x2e) &&
0868       (imSony.CameraType != LIBRAW_SONY_DSC))
0869   {
0870     imSony.FocusPosition = (ushort)SonySubstitution[buf[0x2d]]; // FocusPosition2
0871   }
0872   return;
0873 }
0874 
0875 void LibRaw::process_Sony_0x9403(uchar *buf, ushort len)
0876 {
0877   if ((len < 6) || (unique_id == SonyID_ILCE_7C))
0878     return;
0879   uchar bufx = SonySubstitution[buf[4]];
0880   if ((bufx == 0x00) || (bufx == 0x94))
0881     return;
0882 
0883   imCommon.SensorTemperature = (float)((short)SonySubstitution[buf[5]]);
0884 
0885   return;
0886 }
0887 
0888 void LibRaw::process_Sony_0x9406(uchar *buf, ushort len)
0889 {
0890   if (len < 6)
0891     return;
0892   uchar bufx = buf[0];
0893   if ((bufx != 0x01) && (bufx != 0x08) && (bufx != 0x1b))
0894     return;
0895   bufx = buf[2];
0896   if ((bufx != 0x08) && (bufx != 0x1b))
0897     return;
0898 
0899   imCommon.BatteryTemperature =
0900       (float)(SonySubstitution[buf[5]] - 32) / 1.8f;
0901 
0902   return;
0903 }
0904 
0905 void LibRaw::process_Sony_0x940c(uchar *buf, ushort len)
0906 {
0907   if ((imSony.CameraType != LIBRAW_SONY_ILCE) &&
0908       (imSony.CameraType != LIBRAW_SONY_NEX))
0909     return;
0910   if (len <= 0x000a)
0911     return;
0912   ushort lid2;
0913   if ((ilm.LensMount != LIBRAW_MOUNT_Canon_EF) &&
0914       (ilm.LensMount != LIBRAW_MOUNT_Sigma_X3F))
0915   {
0916     switch (SonySubstitution[buf[0x0008]])
0917     {
0918     case 1:
0919     case 5:
0920       ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
0921       break;
0922     case 4:
0923       ilm.LensMount = LIBRAW_MOUNT_Sony_E;
0924       break;
0925     }
0926   }
0927   if (ilm.LensMount != LIBRAW_MOUNT_Unknown) {
0928     lid2 = (((ushort)SonySubstitution[buf[0x000a]]) << 8) |
0929            ((ushort)SonySubstitution[buf[0x0009]]);
0930     if ((lid2 > 0) &&
0931         ((lid2 < 32784) || (ilm.LensID == 0x1999) || (ilm.LensID == 0xffff)))
0932       parseSonyLensType2(
0933           SonySubstitution[buf[0x000a]], // LensType2 - Sony lens ids
0934           SonySubstitution[buf[0x0009]]);
0935     if ((lid2 == 44) || (lid2 == 78) || (lid2 == 184) || (lid2 == 234) ||
0936         (lid2 == 239))
0937       ilm.AdapterID = lid2;
0938     }
0939   return;
0940 }
0941 
0942 void LibRaw::process_Sony_0x940e(uchar *buf, ushort len, unsigned long long id)
0943 {
0944   if (len < 3)
0945     return;
0946 
0947   if (((imSony.CameraType != LIBRAW_SONY_SLT) &&
0948        (imSony.CameraType != LIBRAW_SONY_ILCA)) ||
0949       (id == SonyID_SLT_A33)  ||
0950       (id == SonyID_SLT_A35)  ||
0951       (id == SonyID_SLT_A55))
0952     return;
0953 
0954   int c;
0955   imSony.AFType = SonySubstitution[buf[0x02]];
0956 
0957   if (imCommon.afcount < LIBRAW_AFDATA_MAXCOUNT)
0958   {
0959     unsigned tag = 0x940e;
0960     imCommon.afdata[imCommon.afcount].AFInfoData_tag = tag;
0961     imCommon.afdata[imCommon.afcount].AFInfoData_order = order;
0962     imCommon.afdata[imCommon.afcount].AFInfoData_length = len;
0963     imCommon.afdata[imCommon.afcount].AFInfoData = (uchar *)malloc(imCommon.afdata[imCommon.afcount].AFInfoData_length);
0964     FORC((int)imCommon.afdata[imCommon.afcount].AFInfoData_length)
0965       imCommon.afdata[imCommon.afcount].AFInfoData[c] = SonySubstitution[buf[c]];
0966     imCommon.afcount++;
0967   }
0968 
0969   if (imSony.CameraType == LIBRAW_SONY_ILCA)
0970   {
0971     if (len >= 0x0051)
0972     {
0973       imgdata.shootinginfo.FocusMode = SonySubstitution[buf[0x05]];
0974       imSony.nAFPointsUsed =
0975           MIN(10, sizeof imSony.AFPointsUsed);
0976       FORC(imSony.nAFPointsUsed) imSony.AFPointsUsed[c] = SonySubstitution[buf[0x10 +c]];
0977       imSony.AFAreaMode = (uint16_t)SonySubstitution[buf[0x3a]];
0978       imSony.AFMicroAdjValue = SonySubstitution[buf[0x0050]];
0979       if (!imSony.AFMicroAdjValue) imSony.AFMicroAdjValue = 0x7f;
0980       else imSony.AFMicroAdjOn = 1;
0981     }
0982   }
0983   else
0984   {
0985     if (len >= 0x017e)
0986     {
0987       imSony.AFAreaMode = (uint16_t)SonySubstitution[buf[0x0a]];
0988       imgdata.shootinginfo.FocusMode = SonySubstitution[buf[0x0b]];
0989       imSony.nAFPointsUsed =
0990           MIN(4, sizeof imSony.AFPointsUsed);
0991       FORC(imSony.nAFPointsUsed) imSony.AFPointsUsed[c] = SonySubstitution[buf[0x016e +c]];
0992       imSony.AFMicroAdjValue = SonySubstitution[buf[0x017d]];
0993       if (!imSony.AFMicroAdjValue) imSony.AFMicroAdjValue = 0x7f;
0994       else imSony.AFMicroAdjOn = 1;
0995     }
0996   }
0997 
0998 }
0999 
1000 void LibRaw::parseSonyMakernotes(
1001     int base, unsigned tag, unsigned type, unsigned len, unsigned dng_writer,
1002     uchar *&table_buf_0x0116, ushort &table_buf_0x0116_len,
1003     uchar *&table_buf_0x2010, ushort &table_buf_0x2010_len,
1004     uchar *&table_buf_0x9050, ushort &table_buf_0x9050_len,
1005     uchar *&table_buf_0x9400, ushort &table_buf_0x9400_len,
1006     uchar *&table_buf_0x9402, ushort &table_buf_0x9402_len,
1007     uchar *&table_buf_0x9403, ushort &table_buf_0x9403_len,
1008     uchar *&table_buf_0x9406, ushort &table_buf_0x9406_len,
1009     uchar *&table_buf_0x940c, ushort &table_buf_0x940c_len,
1010     uchar *&table_buf_0x940e, ushort &table_buf_0x940e_len)
1011 {
1012 
1013   ushort lid, a, c, d;
1014   uchar *table_buf;
1015   uchar uc;
1016   uchar s[2];
1017   int LensDataValid = 0;
1018   unsigned uitemp;
1019 
1020 // printf ("==>> tag 0x%x, len %d, type %d, model =%s=, cam.id 0x%llx, cam.type %d, =%s=\n",
1021 // tag, len, type, model, ilm.CamID, imSony.CameraType, imSony.MetaVersion);
1022 
1023   if (tag == 0xb001) // Sony ModelID
1024   {
1025     unique_id = get2();
1026     setSonyBodyFeatures(unique_id);
1027 
1028     if (table_buf_0x0116_len)
1029     {
1030       process_Sony_0x0116(table_buf_0x0116, table_buf_0x0116_len, unique_id);
1031       free(table_buf_0x0116);
1032       table_buf_0x0116_len = 0;
1033     }
1034 
1035     if (table_buf_0x2010_len)
1036     {
1037       process_Sony_0x2010(table_buf_0x2010, table_buf_0x2010_len);
1038       free(table_buf_0x2010);
1039       table_buf_0x2010_len = 0;
1040     }
1041 
1042     if (table_buf_0x9050_len)
1043     {
1044       process_Sony_0x9050(table_buf_0x9050, table_buf_0x9050_len, unique_id);
1045       free(table_buf_0x9050);
1046       table_buf_0x9050_len = 0;
1047     }
1048 
1049     if (table_buf_0x9400_len)
1050     {
1051       process_Sony_0x9400(table_buf_0x9400, table_buf_0x9400_len, unique_id);
1052       free(table_buf_0x9400);
1053       table_buf_0x9400_len = 0;
1054     }
1055 
1056     if (table_buf_0x9402_len)
1057     {
1058       process_Sony_0x9402(table_buf_0x9402, table_buf_0x9402_len);
1059       free(table_buf_0x9402);
1060       table_buf_0x9402_len = 0;
1061     }
1062 
1063     if (table_buf_0x9403_len)
1064     {
1065       process_Sony_0x9403(table_buf_0x9403, table_buf_0x9403_len);
1066       free(table_buf_0x9403);
1067       table_buf_0x9403_len = 0;
1068     }
1069 
1070     if (table_buf_0x9406_len)
1071     {
1072       process_Sony_0x9406(table_buf_0x9406, table_buf_0x9406_len);
1073       free(table_buf_0x9406);
1074       table_buf_0x9406_len = 0;
1075     }
1076 
1077     if (table_buf_0x940c_len)
1078     {
1079       process_Sony_0x940c(table_buf_0x940c, table_buf_0x940c_len);
1080       free(table_buf_0x940c);
1081       table_buf_0x940c_len = 0;
1082     }
1083 
1084     if (table_buf_0x940e_len)
1085     {
1086       process_Sony_0x940e(table_buf_0x940e, table_buf_0x940e_len, unique_id);
1087       free(table_buf_0x940e);
1088       table_buf_0x940e_len = 0;
1089     }
1090   }
1091   else if (tag == 0xb000)
1092   {
1093     FORC4 imSony.FileFormat = imSony.FileFormat * 10 + fgetc(ifp);
1094   }
1095   else if (tag == 0xb026)
1096   {
1097     uitemp = get4();
1098     if (uitemp != 0xffffffff)
1099       imgdata.shootinginfo.ImageStabilization = uitemp;
1100   }
1101   else if (((tag == 0x0001) || // Minolta CameraSettings, big endian
1102             (tag == 0x0003)) &&
1103            (len >= 196))
1104   {
1105     table_buf = (uchar *)malloc(len);
1106     fread(table_buf, len, 1, ifp);
1107 
1108     lid = 0x01 << 2;
1109     imgdata.shootinginfo.ExposureMode =
1110         (unsigned)table_buf[lid] << 24 | (unsigned)table_buf[lid + 1] << 16 |
1111         (unsigned)table_buf[lid + 2] << 8 | (unsigned)table_buf[lid + 3];
1112 
1113     lid = 0x06 << 2;
1114     imgdata.shootinginfo.DriveMode =
1115         (unsigned)table_buf[lid] << 24 | (unsigned)table_buf[lid + 1] << 16 |
1116         (unsigned)table_buf[lid + 2] << 8 | (unsigned)table_buf[lid + 3];
1117 
1118     lid = 0x07 << 2;
1119     imgdata.shootinginfo.MeteringMode =
1120         (unsigned)table_buf[lid] << 24 | (unsigned)table_buf[lid + 1] << 16 |
1121         (unsigned)table_buf[lid + 2] << 8 | (unsigned)table_buf[lid + 3];
1122 
1123     lid = 0x25 << 2;
1124     imSony.MinoltaCamID =
1125         (unsigned)table_buf[lid] << 24 | (unsigned)table_buf[lid + 1] << 16 |
1126         (unsigned)table_buf[lid + 2] << 8 | (unsigned)table_buf[lid + 3];
1127     if (imSony.MinoltaCamID != 0xffffffff)
1128       ilm.CamID = imSony.MinoltaCamID;
1129 
1130     lid = 0x30 << 2;
1131     imgdata.shootinginfo.FocusMode =
1132         table_buf[lid + 3]?LIBRAW_SONY_FOCUSMODE_MF:LIBRAW_SONY_FOCUSMODE_AF;
1133     free(table_buf);
1134   }
1135   else if ((tag == 0x0004) && // Minolta CameraSettings7D, big endian
1136            (len >= 227))
1137   {
1138     table_buf = (uchar *)malloc(len);
1139     fread(table_buf, len, 1, ifp);
1140 
1141     lid = 0x0;
1142     imgdata.shootinginfo.ExposureMode =
1143         (ushort)table_buf[lid] << 8 | (ushort)table_buf[lid + 1];
1144 
1145     lid = 0x0e << 1;
1146     imgdata.shootinginfo.FocusMode = (short)table_buf[lid + 1];
1147     switch (imgdata.shootinginfo.FocusMode) {
1148       case 0: case 1: imgdata.shootinginfo.FocusMode += 2; break;
1149       case 3: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_MF; break;
1150     }
1151     lid = 0x10 << 1;
1152     imgdata.shootinginfo.AFPoint =
1153         (ushort)table_buf[lid] << 8 | (ushort)table_buf[lid + 1];
1154 
1155     lid = 0x25 << 1;
1156     switch ((ushort)table_buf[lid] << 8 | (ushort)table_buf[lid + 1]) {
1157     case 0:
1158     case 1:
1159       imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1160       break;
1161     case 4:
1162       imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1163       break;
1164     default:
1165       imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1166       break;
1167     }
1168 
1169     lid = 0x71 << 1;
1170     imgdata.shootinginfo.ImageStabilization =
1171         (ushort)table_buf[lid] << 8 | (ushort)table_buf[lid + 1];
1172 
1173     free(table_buf);
1174   }
1175   else if ((tag == 0x0010) && // CameraInfo
1176            strncasecmp(model, "DSLR-A100", 9) &&
1177            !strncasecmp(make, "SONY", 4) &&
1178            ((len == 368) ||  // a700                         : CameraInfo
1179             (len == 5478) || // a850, a900                   : CameraInfo
1180             (len == 5506) || // a200, a300, a350             : CameraInfo2
1181             (len == 6118) || // a230, a290, a330, a380, a390 : CameraInfo2
1182             (len == 15360))  // a450, a500, a550, a560, a580 : CameraInfo3
1183                              // a33, a35, a55
1184                              // NEX-3, NEX-5, NEX-5C, NEX-C3, NEX-VG10E
1185 
1186   )
1187   {
1188     table_buf = (uchar *)malloc(len);
1189     fread(table_buf, len, 1, ifp);
1190         if (imCommon.afcount < LIBRAW_AFDATA_MAXCOUNT)
1191         {
1192             imCommon.afdata[imCommon.afcount].AFInfoData_tag = tag;
1193             imCommon.afdata[imCommon.afcount].AFInfoData_order = order;
1194             imCommon.afdata[imCommon.afcount].AFInfoData_length = len;
1195             imCommon.afdata[imCommon.afcount].AFInfoData = (uchar *)malloc(imCommon.afdata[imCommon.afcount].AFInfoData_length);
1196             memcpy(imCommon.afdata[imCommon.afcount].AFInfoData, table_buf, imCommon.afdata[imCommon.afcount].AFInfoData_length);
1197             imCommon.afcount++;
1198         }
1199     if (memcmp(table_buf, "\xff\xff\xff\xff\xff\xff\xff\xff", 8) &&
1200         memcmp(table_buf, "\x00\x00\x00\x00\x00\x00\x00\x00", 8))
1201     {
1202       LensDataValid = 1;
1203     }
1204     switch (len)
1205     {
1206     case 368:  // a700: CameraInfo
1207     case 5478: // a850, a900: CameraInfo
1208       if ((!dng_writer) ||
1209           (saneSonyCameraInfo(table_buf[0], table_buf[3], table_buf[2],
1210                               table_buf[5], table_buf[4], table_buf[7])))
1211       {
1212         if (LensDataValid)
1213         {
1214           if (table_buf[0] | table_buf[3])
1215             ilm.MinFocal = bcd2dec(table_buf[0]) * 100 + bcd2dec(table_buf[3]);
1216           if (table_buf[2] | table_buf[5])
1217             ilm.MaxFocal = bcd2dec(table_buf[2]) * 100 + bcd2dec(table_buf[5]);
1218           if (table_buf[4])
1219             ilm.MaxAp4MinFocal = bcd2dec(table_buf[4]) / 10.0f;
1220           if (table_buf[4])
1221             ilm.MaxAp4MaxFocal = bcd2dec(table_buf[7]) / 10.0f;
1222           parseSonyLensFeatures(table_buf[1], table_buf[6]);
1223         }
1224 
1225         imSony.AFPointSelected = table_buf[21];
1226         imgdata.shootinginfo.AFPoint = (ushort)table_buf[25];
1227 
1228         if (len == 5478)
1229         {
1230           imSony.AFMicroAdjValue = table_buf[0x130] - 20;
1231           imSony.AFMicroAdjOn = (((table_buf[0x131] & 0x80) == 0x80) ? 1 : 0);
1232           imSony.AFMicroAdjRegisteredLenses = table_buf[0x131] & 0x7f;
1233         }
1234       }
1235       break;
1236     default:
1237       // CameraInfo2 & 3
1238       if ((!dng_writer) ||
1239           (saneSonyCameraInfo(table_buf[1], table_buf[2], table_buf[3],
1240                               table_buf[4], table_buf[5], table_buf[6])))
1241       {
1242         if ((LensDataValid) && strncasecmp(model, "NEX-5C", 6))
1243         {
1244           if (table_buf[1] | table_buf[2])
1245             ilm.MinFocal = bcd2dec(table_buf[1]) * 100 + bcd2dec(table_buf[2]);
1246           if (table_buf[3] | table_buf[4])
1247             ilm.MaxFocal = bcd2dec(table_buf[3]) * 100 + bcd2dec(table_buf[4]);
1248           if (table_buf[5])
1249             ilm.MaxAp4MinFocal = bcd2dec(table_buf[5]) / 10.0f;
1250           if (table_buf[6])
1251             ilm.MaxAp4MaxFocal = bcd2dec(table_buf[6]) / 10.0f;
1252           parseSonyLensFeatures(table_buf[0], table_buf[7]);
1253         }
1254 
1255         if (                 // CameraInfo2
1256             (len == 5506) || // a200, a300, a350
1257             (len == 6118))   // a230, a290, a330, a380, a390
1258         {
1259           imSony.AFPointSelected = table_buf[0x14];
1260         }
1261         else if (!strncasecmp(model, "DSLR-A450", 9) ||
1262                  !strncasecmp(model, "DSLR-A500", 9) ||
1263                  !strncasecmp(model, "DSLR-A550", 9))
1264         {
1265           imSony.AFPointSelected = table_buf[0x14];
1266           if (table_buf[0x15]) /* focus mode values translated to values in tag 0x201b */
1267             imgdata.shootinginfo.FocusMode = table_buf[0x15]+1;
1268           else imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_MF;
1269          imgdata.shootinginfo.AFPoint = (ushort)table_buf[0x18];
1270         }
1271         else if (!strncasecmp(model, "SLT-", 4)      ||
1272                  !strncasecmp(model, "DSLR-A560", 9) ||
1273                  !strncasecmp(model, "DSLR-A580", 9))
1274         {
1275           imSony.AFPointSelected = table_buf[0x1c];
1276           if (table_buf[0x1d])
1277             imgdata.shootinginfo.FocusMode = table_buf[0x1d]+1;
1278           else imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_MF;
1279           imgdata.shootinginfo.AFPoint = (ushort)table_buf[0x20];
1280         }
1281       }
1282     }
1283     free(table_buf);
1284   }
1285   else if ((!dng_writer) &&
1286            ((tag == 0x0020) || (tag == 0xb0280020)))
1287   {
1288     if (!strncasecmp(model, "DSLR-A100", 9)) // WBInfoA100
1289     {
1290       fseek(ifp, 0x49dc, SEEK_CUR);
1291       stmread(imgdata.shootinginfo.InternalBodySerial, 13, ifp);
1292     }
1293     else if ((len == 19154) || // a200 a230 a290 a300 a330 a350 a380 a390 : FocusInfo
1294              (len == 19148))   // a700 a850 a900                          : FocusInfo
1295     {
1296       table_buf = (uchar *)malloc(0x0080);
1297       fread(table_buf, 0x0080, 1, ifp);
1298       imgdata.shootinginfo.DriveMode = table_buf[14];
1299       imgdata.shootinginfo.ExposureProgram = table_buf[63];
1300       free(table_buf);
1301       fseek (ifp, 0x09bb - 0x0080, SEEK_CUR); // offset 2491 from the start of tag 0x0020
1302       imSony.FocusPosition = (ushort)fgetc(ifp);
1303     }
1304     else if (len == 20480) // a450 a500 a550 a560 a580 a33 a35 a55 : MoreInfo
1305                            // NEX-3 NEX-5 NEX-C3 NEX-VG10E         : MoreInfo
1306     {
1307       a = get2();
1308       /*b =*/ get2();
1309       c = get2();
1310       d = get2();
1311       if ((a) && (c == 1))
1312       {
1313         fseek(ifp, INT64(d) - 8LL, SEEK_CUR);
1314         table_buf = (uchar *)malloc(256);
1315         fread(table_buf, 256, 1, ifp);
1316         imgdata.shootinginfo.DriveMode = table_buf[1];
1317         imgdata.shootinginfo.ExposureProgram = table_buf[2];
1318         imgdata.shootinginfo.MeteringMode = table_buf[3];
1319         switch (table_buf[6]) {
1320         case 1:
1321           imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1322           break;
1323         case 2:
1324           imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1325           break;
1326         default:
1327           imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1328           break;
1329         }
1330         if (strncasecmp(model, "DSLR-A450", 9) &&
1331             strncasecmp(model, "DSLR-A500", 9) &&
1332             strncasecmp(model, "DSLR-A550", 9))
1333         { // NEX-3, NEX-5, NEX-5C??, NEX-C3, NEX-VG10(E), a560, a580, a33, a35, a55
1334           imgdata.shootinginfo.FocusMode = table_buf[0x13];
1335           switch (table_buf[0x13]) {
1336             case 17: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_AF_S; break;
1337             case 18: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_AF_C; break;
1338             case 19: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_AF_A; break;
1339             case 32: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_MF; break;
1340             case 48: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_DMF; break;
1341             default: imgdata.shootinginfo.FocusMode = table_buf[0x13]; break;
1342           }
1343           if (!strncasecmp(model, "DSLR-A560", 9) ||
1344               !strncasecmp(model, "DSLR-A580", 9) ||
1345               !strncasecmp(model, "SLT-A33", 7)   ||
1346               !strncasecmp(model, "SLT-A35", 7)   ||
1347               !strncasecmp(model, "SLT-A55", 7)   ||
1348               !strncasecmp(model, "NEX-VG10", 8)  ||
1349               !strncasecmp(model, "NEX-C3", 6))
1350             imSony.FocusPosition = (ushort)table_buf[0x2f]; // FocusPosition2
1351           else  // NEX-3, NEX-5, NEX-5C
1352             imSony.FocusPosition = (ushort)table_buf[0x2b]; // FocusPosition2
1353         }
1354         else // a450 a500 a550
1355         {
1356           imSony.FocusPosition = (ushort)table_buf[0x29]; // FocusPosition2
1357         }
1358         free(table_buf);
1359       }
1360     }
1361   }
1362   else if (tag == 0x0102)
1363   {
1364     imSony.Quality = get4();
1365   }
1366   else if (tag == 0x0104)
1367   {
1368     imCommon.FlashEC = getreal(type);
1369   }
1370   else if (tag == 0x0105) // Teleconverter
1371   {
1372     ilm.TeleconverterID = get4();
1373   }
1374   else if (tag == 0x0107)
1375   {
1376     uitemp = get4();
1377     if (uitemp == 1)
1378       imgdata.shootinginfo.ImageStabilization = 0;
1379     else if (uitemp == 5)
1380       imgdata.shootinginfo.ImageStabilization = 1;
1381     else
1382       imgdata.shootinginfo.ImageStabilization = uitemp;
1383   }
1384   else if ((tag == 0xb0280088) && (dng_writer == nonDNG))
1385   {
1386     thumb_offset = get4() + base;
1387   }
1388   else if ((tag == 0xb0280089) && (dng_writer == nonDNG))
1389   {
1390     thumb_length = get4();
1391   }
1392   else if (((tag == 0x0114) || // CameraSettings
1393             (tag == 0xb0280114)) &&
1394            (len < 256000))
1395   {
1396     table_buf = (uchar *)malloc(len);
1397     fread(table_buf, len, 1, ifp);
1398     switch (len)
1399     {
1400     case 260: // Sony a100, big endian
1401       imgdata.shootinginfo.ExposureMode =
1402           ((ushort)table_buf[0]) << 8 | ((ushort)table_buf[1]);
1403       lid = 0x0a << 1;
1404       imgdata.shootinginfo.DriveMode =
1405           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1406       lid = 0x0c << 1;
1407       imgdata.shootinginfo.FocusMode =
1408           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1409       switch (imgdata.shootinginfo.FocusMode) {
1410         case 0: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_AF_S; break;
1411         case 1: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_AF_C; break;
1412         case 5: imgdata.shootinginfo.FocusMode = LIBRAW_SONY_FOCUSMODE_MF; break;
1413       }
1414       lid = 0x0d << 1;
1415       imSony.AFPointSelected = table_buf[lid + 1];
1416       lid = 0x0e << 1;
1417       imSony.AFAreaMode = (uint16_t)table_buf[lid + 1];
1418       lid = 0x12 << 1;
1419       imgdata.shootinginfo.MeteringMode =
1420           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1421 
1422       lid = 0x17 << 1;
1423       switch ((ushort)table_buf[lid] << 8 | (ushort)table_buf[lid + 1]) {
1424       case 0:
1425         imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1426         break;
1427       case 2:
1428         imCommon.ColorSpace = LIBRAW_COLORSPACE_MonochromeGamma;
1429         break;
1430       case 5:
1431         imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1432         break;
1433       default:
1434         imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1435         break;
1436       }
1437 
1438       break;
1439     case 448: // Minolta "DYNAX 5D" and its aliases, big endian
1440       lid = 0x0a << 1;
1441       imgdata.shootinginfo.ExposureMode =
1442           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1443       lid = 0x25 << 1;
1444       imgdata.shootinginfo.MeteringMode =
1445           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1446 
1447       lid = 0x2f << 1;
1448       switch ((ushort)table_buf[lid] << 8 | (ushort)table_buf[lid + 1]) {
1449       case 0:
1450       case 1:
1451         imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1452         break;
1453       case 2:
1454         imCommon.ColorSpace = LIBRAW_COLORSPACE_MonochromeGamma;
1455         break;
1456       case 4:
1457       case 5:
1458         imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1459         break;
1460       default:
1461         imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1462         break;
1463       }
1464 
1465       lid = 0xbd << 1;
1466       imgdata.shootinginfo.ImageStabilization =
1467           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1468       break;
1469     case 280: // a200 a300 a350 a700
1470     case 364: // a850 a900
1471       // CameraSettings and CameraSettings2 are big endian
1472       if (table_buf[2] | table_buf[3])
1473       {
1474         lid = (((ushort)table_buf[2]) << 8) | ((ushort)table_buf[3]);
1475         ilm.CurAp = libraw_powf64l(2.0f, ((float)lid / 8.0f - 1.0f) / 2.0f);
1476       }
1477       lid = 0x04 << 1;
1478       imgdata.shootinginfo.DriveMode = table_buf[lid + 1];
1479       lid = 0x11 << 1;
1480       imSony.AFAreaMode = (uint16_t)table_buf[lid + 1];
1481       lid = 0x1b << 1;
1482       switch (((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1])) {
1483       case 0:
1484         imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1485         break;
1486       case 1:
1487       case 5:
1488         imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1489         break;
1490       default:
1491         imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1492         break;
1493       }
1494       lid = 0x4d << 1;
1495       imgdata.shootinginfo.FocusMode =
1496           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1497       switch (imgdata.shootinginfo.FocusMode) {
1498         case 1: case 2: case 3: imgdata.shootinginfo.FocusMode++; break;
1499         case 4: imgdata.shootinginfo.FocusMode +=2; break;
1500       }
1501       if (!imCommon.ColorSpace ||
1502           (imCommon.ColorSpace == LIBRAW_COLORSPACE_Unknown)) {
1503         lid = 0x83 << 1;
1504         switch (((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1])) {
1505         case 6:
1506           imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1507           break;
1508         case 5:
1509           imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1510           break;
1511         default:
1512           imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1513           break;
1514         }
1515       }
1516       break;
1517     case 332: // a230 a290 a330 a380 a390
1518       // CameraSettings and CameraSettings2 are big endian
1519       if (table_buf[2] | table_buf[3])
1520       {
1521         lid = (((ushort)table_buf[2]) << 8) | ((ushort)table_buf[3]);
1522         ilm.CurAp = libraw_powf64l(2.0f, ((float)lid / 8.0f - 1.0f) / 2.0f);
1523       }
1524       lid = 0x10 << 1;
1525       imSony.AFAreaMode = (uint16_t)table_buf[lid + 1];
1526       lid = 0x4d << 1;
1527       imgdata.shootinginfo.FocusMode =
1528           ((ushort)table_buf[lid]) << 8 | ((ushort)table_buf[lid + 1]);
1529       switch (imgdata.shootinginfo.FocusMode) {
1530         case 1: case 2: case 3: imgdata.shootinginfo.FocusMode++; break;
1531         case 4: imgdata.shootinginfo.FocusMode +=2; break;
1532      }
1533       lid = 0x7e << 1;
1534       imgdata.shootinginfo.DriveMode = table_buf[lid + 1];
1535       break;
1536     case 1536: // a560 a580 a33 a35 a55 NEX-3 NEX-5 NEX-5C NEX-C3 NEX-VG10E
1537     case 2048: // a450 a500 a550
1538       // CameraSettings3 are little endian
1539       switch (table_buf[0x0e]) {
1540       case 1:
1541         imCommon.ColorSpace = LIBRAW_COLORSPACE_sRGB;
1542         break;
1543       case 2:
1544         imCommon.ColorSpace = LIBRAW_COLORSPACE_AdobeRGB;
1545         break;
1546       default:
1547         imCommon.ColorSpace = LIBRAW_COLORSPACE_Unknown;
1548         break;
1549       }
1550       imSony.AFAreaMode = (uint16_t)table_buf[0x24];
1551       imgdata.shootinginfo.DriveMode = table_buf[0x34];
1552       parseSonyLensType2(table_buf[1016], table_buf[1015]);
1553       if (ilm.LensMount != LIBRAW_MOUNT_Canon_EF)
1554       {
1555         switch (table_buf[153])
1556         {
1557         case 16:
1558           ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
1559           break;
1560         case 17:
1561           ilm.LensMount = LIBRAW_MOUNT_Sony_E;
1562           break;
1563         }
1564       }
1565       break;
1566     }
1567     free(table_buf);
1568   }
1569   else if ((tag == 0x3000) && (len < 256000))
1570   {
1571     table_buf = (uchar *)malloc(len);
1572     fread(table_buf, len, 1, ifp);
1573     if (len >= 0x19)
1574     {
1575       for (int i = 0; i < 20; i++)
1576         imSony.SonyDateTime[i] = table_buf[6 + i];
1577     }
1578     if (len >= 0x43) // MetaVersion: (unique_id >= 286)
1579     {
1580       memcpy (imSony.MetaVersion, table_buf+0x34, 15);
1581       imSony.MetaVersion[15] = 0;
1582     }
1583     free(table_buf);
1584   }
1585   else if (tag == 0x0116 && len < 256000)
1586   {
1587     table_buf_0x0116 = (uchar *)malloc(len);
1588     table_buf_0x0116_len = len;
1589     fread(table_buf_0x0116, len, 1, ifp);
1590     if (ilm.CamID)
1591     {
1592       process_Sony_0x0116(table_buf_0x0116, table_buf_0x0116_len, ilm.CamID);
1593       free(table_buf_0x0116);
1594       table_buf_0x0116_len = 0;
1595     }
1596   }
1597   else if (tag == 0x2008)
1598   {
1599     imSony.LongExposureNoiseReduction = get4();
1600   }
1601   else if (tag == 0x2009)
1602   {
1603     imSony.HighISONoiseReduction = get2();
1604   }
1605   else if (tag == 0x200a)
1606   {
1607     imSony.HDR[0] = get2();
1608     imSony.HDR[1] = get2();
1609   }
1610   else if (tag == 0x2010 && len < 256000)
1611   {
1612     table_buf_0x2010 = (uchar *)malloc(len);
1613     table_buf_0x2010_len = len;
1614     fread(table_buf_0x2010, len, 1, ifp);
1615     if (ilm.CamID)
1616     {
1617       process_Sony_0x2010(table_buf_0x2010, table_buf_0x2010_len);
1618       free(table_buf_0x2010);
1619       table_buf_0x2010_len = 0;
1620     }
1621   }
1622   else if (tag == 0x201a)
1623   {
1624     imSony.ElectronicFrontCurtainShutter = get4();
1625   }
1626   else if (tag == 0x201b)
1627   {
1628     if ((imSony.CameraType != LIBRAW_SONY_DSC) ||
1629         (imSony.group2010 == LIBRAW_SONY_Tag2010i))
1630     {
1631       short t = (short)fgetc(ifp);
1632       if (imgdata.shootinginfo.FocusMode != t)
1633       {
1634         imgdata.shootinginfo.FocusMode = t;
1635       }
1636     }
1637   }
1638   else if ((tag == 0x201c) &&
1639            (len == 1) &&
1640            tagtypeIs(LIBRAW_EXIFTAG_TYPE_BYTE))
1641   {
1642     imSony.AFAreaModeSetting = (uint8_t)fgetc(ifp);
1643   }
1644   else if ((tag == 0x201d) &&
1645            (len == 2) &&
1646            tagtypeIs(LIBRAW_EXIFTAG_TYPE_SHORT))
1647   {
1648       imSony.FlexibleSpotPosition[0] = get2();
1649       imSony.FlexibleSpotPosition[1] = get2();
1650   }
1651   else if (tag == 0x201e)
1652   {
1653     if (imSony.CameraType != LIBRAW_SONY_DSC)
1654     {
1655       imSony.AFPointSelected = imSony.AFPointSelected_0x201e = fgetc(ifp);
1656     }
1657   }
1658   else if (tag == 0x2020) // AFPointsUsed
1659   {
1660     if (imSony.CameraType != LIBRAW_SONY_DSC)
1661     {
1662       if (imCommon.afcount < LIBRAW_AFDATA_MAXCOUNT)
1663       {
1664         imCommon.afdata[imCommon.afcount].AFInfoData_tag = tag;
1665         imCommon.afdata[imCommon.afcount].AFInfoData_order = order;
1666         imCommon.afdata[imCommon.afcount].AFInfoData_length = len;
1667         imCommon.afdata[imCommon.afcount].AFInfoData = (uchar *)malloc(imCommon.afdata[imCommon.afcount].AFInfoData_length);
1668         fread(imCommon.afdata[imCommon.afcount].AFInfoData, imCommon.afdata[imCommon.afcount].AFInfoData_length, 1, ifp);
1669         imSony.nAFPointsUsed =
1670             short(MIN(imCommon.afdata[imCommon.afcount].AFInfoData_length, sizeof imSony.AFPointsUsed));
1671         memcpy(imSony.AFPointsUsed, imCommon.afdata[imCommon.afcount].AFInfoData, imSony.nAFPointsUsed);
1672         imCommon.afcount++;
1673       }
1674     }
1675   }
1676   else if (tag == 0x2021) // AFTracking
1677   {
1678     if ((imSony.CameraType != LIBRAW_SONY_DSC) ||
1679         (imSony.group2010 == LIBRAW_SONY_Tag2010i))
1680     {
1681       imSony.AFTracking = fgetc(ifp);
1682     }
1683   }
1684   else if (tag == 0x2022) // FocalPlaneAFPointsUsed
1685   {
1686     if (imCommon.afcount < LIBRAW_AFDATA_MAXCOUNT)
1687     {
1688       imCommon.afdata[imCommon.afcount].AFInfoData_tag = tag;
1689       imCommon.afdata[imCommon.afcount].AFInfoData_order = order;
1690       imCommon.afdata[imCommon.afcount].AFInfoData_length = len;
1691       imCommon.afdata[imCommon.afcount].AFInfoData = (uchar *)malloc(imCommon.afdata[imCommon.afcount].AFInfoData_length);
1692       fread(imCommon.afdata[imCommon.afcount].AFInfoData, imCommon.afdata[imCommon.afcount].AFInfoData_length, 1, ifp);
1693       imCommon.afcount++;
1694     }
1695   }
1696   else if (tag == 0x2027)
1697   {
1698     FORC4 imSony.FocusLocation[c] = get2();
1699   }
1700   else if (tag == 0x2028)
1701   {
1702     if (get2())
1703     {
1704       imSony.VariableLowPassFilter = get2();
1705     }
1706   }
1707   else if (tag == 0x2029)
1708   {
1709     imSony.RAWFileType = get2();
1710   }
1711   else if (tag == 0x202c)
1712   {
1713     imSony.MeteringMode2 = get2();
1714   }
1715 
1716   else if (tag == 0x202a) // FocalPlaneAFPointsUsed, newer??
1717   {
1718     if (imCommon.afcount < LIBRAW_AFDATA_MAXCOUNT)
1719     {
1720       imCommon.afdata[imCommon.afcount].AFInfoData_tag = tag;
1721       imCommon.afdata[imCommon.afcount].AFInfoData_order = order;
1722       imCommon.afdata[imCommon.afcount].AFInfoData_length = len;
1723       imCommon.afdata[imCommon.afcount].AFInfoData = (uchar *)malloc(imCommon.afdata[imCommon.afcount].AFInfoData_length);
1724       fread(imCommon.afdata[imCommon.afcount].AFInfoData, imCommon.afdata[imCommon.afcount].AFInfoData_length, 1, ifp);
1725           imCommon.afcount++;
1726     }
1727   }
1728   else if (tag == 0x202e)
1729   {
1730     imSony.RawSizeType = get2();
1731   }
1732   else if (tag == 0x202f)
1733   {
1734     imSony.PixelShiftGroupID = get4();
1735     imSony.PixelShiftGroupPrefix = imSony.PixelShiftGroupID >> 22;
1736     imSony.PixelShiftGroupID =
1737         ((imSony.PixelShiftGroupID >> 17) & (unsigned)0x1f) *
1738             (unsigned)1000000 +
1739         ((imSony.PixelShiftGroupID >> 12) & (unsigned)0x1f) * (unsigned)10000 +
1740         ((imSony.PixelShiftGroupID >> 6) & (unsigned)0x3f) * (unsigned)100 +
1741         (imSony.PixelShiftGroupID & (unsigned)0x3f);
1742 
1743     imSony.numInPixelShiftGroup = fgetc(ifp);
1744     imSony.nShotsInPixelShiftGroup = fgetc(ifp);
1745   }
1746   else if (tag == 0x9050 && len < 256000) // little endian
1747   {
1748     table_buf_0x9050 = (uchar *)malloc(len);
1749     table_buf_0x9050_len = len;
1750     fread(table_buf_0x9050, len, 1, ifp);
1751 
1752     if (ilm.CamID)
1753     {
1754       process_Sony_0x9050(table_buf_0x9050, table_buf_0x9050_len, ilm.CamID);
1755       free(table_buf_0x9050);
1756       table_buf_0x9050_len = 0;
1757     }
1758   }
1759   else if (tag == 0x9400 && len < 256000)
1760   {
1761     table_buf_0x9400 = (uchar *)malloc(len);
1762     table_buf_0x9400_len = len;
1763     fread(table_buf_0x9400, len, 1, ifp);
1764     if (ilm.CamID)
1765     {
1766       process_Sony_0x9400(table_buf_0x9400, table_buf_0x9400_len, unique_id);
1767       free(table_buf_0x9400);
1768       table_buf_0x9400_len = 0;
1769     }
1770   }
1771   else if (tag == 0x9402 && len < 256000)
1772   {
1773     table_buf_0x9402 = (uchar *)malloc(len);
1774     table_buf_0x9402_len = len;
1775     fread(table_buf_0x9402, len, 1, ifp);
1776     if (ilm.CamID)
1777     {
1778       process_Sony_0x9402(table_buf_0x9402, table_buf_0x9402_len);
1779       free(table_buf_0x9402);
1780       table_buf_0x9402_len = 0;
1781     }
1782   }
1783   else if (tag == 0x9403 && len < 256000)
1784   {
1785     table_buf_0x9403 = (uchar *)malloc(len);
1786     table_buf_0x9403_len = len;
1787     fread(table_buf_0x9403, len, 1, ifp);
1788     if (ilm.CamID)
1789     {
1790       process_Sony_0x9403(table_buf_0x9403, table_buf_0x9403_len);
1791       free(table_buf_0x9403);
1792       table_buf_0x9403_len = 0;
1793     }
1794   }
1795   else if ((tag == 0x9405) && (len < 256000) && (len > 0x64))
1796   {
1797     table_buf = (uchar *)malloc(len);
1798     fread(table_buf, len, 1, ifp);
1799     uc = table_buf[0x0];
1800     if (imCommon.real_ISO < 0.1f)
1801     {
1802       if ((uc == 0x25) || (uc == 0x3a) || (uc == 0x76) || (uc == 0x7e) ||
1803           (uc == 0x8b) || (uc == 0x9a) || (uc == 0xb3) || (uc == 0xe1))
1804       {
1805         s[0] = SonySubstitution[table_buf[0x04]];
1806         s[1] = SonySubstitution[table_buf[0x05]];
1807         imCommon.real_ISO =
1808             100.0f * libraw_powf64l(2.0f, (16 - ((float)sget2(s)) / 256.0f));
1809       }
1810     }
1811     free(table_buf);
1812   }
1813   else if ((tag == 0x9404) && (len < 256000) && (len > 0x21))
1814   {
1815     table_buf = (uchar *)malloc(len);
1816     fread(table_buf, len, 1, ifp);
1817     uc = table_buf[0x00];
1818     if (((uc == 0x70) ||
1819          (uc == 0x8a) ||
1820          (uc == 0xcd) ||
1821          (uc == 0xe7) ||
1822          (uc == 0xea)) &&
1823          (table_buf[0x03] == 0x08))
1824     {
1825       if ((imSony.CameraType == LIBRAW_SONY_ILCA) ||
1826           (imSony.CameraType == LIBRAW_SONY_SLT))
1827       {
1828         imSony.FocusPosition = (ushort)SonySubstitution[table_buf[0x20]]; // FocusPosition2
1829       }
1830     }
1831     free(table_buf);
1832   }
1833   else if (tag == 0x9406 && len < 256000)
1834   {
1835     table_buf_0x9406 = (uchar *)malloc(len);
1836     table_buf_0x9406_len = len;
1837     fread(table_buf_0x9406, len, 1, ifp);
1838     if (ilm.CamID)
1839     {
1840       process_Sony_0x9406(table_buf_0x9406, table_buf_0x9406_len);
1841       free(table_buf_0x9406);
1842       table_buf_0x9406_len = 0;
1843     }
1844   }
1845   else if (tag == 0x940c && len < 256000)
1846   {
1847     table_buf_0x940c = (uchar *)malloc(len);
1848     table_buf_0x940c_len = len;
1849     fread(table_buf_0x940c, len, 1, ifp);
1850     if (ilm.CamID)
1851     {
1852       process_Sony_0x940c(table_buf_0x940c, table_buf_0x940c_len);
1853       free(table_buf_0x940c);
1854       table_buf_0x940c_len = 0;
1855     }
1856   }
1857   else if (tag == 0x940e && len < 256000)
1858   {
1859     table_buf_0x940e = (uchar *)malloc(len);
1860     table_buf_0x940e_len = len;
1861     fread(table_buf_0x940e, len, 1, ifp);
1862     if (ilm.CamID)
1863     {
1864       process_Sony_0x940e(table_buf_0x940e, table_buf_0x940e_len, ilm.CamID);
1865       free(table_buf_0x940e);
1866       table_buf_0x940e_len = 0;
1867     }
1868   }
1869   else if ((tag == 0x9416) && (len < 256000) && (len > 0x0076)) {
1870     table_buf = (uchar *)malloc(len);
1871     fread(table_buf, len, 1, ifp);
1872     if (imCommon.real_ISO < 0.1f) {
1873       s[0] = SonySubstitution[table_buf[0x04]];
1874       s[1] = SonySubstitution[table_buf[0x05]];
1875       imCommon.real_ISO =
1876           100.0f * libraw_powf64l(2.0f, (16 - ((float)sget2(s)) / 256.0f));
1877     }
1878     imgdata.shootinginfo.ExposureProgram = SonySubstitution[table_buf[0x35]];
1879     if ((ilm.LensMount != LIBRAW_MOUNT_Canon_EF) &&
1880         (ilm.LensMount != LIBRAW_MOUNT_Sigma_X3F)) {
1881       switch (SonySubstitution[table_buf[0x0048]]) {
1882       case 1:
1883       case 3:
1884         ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
1885         break;
1886       case 2:
1887         ilm.LensMount = LIBRAW_MOUNT_Sony_E;
1888         break;
1889       }
1890     }
1891     switch (SonySubstitution[table_buf[0x0049]]) {
1892       case 1:
1893         ilm.LensFormat = LIBRAW_FORMAT_APSC;
1894         break;
1895       case 2:
1896         ilm.LensFormat = LIBRAW_FORMAT_FF;
1897         break;
1898     }
1899     if (ilm.LensMount == LIBRAW_MOUNT_Sony_E)
1900       parseSonyLensType2(SonySubstitution[table_buf[0x4c]], SonySubstitution[table_buf[0x4b]]);
1901     free(table_buf);
1902   }
1903   else if (((tag == 0xb027) ||
1904             (tag == 0x010c)) &&
1905            (ilm.LensID == LIBRAW_LENS_NOT_SET))
1906   {
1907     ilm.LensID = get4();
1908     if ((ilm.LensID > 0x4900) && (ilm.LensID <= 0x5900))
1909     {
1910       ilm.AdapterID = 0x4900;
1911       ilm.LensID -= ilm.AdapterID;
1912       ilm.LensMount = LIBRAW_MOUNT_Sigma_X3F;
1913       strcpy(ilm.Adapter, "MC-11");
1914     }
1915 
1916     else if ((ilm.LensID > 0xef00) &&
1917              (ilm.LensID < 0xffff) &&
1918              (ilm.LensID != 0xff00))
1919     {
1920       ilm.AdapterID = 0xef00;
1921       ilm.LensID -= ilm.AdapterID;
1922       ilm.LensMount = LIBRAW_MOUNT_Canon_EF;
1923     }
1924 
1925     else if (((ilm.LensID != LIBRAW_LENS_NOT_SET) && (ilm.LensID < 0xef00)) ||
1926              (ilm.LensID == 0xff00))
1927       ilm.LensMount = LIBRAW_MOUNT_Minolta_A;
1928     /*
1929         if (tag == 0x010c)
1930           ilm.CameraMount = LIBRAW_MOUNT_Minolta_A;
1931     */
1932   }
1933   else if (tag == 0xb02a && len < 256000) // Sony LensSpec
1934   {
1935     table_buf = (uchar *)malloc(len);
1936     fread(table_buf, len, 1, ifp);
1937     if ((!dng_writer) ||
1938         (saneSonyCameraInfo(table_buf[1], table_buf[2], table_buf[3],
1939                             table_buf[4], table_buf[5], table_buf[6])))
1940     {
1941       if (table_buf[1] | table_buf[2])
1942         ilm.MinFocal = bcd2dec(table_buf[1]) * 100 + bcd2dec(table_buf[2]);
1943       if (table_buf[3] | table_buf[4])
1944         ilm.MaxFocal = bcd2dec(table_buf[3]) * 100 + bcd2dec(table_buf[4]);
1945       if (table_buf[5])
1946         ilm.MaxAp4MinFocal = bcd2dec(table_buf[5]) / 10.0f;
1947       if (table_buf[6])
1948         ilm.MaxAp4MaxFocal = bcd2dec(table_buf[6]) / 10.0f;
1949       parseSonyLensFeatures(table_buf[0], table_buf[7]);
1950     }
1951     free(table_buf);
1952   }
1953   else if ((tag == 0xb02b) && !imgdata.sizes.raw_inset_crops[0].cwidth &&
1954            (len == 2))
1955   {
1956     imgdata.sizes.raw_inset_crops[0].cheight = get4();
1957     imgdata.sizes.raw_inset_crops[0].cwidth = get4();
1958   }
1959   else if (tag == 0xb041)
1960   {
1961     imgdata.shootinginfo.ExposureMode = get2();
1962   }
1963   else if ((tag == 0xb043) &&
1964            (len == 1) &&
1965            tagtypeIs(LIBRAW_EXIFTAG_TYPE_SHORT))
1966   {
1967     imSony.AFAreaMode = get2();
1968   }
1969 }
1970 
1971 class checked_buffer_t
1972 {
1973 public:
1974     // create with internal storage
1975     checked_buffer_t(short ord, int size) : _order(ord), storage(size+64) {
1976         _data = storage.data();
1977         _len = size;
1978     }
1979     checked_buffer_t(short ord, unsigned char *dd, int ss): _order(ord), _data(dd),_len(ss){}
1980 
1981     ushort sget2(int offset)
1982     {
1983         checkoffset(offset + 2);
1984         return libraw_sget2_static(_order, _data + offset);
1985     }
1986     void checkoffset(int off)
1987     {
1988         if (off >= _len) throw LIBRAW_EXCEPTION_IO_EOF;
1989     }
1990     unsigned char operator [] (int idx)
1991     {
1992         checkoffset(idx);
1993         return _data[idx];
1994     }
1995     unsigned sget4(int offset)
1996     {
1997         checkoffset(offset+4);
1998         return libraw_sget4_static(_order, _data + offset);
1999     }
2000     double sgetreal(int type, int offset)
2001     {
2002         int sz = libraw_tagtype_dataunit_bytes(type);
2003         checkoffset(offset + sz);
2004         return libraw_sgetreal_static(_order, type, _data + offset);
2005     }
2006 
2007     unsigned char *data() { return _data; }
2008 
2009     int tiff_sget(unsigned save, INT64 *tag_offset,
2010         unsigned *tag_id, unsigned *tag_type, INT64 *tag_dataoffset,
2011         unsigned *tag_datalen, int *tag_dataunitlen)
2012     {
2013         if ((((*tag_offset) + 12) > _len) || (*tag_offset < 0)) { // abnormal, tag buffer overrun
2014             return -1;
2015         }
2016         int pos = *tag_offset;
2017         *tag_id = sget2(pos); pos += 2;
2018         *tag_type = sget2(pos); pos += 2;
2019         *tag_datalen = sget4(pos); pos += 4;
2020         *tag_dataunitlen = libraw_tagtype_dataunit_bytes(*tag_type);
2021         if ((*tag_datalen * (*tag_dataunitlen)) > 4) {
2022             *tag_dataoffset = sget4(pos) - save;
2023             if ((*tag_dataoffset + *tag_datalen) > _len) { // abnormal, tag data buffer overrun
2024                 return -2;
2025             }
2026         }
2027         else *tag_dataoffset = *tag_offset + 8;
2028         *tag_offset += 12;
2029         return 0;
2030     }
2031 
2032 private:
2033     short _order;
2034     unsigned char *_data;
2035     int _len;
2036     std::vector<unsigned char> storage;
2037 };
2038 
2039 void LibRaw::parseSonySR2(uchar *_cbuf_SR2, unsigned SR2SubIFDOffset,
2040                           unsigned SR2SubIFDLength, unsigned dng_writer)
2041 {
2042   unsigned c;
2043   unsigned entries, tag_id, tag_type, tag_datalen;
2044   INT64 tag_offset, tag_dataoffset;
2045   int TagProcessed;
2046   int tag_dataunitlen;
2047   float num;
2048   int i;
2049   int WBCTC_count;
2050   try
2051   {
2052       checked_buffer_t cbuf_SR2(order, _cbuf_SR2, SR2SubIFDLength);
2053       entries = cbuf_SR2.sget2(0);
2054       if (entries > 1000)
2055           return;
2056       tag_offset = 2;
2057       WBCTC_count = 0;
2058       while (entries--) {
2059           if (cbuf_SR2.tiff_sget(SR2SubIFDOffset,
2060               &tag_offset, &tag_id, &tag_type, &tag_dataoffset,
2061               &tag_datalen, &tag_dataunitlen) == 0) {
2062               TagProcessed = 0;
2063               if (dng_writer == nonDNG) {
2064                   switch (tag_id) {
2065                   case 0x7300:
2066                       FORC4 cblack[c] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2067                       TagProcessed = 1;
2068                       break;
2069                   case 0x7303:
2070                       FORC4 cam_mul[GRBG_2_RGBG(c)] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2071                       TagProcessed = 1;
2072                       break;
2073                   case 0x7310:
2074                       FORC4 cblack[RGGB_2_RGBG(c)] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2075                       i = cblack[3];
2076                       FORC3 if (i > (int)cblack[c]) i = cblack[c];
2077                       FORC4 cblack[c] -= i;
2078                       black = i;
2079                       TagProcessed = 1;
2080                       break;
2081                   case 0x7313:
2082                       FORC4 cam_mul[RGGB_2_RGBG(c)] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2083                       TagProcessed = 1;
2084                       break;
2085                   case 0x74a0:
2086                       ilm.MaxAp4MaxFocal = cbuf_SR2.sgetreal(tag_type, tag_dataoffset);
2087                       TagProcessed = 1;
2088                       break;
2089                   case 0x74a1:
2090                       ilm.MaxAp4MinFocal = cbuf_SR2.sgetreal(tag_type, tag_dataoffset);
2091                       TagProcessed = 1;
2092                       break;
2093                   case 0x74a2:
2094                       ilm.MaxFocal = cbuf_SR2.sgetreal(tag_type, tag_dataoffset);
2095                       TagProcessed = 1;
2096                       break;
2097                   case 0x74a3:
2098                       ilm.MinFocal = cbuf_SR2.sgetreal(tag_type, tag_dataoffset);
2099                       TagProcessed = 1;
2100                       break;
2101                   case 0x7800:
2102                       for (i = 0; i < 3; i++)
2103                       {
2104                           num = 0.0;
2105                           for (c = 0; c < 3; c++)
2106                           {
2107                               imgdata.color.ccm[i][c] =
2108                                   (float)((short)cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * (i * 3 + c)));
2109                               num += imgdata.color.ccm[i][c];
2110                           }
2111                           if (num > 0.01)
2112                               FORC3 imgdata.color.ccm[i][c] = imgdata.color.ccm[i][c] / num;
2113                       }
2114                       TagProcessed = 1;
2115                       break;
2116                   case 0x787f:
2117                       if (tag_datalen == 3)
2118                       {
2119                           FORC3 imgdata.color.linear_max[c] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2120                           imgdata.color.linear_max[3] = imgdata.color.linear_max[1];
2121                       }
2122                       else if (tag_datalen == 1)
2123                       {
2124                           imgdata.color.linear_max[0] = imgdata.color.linear_max[1] =
2125                               imgdata.color.linear_max[2] = imgdata.color.linear_max[3] =
2126                               cbuf_SR2.sget2(tag_dataoffset);
2127                       }
2128                       TagProcessed = 1;
2129                       break;
2130                   }
2131               }
2132 
2133               if (!TagProcessed) {
2134                   if ((tag_id >= 0x7480) && (tag_id <= 0x7486)) {
2135                       i = tag_id - 0x7480;
2136                       if (Sony_SR2_wb_list[i] > 255) {
2137                           icWBCCTC[WBCTC_count][0] = Sony_SR2_wb_list[i];
2138                           FORC3 icWBCCTC[WBCTC_count][c + 1] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2139                           icWBCCTC[WBCTC_count][4] = icWBCCTC[WBCTC_count][2];
2140                           WBCTC_count++;
2141                       }
2142                       else {
2143                           FORC3 icWBC[Sony_SR2_wb_list[i]][c] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2144                           icWBC[Sony_SR2_wb_list[i]][3] = icWBC[Sony_SR2_wb_list[i]][1];
2145                       }
2146                   }
2147                   else if ((tag_id >= 0x7820) && (tag_id <= 0x782d)) {
2148                       i = tag_id - 0x7820;
2149                       if (Sony_SR2_wb_list1[i] > 255) {
2150                           icWBCCTC[WBCTC_count][0] = Sony_SR2_wb_list1[i];
2151                           FORC3 icWBCCTC[WBCTC_count][c + 1] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2152                           icWBCCTC[WBCTC_count][4] = icWBCCTC[WBCTC_count][2];
2153                           if (Sony_SR2_wb_list1[i] == 3200) {
2154                               FORC3 icWBC[LIBRAW_WBI_StudioTungsten][c] = icWBCCTC[WBCTC_count][c + 1];
2155                               icWBC[LIBRAW_WBI_StudioTungsten][3] = icWBC[LIBRAW_WBI_StudioTungsten][1];
2156                           }
2157                           WBCTC_count++;
2158                       }
2159                       else {
2160                           FORC3 icWBC[Sony_SR2_wb_list1[i]][c] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2161                           icWBC[Sony_SR2_wb_list1[i]][3] = icWBC[Sony_SR2_wb_list1[i]][1];
2162                       }
2163                   }
2164                   else if (tag_id == 0x7302) {
2165                       FORC4 icWBC[LIBRAW_WBI_Auto][GRBG_2_RGBG(c)] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2166                   }
2167                   else if (tag_id == 0x7312) {
2168                       FORC4 icWBC[LIBRAW_WBI_Auto][RGGB_2_RGBG(c)] = cbuf_SR2.sget2(tag_dataoffset + tag_dataunitlen * c);
2169                   }
2170               }
2171           }
2172       }
2173   }
2174   catch (...)
2175   {
2176       return;
2177   }
2178 }
2179 
2180 void LibRaw::parseSonySRF(unsigned len)
2181 {
2182 
2183   if ((len > 0xfffff) || (len == 0))
2184     return;
2185 
2186   INT64 save = ftell(ifp);
2187   INT64 offset =  0x0310c0 - save; /* for non-DNG this value normally is 0x8ddc */
2188   if (len < offset || offset < 0)
2189     return;
2190   try {
2191 
2192       INT64 decrypt_len = offset >> 2; /* master key offset value is the next
2193                                           un-encrypted metadata field after SRF0 */
2194 
2195       unsigned i, nWB;
2196       unsigned MasterKey, SRF2Key=0;
2197       INT64 srf_offset, tag_offset, tag_dataoffset;
2198       int tag_dataunitlen;
2199       //uchar *srf_buf;
2200       ushort entries;
2201       unsigned tag_id, tag_type, tag_datalen;
2202 
2203       //srf_buf = (uchar *)malloc(len+64);
2204       checked_buffer_t srf_buf(order, len);
2205       fread(srf_buf.data(), len, 1, ifp);
2206 
2207       offset += srf_buf[offset] << 2;
2208 
2209       /* master key is stored in big endian */
2210       MasterKey = ((unsigned)srf_buf[offset] << 24) |
2211           ((unsigned)srf_buf[offset + 1] << 16) |
2212           ((unsigned)srf_buf[offset + 2] << 8) |
2213           (unsigned)srf_buf[offset + 3];
2214 
2215       /* skip SRF0 */
2216       srf_offset = 0;
2217       entries = srf_buf.sget2(srf_offset);
2218       if (entries > 1000)
2219           goto restore_after_parseSonySRF;
2220       offset = srf_offset + 2;
2221       srf_offset = srf_buf.sget4(offset + 12 * entries) - save; /* SRF0 ends with SRF1 abs. position */
2222 
2223       /* get SRF1, it has fixed 40 bytes length and contains keys to decode metadata
2224        * and raw data */
2225       if (srf_offset < 0 || decrypt_len < srf_offset / 4)
2226           goto restore_after_parseSonySRF;
2227       sony_decrypt((unsigned *)(srf_buf.data() + srf_offset), decrypt_len - srf_offset / 4,
2228           1, MasterKey);
2229       entries = srf_buf.sget2(srf_offset);
2230       if (entries > 1000)
2231           goto restore_after_parseSonySRF;
2232       offset = srf_offset + 2;
2233       tag_offset = offset;
2234 
2235       while (entries--) {
2236           if (tiff_sget(save, srf_buf.data(), len,
2237               &tag_offset, &tag_id, &tag_type, &tag_dataoffset,
2238               &tag_datalen, &tag_dataunitlen) == 0) {
2239               if (tag_id == 0x0000) {
2240                   SRF2Key = srf_buf.sget4(tag_dataoffset);
2241               }
2242               else if (tag_id == 0x0001) {
2243                   /*RawDataKey =*/ srf_buf.sget4(tag_dataoffset);
2244               }
2245           }
2246           else goto restore_after_parseSonySRF;
2247       }
2248       offset = tag_offset;
2249 
2250       /* get SRF2 */
2251       srf_offset = srf_buf.sget4(offset) - save; /* SRFn ends with SRFn+1 position */
2252       if (srf_offset < 0 || decrypt_len < srf_offset / 4)
2253           goto restore_after_parseSonySRF;
2254       sony_decrypt((unsigned *)(srf_buf.data() + srf_offset), decrypt_len - srf_offset / 4,
2255           1, SRF2Key);
2256 
2257       entries = srf_buf.sget2(srf_offset);
2258       if (entries > 1000)
2259           goto restore_after_parseSonySRF;
2260       offset = srf_offset + 2;
2261       tag_offset = offset;
2262 
2263       while (entries--) {
2264           if (srf_buf.tiff_sget(save,
2265               &tag_offset, &tag_id, &tag_type, &tag_dataoffset,
2266               &tag_datalen, &tag_dataunitlen) == 0) {
2267               if ((tag_id >= 0x00c0) && (tag_id <= 0x00ce)) {
2268                   i = (tag_id - 0x00c0) % 3;
2269                   nWB = (tag_id - 0x00c0) / 3;
2270                   icWBC[Sony_SRF_wb_list[nWB]][i] = srf_buf.sget4(tag_dataoffset);
2271                   if (i == 1) {
2272                       icWBC[Sony_SRF_wb_list[nWB]][3] =
2273                           icWBC[Sony_SRF_wb_list[nWB]][i];
2274                   }
2275               }
2276               else if ((tag_id >= 0x00d0) && (tag_id <= 0x00d2)) {
2277                   i = (tag_id - 0x00d0) % 3;
2278                   cam_mul[i] = srf_buf.sget4(tag_dataoffset);
2279                   if (i == 1) {
2280                       cam_mul[3] = cam_mul[i];
2281                   }
2282               }
2283               else switch (tag_id) {
2284                   /*
2285                   0x0002  SRF6Offset
2286                   0x0003  SRFDataOffset (?)
2287                   0x0004  RawDataOffset
2288                   0x0005  RawDataLength
2289                   */
2290               case 0x0043:
2291                   ilm.MaxAp4MaxFocal = srf_buf.sgetreal(tag_type, tag_dataoffset);
2292                   break;
2293               case 0x0044:
2294                   ilm.MaxAp4MinFocal = srf_buf.sgetreal(tag_type, tag_dataoffset);
2295                   break;
2296               case 0x0045:
2297                   ilm.MinFocal = srf_buf.sgetreal(tag_type, tag_dataoffset);
2298                   break;
2299               case 0x0046:
2300                   ilm.MaxFocal = srf_buf.sgetreal(tag_type, tag_dataoffset);
2301                   break;
2302               }
2303           }
2304           else goto restore_after_parseSonySRF;
2305       }
2306       offset = tag_offset;
2307 
2308   restore_after_parseSonySRF:;
2309   }
2310   catch (...) // srf_buf can raise IO_EOF exception, catch it and return usual way
2311   {
2312       fseek(ifp, save, SEEK_SET);
2313       return;
2314   }
2315   fseek(ifp, save, SEEK_SET);
2316 }