From 8d10376fad3795c35693643843f71e52bf0c677d Mon Sep 17 00:00:00 2001 From: SheetJS Date: Fri, 20 Sep 2013 15:43:02 -0700 Subject: [PATCH] version bump 0.3.0: name collision resolution It is possible for multiple streams to have the same name (albeit with different paths), so: - `FileIndex` is an array of the streams - `FullPaths` is an array of the full paths - `FullPathDir` is a full path version of `Directory` --- bin/cfb | 50 +++++++++++++++----------------------------------- cfb.js | 36 +++++++++++++++++++++++++++++++++++- package.json | 2 +- 3 files changed, 51 insertions(+), 37 deletions(-) diff --git a/bin/cfb b/bin/cfb index 9fe2615..750888b 100755 --- a/bin/cfb +++ b/bin/cfb @@ -2,44 +2,24 @@ var CFB = require('../cfb'); var args = process.argv.slice(2); + +if(args.length === 0 || !require('fs').existsSync(args[0])) { + console.error("Usage: " + process.argv[1] + " "); + process.exit(1); +} + var cfb = CFB.read(args[0], {type:'file'}); -cfb.Paths.unshift(cfb.Paths.root); - -var dir = cfb.Directory; - -var dad = new Array(cfb.Paths.length); -var paths = new Array(cfb.Paths.length); - -var q = new Array(paths.length); - -for(var i=0; i != dad.length; ++i) { dad[i]=q[i]=i; paths[i]=cfb.Paths[i]; } - -for(var i = q[0]; q.length != 0; i = q.shift()) { - if(dir[paths[i]].child) dad[dir[paths[i]].child] = i; - if(dir[paths[i]].left) { dad[dir[paths[i]].left] = dad[i]; q.push(dir[paths[i]].left); } - if(dir[paths[i]].right) { dad[dir[paths[i]].right] = dad[i]; q.push(dir[paths[i]].right); } +if(args[1] === "-q") { + console.log(cfb); + return; } - -for(var i=1; i != paths.length; ++i) { - var j = dad[i]; - if(j === 0) paths[i] = paths[0] + "/" + paths[i]; - else while(j != 0) { - paths[i] = paths[j] + "/" + paths[i]; - j = dad[j]; - } - dad[i] = 0; -} - -paths[0] += "/"; -for(var i=1; i != paths.length; ++i) if(dir[cfb.Paths[i]].type != 'stream') paths[i] += "/"; - var fs = require('fs'); -for(var i=0; i != paths.length; ++i) { - if(paths[i].slice(-1) === "/") { - console.error("mkdir " + paths[i]); - fs.mkdirSync(paths[i]); +for(var i=0; i != cfb.FullPaths.length; ++i) { + if(cfb.FullPaths[i].slice(-1) === "/") { + console.error("mkdir " + cfb.FullPaths[i]); + fs.mkdirSync(cfb.FullPaths[i]); } else { - console.error("writing " + paths[i]); - fs.writeFile(paths[i], dir[cfb.Paths[i]].content); + console.error("writing " + cfb.FullPaths[i]); + fs.writeFileSync(cfb.FullPaths[i], cfb.FileIndex[i].content); } } diff --git a/cfb.js b/cfb.js index baa423c..0cbf0b4 100644 --- a/cfb.js +++ b/cfb.js @@ -288,7 +288,7 @@ if(nmfs > 0) sector_list[minifat_start].name = "!MiniFAT"; sector_list[fat_addrs[0]].name = "!FAT"; /* [MS-CFB] 2.6.1 Compound File Directory Entry */ -var files = {}, Paths = []; +var files = {}, Paths = [], FileIndex = [], FullPaths = [], FullPathDir = {}; function read_directory(idx) { var blob, read, w; var sector = sector_list[idx].data; @@ -338,16 +338,50 @@ function read_directory(idx) { o.mt = new Date((m2 - 11644473600)*1000); } files[name] = o; + FileIndex.push(o); } } read_directory(dir_start); +function build_full_paths(Dir, pathobj, paths, patharr) { + var i; + var dad = new Array(patharr.length); + + var q = new Array(patharr.length); + + for(i=0; i != dad.length; ++i) { dad[i]=q[i]=i; paths[i]=patharr[i]; } + + for(i = q[0]; q.length !== 0; i = q.shift()) { + if(Dir[i].child) dad[Dir[i].child] = i; + if(Dir[i].left) { dad[Dir[i].left] = dad[i]; q.push(Dir[i].left); } + if(Dir[i].right) { dad[Dir[i].right] = dad[i]; q.push(Dir[i].right); } + } + + for(i=1; i !== paths.length; ++i) { + var j = dad[i]; + if(j === 0) paths[i] = paths[0] + "/" + paths[i]; + else while(j != 0) { + paths[i] = paths[j] + "/" + paths[i]; + j = dad[j]; + } + dad[i] = 0; + } + + paths[0] += "/"; + for(i=1; i !== paths.length; ++i) if(Dir[i].type !== 'stream') paths[i] += "/"; + for(i=0; i !== paths.length; ++i) pathobj[paths[i]] = FileIndex[i]; +} +build_full_paths(FileIndex, FullPathDir, FullPaths, Paths); + var root_name = Paths.shift(); Paths.root = root_name; var rval = { raw: {header: header, sectors: sectors}, Paths: Paths, + FileIndex: FileIndex, + FullPaths: FullPaths, + FullPathDir: FullPathDir, Directory: files }; diff --git a/package.json b/package.json index 3a10dc7..420ee7e 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "cfb", - "version": "0.2.1", + "version": "0.3.0", "author": "Niggler", "description": "Compound File Binary File Format extractor", "keywords": [ "cfb", "compression", "office" ],