Skip to content

Commit 3bc2923

Browse files
committed
version bump 0.4.0: Fixes from JS-XLS + travis
1 parent 8d10376 commit 3bc2923

File tree

5 files changed

+61
-15
lines changed

5 files changed

+61
-15
lines changed

Diff for: .travis.yml

+8
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
language: node_js
2+
node_js:
3+
- "0.10"
4+
- "0.8"
5+
before_install:
6+
- "npm install -g mocha"
7+
before_script:
8+
- "make init"

Diff for: Makefile

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
.PHONY: init test clean
2+
test: init
3+
mocha -R spec
4+
5+
init:
6+
if [ ! -e test_files ]; then git clone https://github.com/Niggler/test_files; fi
7+
cd test_files; make
8+
9+
clean:
10+
rm -rf ./test_files/

Diff for: cfb.js

+28-14
Original file line numberDiff line numberDiff line change
@@ -112,16 +112,19 @@ function ReadShift(size, t) {
112112
}
113113
this.l+=size; return o;
114114
}
115+
115116
function CheckField(hexstr, fld) {
116117
var m = this.slice(this.l, this.l+hexstr.length/2).hexlify('hex');
117118
if(m !== hexstr) throw (fld||"") + 'Expected ' + hexstr + ' saw ' + m;
118119
this.l += hexstr.length/2;
119120
}
121+
120122
function WarnField(hexstr, fld) {
121123
var m = this.slice(this.l, this.l+hexstr.length/2).hexlify('hex');
122124
if(m !== hexstr) console.error((fld||"") + 'Expected ' + hexstr +' saw ' + m);
123125
this.l += hexstr.length/2;
124126
}
127+
125128
function prep_blob(blob, pos) {
126129
blob.read_shift = ReadShift.bind(blob);
127130
blob.chk = CheckField;
@@ -237,9 +240,9 @@ for(j = 0; blob.l != 512; ) {
237240

238241

239242
/** Break the file up into sectors */
240-
if(file.length%ssz!==0) throw "File Length: Expected multiple of "+ssz;
243+
if(file.length%ssz!==0) console.error("CFB: size " + file.length + " % "+ssz);
241244

242-
var nsectors = (file.length - ssz)/ssz;
245+
var nsectors = Math.ceil((file.length - ssz)/ssz);
243246
var sectors = [];
244247
for(var i=1; i != nsectors + 1; ++i) sectors[i-1] = file.slice(i*ssz,(i+1)*ssz);
245248

@@ -250,12 +253,14 @@ function sleuth_fat(idx, cnt) {
250253
if(cnt !== 0) throw "DIFAT chain shorter than expected";
251254
return;
252255
}
253-
var sector = sectors[idx];
254-
for(var i = 0; i != ssz/4-1; ++i) {
255-
if((q = sector.readUInt32LE(i*4)) === ENDOFCHAIN) break;
256-
fat_addrs.push(q);
256+
if(idx !== FREESECT) {
257+
var sector = sectors[idx];
258+
for(var i = 0; i != ssz/4-1; ++i) {
259+
if((q = sector.readUInt32LE(i*4)) === ENDOFCHAIN) break;
260+
fat_addrs.push(q);
261+
}
262+
sleuth_fat(sector.readUInt32LE(ssz-4),cnt - 1);
257263
}
258-
sleuth_fat(sector.readUInt32LE(ssz-4),cnt - 1);
259264
}
260265
sleuth_fat(difat_start, ndfs);
261266

@@ -284,7 +289,7 @@ for(i=0; i != sectors.length; ++i) {
284289
sector_list[i].data = Array(buf.map(get_sector)).toBuffer();
285290
}
286291
sector_list[dir_start].name = "!Directory";
287-
if(nmfs > 0) sector_list[minifat_start].name = "!MiniFAT";
292+
if(nmfs > 0 && minifat_start !== ENDOFCHAIN) sector_list[minifat_start].name = "!MiniFAT";
288293
sector_list[fat_addrs[0]].name = "!FAT";
289294

290295
/* [MS-CFB] 2.6.1 Compound File Directory Entry */
@@ -314,18 +319,26 @@ function read_directory(idx) {
314319
o.size = read(4);
315320
if(o.type === 'root') { //root entry
316321
minifat_store = o.start;
317-
if(nmfs > 0) sector_list[minifat_store].name = "!StreamData";
322+
if(nmfs > 0 && minifat_store !== ENDOFCHAIN) sector_list[minifat_store].name = "!StreamData";
318323
minifat_size = o.size;
319324
} else if(o.size >= ms_cutoff_size) {
320325
o.storage = 'fat';
326+
try {
327+
sector_list[o.start].name = o.name;
328+
o.content = sector_list[o.start].data.slice(0,o.size);
329+
} catch(e) {
330+
o.start = o.start - 1;
321331
sector_list[o.start].name = o.name;
322332
o.content = sector_list[o.start].data.slice(0,o.size);
333+
}
323334
prep_blob(o.content);
324335
} else {
325336
o.storage = 'minifat';
326337
w = o.start * mssz;
327-
o.content = sector_list[minifat_store].data.slice(w,w+o.size);
328-
prep_blob(o.content);
338+
if(minifat_store !== ENDOFCHAIN) {
339+
o.content = sector_list[minifat_store].data.slice(w,w+o.size);
340+
prep_blob(o.content);
341+
}
329342
}
330343
if(o.ctime) {
331344
var ct = blob.slice(blob.l-24, blob.l-16);
@@ -351,13 +364,14 @@ function build_full_paths(Dir, pathobj, paths, patharr) {
351364

352365
for(i=0; i != dad.length; ++i) { dad[i]=q[i]=i; paths[i]=patharr[i]; }
353366

354-
for(i = q[0]; q.length !== 0; i = q.shift()) {
367+
for(i = q[0]; typeof i !== "undefined"; i = q.shift()) {
355368
if(Dir[i].child) dad[Dir[i].child] = i;
356369
if(Dir[i].left) { dad[Dir[i].left] = dad[i]; q.push(Dir[i].left); }
357370
if(Dir[i].right) { dad[Dir[i].right] = dad[i]; q.push(Dir[i].right); }
358371
}
359372

360373
for(i=1; i !== paths.length; ++i) {
374+
if(Dir[i].type === "unknown") continue;
361375
var j = dad[i];
362376
if(j === 0) paths[i] = paths[0] + "/" + paths[i];
363377
else while(j != 0) {
@@ -426,14 +440,14 @@ return this;
426440
var NOSTREAM = 0xFFFFFFFF;
427441
var HEADER_CLSID = '00000000000000000000000000000000';
428442
/* 2.6.1 Compound File Directory Entry */
429-
var EntryTypes = ['unknown','storage','stream',null,null,'root'];
443+
var EntryTypes = ['unknown','storage','stream','lockbytes','property','root'];
430444
}
431445

432446
var CFB_utils = {
433447
ReadShift: ReadShift,
434448
WarnField: WarnField,
435449
CheckField: CheckField,
436-
prep_blob: prep_blob,
450+
prep_blob: prep_blob,
437451
bconcat: bconcat
438452
};
439453

Diff for: package.json

+4-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "cfb",
3-
"version": "0.3.0",
3+
"version": "0.4.0",
44
"author": "Niggler",
55
"description": "Compound File Binary File Format extractor",
66
"keywords": [ "cfb", "compression", "office" ],
@@ -9,6 +9,9 @@
99
},
1010
"main": "./cfb",
1111
"repository": { "type":"git", "url":"git://github.com/Niggler/js-cfb.git" },
12+
"scripts": {
13+
"test": "make test"
14+
},
1215
"bugs": { "url": "https://github.com/Niggler/js-cfb/issues" },
1316
"license": "Apache 2.0"
1417
}

Diff for: test.js

+11
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
var CFB;
2+
var fs = require('fs');
3+
describe('source', function() { it('should load', function() { CFB = require('./'); }); });
4+
var files = fs.readdirSync('test_files').filter(function(x){return x.substr(-4)==".xls";});
5+
files.forEach(function(x) {
6+
describe(x, function() {
7+
it('should parse ' + x, function() {
8+
var cfb = CFB.read('./test_files/' + x, {type: "file"});
9+
});
10+
});
11+
});

0 commit comments

Comments
 (0)