MythTV  master
rom_metadata.cpp
Go to the documentation of this file.
1 #include "config.h"
2 #include "rom_metadata.h"
3 
4 #include <QFile>
5 
6 #include <mythcontext.h>
7 
8 #include "zlib.h"
9 #include MINIZIP_UNZIP_H
10 #undef Z_NULL
11 #define Z_NULL nullptr
12 
13 static int calcOffset(const QString& GameType, uLong filesize) {
14  int result;
15  uLong rom_size;
16 
17  result = 0;
18 
19  if (GameType == "NES")
20  {
21  result = 16;
22  }
23  else if (GameType == "SNES")
24  {
25  rom_size = (filesize / 0x2000) * 0x2000;
26 
27  if (rom_size < filesize)
28  result = filesize - rom_size;
29  }
30  else if (GameType == "PCE")
31  {
32  if (filesize & 0x0FFF)
33  result = filesize & 0x0FFF;
34 
35  }
36 
37  return result;
38 }
39 
40 static QString crcStr(uLong crc)
41 {
42  QString tmpcrc("");
43 
44  tmpcrc = QString("%1").arg( crc, 0, 16 );
45  if (tmpcrc == "0")
46  tmpcrc = "";
47  else
48  tmpcrc = tmpcrc.rightJustified(8, '0');
49 
50  return tmpcrc;
51 }
52 
53 // Return the crc32 info for this rom. (ripped mostly from the old neshandler.cpp source)
54 QString crcinfo(const QString& romname, const QString& GameType, QString *key, RomDBMap *romDB)
55 {
56  // Get CRC of file
57  char block[32768] = "";
58  uLong crc = crc32(0, Z_NULL, 0);
59  QString crcRes;
60  unz_file_info file_info;
61  int offset;
62  unzFile zf;
63  int blocksize;
64 
65  blocksize = 8192;
66 #if 0
67  LOG(VB_GENERAL, LOG_DEBUG,
68  QString("crcinfo : %1 : %2 :").arg(romname).arg(GameType));
69 #endif
70 
71  if ((zf = unzOpen(qPrintable(romname))))
72  {
73  int FoundFile;
74  for (FoundFile = unzGoToFirstFile(zf); FoundFile == UNZ_OK;
75  FoundFile = unzGoToNextFile(zf))
76  {
77  if (unzOpenCurrentFile(zf) == UNZ_OK)
78  {
79  char filename_inzip[256];
80  unzGetCurrentFileInfo(zf,&file_info,filename_inzip,sizeof(filename_inzip),nullptr,0,nullptr,0);
81 
82  offset = calcOffset(GameType, file_info.uncompressed_size);
83 
84  if (offset > 0)
85  unzReadCurrentFile(zf, block, offset);
86 
87  // Get CRC of rom data
88  int count;
89  while ((count = unzReadCurrentFile(zf, block, blocksize)) > 0)
90  {
91  crc = crc32(crc, (Bytef *)block, (uInt)count);
92  }
93  crcRes = crcStr(crc);
94  *key = QString("%1:%2")
95  .arg(crcRes)
96  .arg(filename_inzip);
97 
98  if (romDB->contains(*key))
99  {
100  unzCloseCurrentFile(zf);
101  break;
102  }
103 
104  unzCloseCurrentFile(zf);
105  }
106  }
107  unzClose(zf);
108  }
109  else
110  {
111  QFile f(romname);
112 
113  if (f.open(QIODevice::ReadOnly))
114  {
115  offset = calcOffset(GameType, f.size());
116 
117  if (offset > 0)
118  f.read(block, offset);
119 
120  // Get CRC of rom data
121  qint64 count;
122  while ((count = f.read(block, blocksize)) > 0)
123  {
124  crc = crc32(crc, (Bytef *)block, (uInt)count);
125  }
126 
127  crcRes = crcStr(crc);
128  *key = QString("%1:").arg(crcRes);
129  f.close();
130  }
131  }
132 
133  return crcRes;
134 }
135 
static int calcOffset(const QString &GameType, uLong filesize)
QMap< QString, RomData > RomDBMap
Definition: rom_metadata.h:45
static QString crcStr(uLong crc)
virtual int size(void) const
QString crcinfo(const QString &romname, const QString &GameType, QString *key, RomDBMap *romDB)
#define LOG(_MASK_, _LEVEL_, _STRING_)
Definition: mythlogging.h:41
static uint32_t crc32(const unsigned char *data, int len)
Definition: dsmcc.cpp:618
#define Z_NULL