Commit 5ccd4c43035df90b493ebdfd40bf9afdc51579c0

Authored by Imanol-Mikel Barba Sabariego
1 parent 36186f24

Fixed region and relative chunk calculation from coords. Fixed bug when chunks w…

…ere not generated in region file. Fixed potential crash when header length is 0
@@ -8,8 +8,8 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData); @@ -8,8 +8,8 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData);
8 8
9 RegionID translateChunkToRegion(int x, int z) { 9 RegionID translateChunkToRegion(int x, int z) {
10 RegionID region; 10 RegionID region;
11 - region.x = x/CHUNKS_PER_REGION;  
12 - region.z = z/CHUNKS_PER_REGION; 11 + region.x = floor((double)x/CHUNKS_PER_REGION);
  12 + region.z = floor((double)z/CHUNKS_PER_REGION);
13 return region; 13 return region;
14 } 14 }
15 15
@@ -20,16 +20,16 @@ RegionID translateCoordsToRegion(double x, double y, double z) { @@ -20,16 +20,16 @@ RegionID translateCoordsToRegion(double x, double y, double z) {
20 20
21 ChunkID translateCoordsToChunk(double x, double y, double z) { 21 ChunkID translateCoordsToChunk(double x, double y, double z) {
22 ChunkID chunk; 22 ChunkID chunk;
23 - chunk.x = x/BLOCKS_PER_CHUNK;  
24 - chunk.z = z/BLOCKS_PER_CHUNK; 23 + chunk.x = floor((double)x/BLOCKS_PER_CHUNK);
  24 + chunk.z = floor((double)z/BLOCKS_PER_CHUNK);
25 return chunk; 25 return chunk;
26 } 26 }
27 27
28 int overwriteChunk(const char* regionFolder, ChunkID chunk, void* chunkData, size_t chunkLength) { 28 int overwriteChunk(const char* regionFolder, ChunkID chunk, void* chunkData, size_t chunkLength) {
29 RegionID region = translateChunkToRegion(chunk.x,chunk.z); 29 RegionID region = translateChunkToRegion(chunk.x,chunk.z);
30 ChunkID relativeChunk; 30 ChunkID relativeChunk;
31 - relativeChunk.x = chunk.x % 32;  
32 - relativeChunk.z = chunk.z % 32; 31 + relativeChunk.x = chunk.x & 31;
  32 + relativeChunk.z = chunk.z & 31;
33 33
34 char* regionFilename = calloc(MAX_REGION_FILENAME_LENGTH + strlen(regionFolder),sizeof(char)); 34 char* regionFilename = calloc(MAX_REGION_FILENAME_LENGTH + strlen(regionFolder),sizeof(char));
35 sprintf(regionFilename,"%s/r.%d.%d.mca",regionFolder,region.x,region.z); 35 sprintf(regionFilename,"%s/r.%d.%d.mca",regionFolder,region.x,region.z);
@@ -110,8 +110,8 @@ int overwriteChunk(const char* regionFolder, ChunkID chunk, void* chunkData, siz @@ -110,8 +110,8 @@ int overwriteChunk(const char* regionFolder, ChunkID chunk, void* chunkData, siz
110 ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) { 110 ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) {
111 RegionID region = translateChunkToRegion(chunk.x,chunk.z); 111 RegionID region = translateChunkToRegion(chunk.x,chunk.z);
112 ChunkID relativeChunk; 112 ChunkID relativeChunk;
113 - relativeChunk.x = chunk.x % 32;  
114 - relativeChunk.z = chunk.z % 32; 113 + relativeChunk.x = chunk.x & 31;
  114 + relativeChunk.z = chunk.z & 31;
115 115
116 char* regionFilename = calloc(MAX_REGION_FILENAME_LENGTH + strlen(regionFolder),sizeof(char)); 116 char* regionFilename = calloc(MAX_REGION_FILENAME_LENGTH + strlen(regionFolder),sizeof(char));
117 sprintf(regionFilename,"%s/r.%d.%d.mca",regionFolder,region.x,region.z); 117 sprintf(regionFilename,"%s/r.%d.%d.mca",regionFolder,region.x,region.z);
@@ -135,6 +135,11 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) { @@ -135,6 +135,11 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) {
135 return -3; 135 return -3;
136 } 136 }
137 chunkHeaderOffset = (__bswap_32(chunkHeaderOffset & 0x00FFFFFF) >> 8) * CHUNK_SECTOR_SIZE; 137 chunkHeaderOffset = (__bswap_32(chunkHeaderOffset & 0x00FFFFFF) >> 8) * CHUNK_SECTOR_SIZE;
  138 + if(chunkHeaderOffset == 0) {
  139 + // Chunk not present. Hasn't been generated
  140 + close(fd);
  141 + return 0;
  142 + }
138 143
139 if(lseek(fd,chunkHeaderOffset,SEEK_SET) == -1) { 144 if(lseek(fd,chunkHeaderOffset,SEEK_SET) == -1) {
140 close(fd); 145 close(fd);
@@ -150,6 +155,16 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) { @@ -150,6 +155,16 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) {
150 } 155 }
151 header.length = __bswap_32(header.length); 156 header.length = __bswap_32(header.length);
152 ssize_t chunkLength = header.length; 157 ssize_t chunkLength = header.length;
  158 + if(header.compressionType != COMPRESSION_TYPE_ZLIB && header.compressionType != COMPRESSION_TYPE_GZIP) {
  159 + fprintf(stderr, "Invalid compression method. Proably reading the wrong data for the header\n");
  160 + close(fd);
  161 + return -6;
  162 + }
  163 + if(header.length == 0) {
  164 + fprintf(stderr, "Header length is 0. Probably reading the wrong data for the header\n");
  165 + close(fd);
  166 + return -7;
  167 + }
153 168
154 void* compressedChunk = calloc(chunkLength,sizeof(char)); 169 void* compressedChunk = calloc(chunkLength,sizeof(char));
155 ssize_t nRead = 0; 170 ssize_t nRead = 0;
@@ -163,7 +178,7 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) { @@ -163,7 +178,7 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) {
163 fprintf(stderr,"Unable to read chunk: %s\n",strerror(errno)); 178 fprintf(stderr,"Unable to read chunk: %s\n",strerror(errno));
164 close(fd); 179 close(fd);
165 free(compressedChunk); 180 free(compressedChunk);
166 - return -6; 181 + return -8;
167 } 182 }
168 totalRead += nRead; 183 totalRead += nRead;
169 } 184 }
@@ -174,7 +189,8 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) { @@ -174,7 +189,8 @@ ssize_t loadChunk(const char* regionFolder, ChunkID chunk, void** chunkData) {
174 189
175 if(chunkLength <= 0) { 190 if(chunkLength <= 0) {
176 fprintf(stderr,"Error while decompressing chunk\n"); 191 fprintf(stderr,"Error while decompressing chunk\n");
177 - return -8; 192 + free(compressedChunk);
  193 + return -9;
178 } 194 }
179 free(compressedChunk); 195 free(compressedChunk);
180 196
@@ -9,6 +9,7 @@ @@ -9,6 +9,7 @@
9 #include <stdint.h> 9 #include <stdint.h>
10 #include <string.h> 10 #include <string.h>
11 #include <byteswap.h> 11 #include <byteswap.h>
  12 +#include <math.h>
12 13
13 #include "compression.h" 14 #include "compression.h"
14 15
compression.c
@@ -45,7 +45,7 @@ ssize_t inflateGzip(void* compData, size_t compDataLen, void** unCompData, int h @@ -45,7 +45,7 @@ ssize_t inflateGzip(void* compData, size_t compDataLen, void** unCompData, int h
45 strm.avail_out = uncompLength - strm.total_out; 45 strm.avail_out = uncompLength - strm.total_out;
46 46
47 // Inflate another chunk. 47 // Inflate another chunk.
48 - err = inflate (&strm, Z_SYNC_FLUSH); 48 + err = inflate(&strm, Z_SYNC_FLUSH);
49 if(err != Z_OK && err != Z_STREAM_END) { 49 if(err != Z_OK && err != Z_STREAM_END) {
50 fprintf(stderr, "Error while inflating buffer: %d - %s.\n", err,strm.msg); 50 fprintf(stderr, "Error while inflating buffer: %d - %s.\n", err,strm.msg);
51 inflateEnd(&strm); 51 inflateEnd(&strm);