Skip to content

Commit b9e6e9b

Browse files
authored
Merge pull request #19 from dpryan79/fix18
Fix creation of bigWig files with very very large intervals
2 parents e33d516 + 49e29ee commit b9e6e9b

File tree

2 files changed

+14
-2
lines changed

2 files changed

+14
-2
lines changed

bigWig.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ extern "C" {
5353
/*!
5454
* The library version number
5555
*/
56-
#define LIBBIGWIG_VERSION 0.3.0
56+
#define LIBBIGWIG_VERSION 0.3.1
5757

5858
/*!
5959
* The magic number of a bigWig file.

bwWrite.c

+13-1
Original file line numberDiff line numberDiff line change
@@ -780,7 +780,7 @@ int writeIndex(bigWigFile_t *fp) {
780780
//This may or may not produce the requested number of zoom levels
781781
int makeZoomLevels(bigWigFile_t *fp) {
782782
uint32_t meanBinSize, i;
783-
uint32_t multiplier = 4, zoom = 10;
783+
uint32_t multiplier = 4, zoom = 10, maxZoom = 0;
784784
uint16_t nLevels = 0;
785785

786786
meanBinSize = ((double) fp->writeBuffer->runningWidthSum)/(fp->writeBuffer->nEntries);
@@ -801,7 +801,15 @@ int makeZoomLevels(bigWigFile_t *fp) {
801801
if(!fp->hdr->zoomHdrs->indexOffset) return 4;
802802
if(!fp->hdr->zoomHdrs->idx) return 5;
803803

804+
//There's no point in having a zoom level larger than the largest chromosome
805+
//This will none the less allow at least one zoom level, which is generally needed for IGV et al.
806+
for(i=0; i<fp->cl->nKeys; i++) {
807+
if(fp->cl->len[i] > maxZoom) maxZoom = fp->cl->len[i];
808+
}
809+
if(zoom > maxZoom) zoom = maxZoom;
810+
804811
for(i=0; i<fp->hdr->nLevels; i++) {
812+
if(zoom > maxZoom) break; //prevent absurdly large zoom levels
805813
fp->hdr->zoomHdrs->level[i] = zoom;
806814
nLevels++;
807815
if(((uint32_t)-1)/multiplier < zoom) break;
@@ -887,6 +895,10 @@ uint32_t updateInterval(bigWigFile_t *fp, bwZoomBuffer_t *buffer, double *sum, d
887895
uint32_t rv = 0, offset = 0;
888896
if(!buffer) return 0;
889897
if(buffer->l+32 >= buffer->m) return 0;
898+
899+
//Make sure that we don't overflow a uint32_t by adding some huge value to start
900+
if(start + size < start) size = ((uint32_t) -1) - start;
901+
890902
if(buffer->l) {
891903
offset = buffer->l/32;
892904
} else {

0 commit comments

Comments
 (0)