Read block as a buffer

This commit is contained in:
Braydon Fuller 2015-07-07 23:24:22 -04:00
parent 218755d9a6
commit 9c2726b09c
1 changed files with 34 additions and 26 deletions

View File

@ -189,6 +189,8 @@ struct async_block_data {
std::string err_msg; std::string err_msg;
std::string hash; std::string hash;
int64_t height; int64_t height;
char* buffer;
uint32_t size;
CBlock cblock; CBlock cblock;
CBlockIndex* cblock_index; CBlockIndex* cblock_index;
Eternal<Function> callback; Eternal<Function> callback;
@ -835,34 +837,45 @@ static void
async_get_block(uv_work_t *req) { async_get_block(uv_work_t *req) {
async_block_data* data = static_cast<async_block_data*>(req->data); async_block_data* data = static_cast<async_block_data*>(req->data);
if (data->height != -1) {
CBlockIndex* pblockindex = chainActive[data->height];
CBlock cblock;
if (ReadBlockFromDisk(cblock, pblockindex)) {
data->cblock = cblock;
data->cblock_index = pblockindex;
} else {
data->err_msg = std::string("Block not found.");
}
return;
}
std::string strHash = data->hash; std::string strHash = data->hash;
uint256 hash(strHash); uint256 hash(strHash);
if (mapBlockIndex.count(hash) == 0) { if (mapBlockIndex.count(hash) == 0) {
data->err_msg = std::string("Block not found."); data->err_msg = std::string("Block not found.");
} else { } else {
CBlock block;
CBlockIndex* pblockindex = mapBlockIndex[hash]; CBlockIndex* pblockindex = mapBlockIndex[hash];
if(!ReadBlockFromDisk(block, pblockindex)) { const CDiskBlockPos& pos = pblockindex->GetBlockPos();
data->err_msg = std::string("Can't read block from disk");
} else { // We can read directly from the file, and pass that, we don't need to
data->cblock = block; // deserialize the entire block only for it to then be serialized
data->cblock_index = pblockindex; // and then deserialized again in JavaScript
// Open history file to read
CAutoFile filein(OpenBlockFile(pos, true), SER_DISK, CLIENT_VERSION);
if (filein.IsNull()) {
data->err_msg = std::string("ReadBlockFromDisk: OpenBlockFile failed");
return;
} }
// Get the actual file, seeked position and rewind a uint32_t
FILE* blockFile = filein.release();
long int filePos = ftell(blockFile);
fseek(blockFile, filePos - sizeof(uint32_t), SEEK_SET);
// Read the size of the block
uint32_t size = 0;
fread(&size, sizeof(uint32_t), 1, blockFile);
// Read block
char buffer[size];
fread((void *)buffer, sizeof(char), size, blockFile);
fclose(blockFile);
data->buffer = buffer;
data->size = size;
data->cblock_index = pblockindex;
} }
} }
@ -883,19 +896,14 @@ async_get_block_after(uv_work_t *req) {
node::FatalException(try_catch); node::FatalException(try_catch);
} }
} else { } else {
const CBlock& cblock = data->cblock;
CBlockIndex* cblock_index = data->cblock_index; CBlockIndex* cblock_index = data->cblock_index;
CDataStream ssBlock(SER_NETWORK, PROTOCOL_VERSION); Local<Value> rawNodeBuffer = node::Buffer::New(isolate, data->buffer, data->size);
ssBlock << cblock;
std::string strHex = HexStr(ssBlock.begin(), ssBlock.end());
Local<String> jsblock = NanNew<String>(strHex);
const unsigned argc = 2; const unsigned argc = 2;
Local<Value> argv[argc] = { Local<Value> argv[argc] = {
Local<Value>::New(isolate, NanNull()), Local<Value>::New(isolate, NanNull()),
Local<Value>::New(isolate, jsblock) rawNodeBuffer
}; };
TryCatch try_catch; TryCatch try_catch;
cb->Call(isolate->GetCurrentContext()->Global(), argc, argv); cb->Call(isolate->GetCurrentContext()->Global(), argc, argv);