added better sighash support as well as (basic) support for carboncoin
This commit is contained in:
parent
b6dfa6b822
commit
970cd756ec
4 changed files with 74 additions and 18 deletions
|
@ -971,6 +971,7 @@
|
||||||
<option value="bitcoin_mainnet" rel="0x00;0x80;0x05;0x488b21e;0x488ade4;coinb.in;coinb.in">Bitcoin (mainnet)</option>
|
<option value="bitcoin_mainnet" rel="0x00;0x80;0x05;0x488b21e;0x488ade4;coinb.in;coinb.in">Bitcoin (mainnet)</option>
|
||||||
<option value="litecoin_mainnet" rel="0x30;0xb0;0x05;0x019da462;0x019d9cfe;blockr.io_litecoin;chain.so_litecoin">Litecoin (mainnet)</option>
|
<option value="litecoin_mainnet" rel="0x30;0xb0;0x05;0x019da462;0x019d9cfe;blockr.io_litecoin;chain.so_litecoin">Litecoin (mainnet)</option>
|
||||||
<option value="dogecoin_mainnet" rel="0x1e;0x9e;0x16;0x0827421e;0x089944e4;chain.so_dogecoin;chain.so_dogecoin">Dogecoin (mainnet)</option>
|
<option value="dogecoin_mainnet" rel="0x1e;0x9e;0x16;0x0827421e;0x089944e4;chain.so_dogecoin;chain.so_dogecoin">Dogecoin (mainnet)</option>
|
||||||
|
<option value="carboncoin_mainnet" rel="0x2f;0xaf;0x05;0x488b21e;0x488ade4;false;false">Carboncoin (mainnet)</option>
|
||||||
<option value="shadowcash_mainnet" rel="0x3f;0xbf;0x7d;0xee80286a;0xee8031e8;false;false">ShadowCash (mainnet)</option>
|
<option value="shadowcash_mainnet" rel="0x3f;0xbf;0x7d;0xee80286a;0xee8031e8;false;false">ShadowCash (mainnet)</option>
|
||||||
<option value="bitcoin_testnet" rel="0x6f;0xef;0xc4;0x043587cf;0x04358394;false;false">Bitcoin (testnet)</option>
|
<option value="bitcoin_testnet" rel="0x6f;0xef;0xc4;0x043587cf;0x04358394;false;false">Bitcoin (testnet)</option>
|
||||||
|
|
||||||
|
|
79
js/coin.js
79
js/coin.js
|
@ -911,20 +911,71 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
/* generate the transaction hash to sign from a transaction input */
|
/* generate the transaction hash to sign from a transaction input */
|
||||||
r.transactionHash = function(index) {
|
r.transactionHash = function(index, sigHashType) {
|
||||||
|
|
||||||
var clone = coinjs.clone(this);
|
var clone = coinjs.clone(this);
|
||||||
|
var shType = sigHashType || 1;
|
||||||
|
|
||||||
if((clone.ins) && clone.ins[index]){
|
if((clone.ins) && clone.ins[index]){
|
||||||
|
|
||||||
|
/* black out all other ins, except this one */
|
||||||
for (var i = 0; i < clone.ins.length; i++) {
|
for (var i = 0; i < clone.ins.length; i++) {
|
||||||
if(index!=i){
|
if(index!=i){
|
||||||
clone.ins[i].script = coinjs.script();
|
clone.ins[i].script = coinjs.script();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* SIGHASH : For more info on sig hashs see https://en.bitcoin.it/wiki/OP_CHECKSIG
|
||||||
|
and https://bitcoin.org/en/developer-guide#signature-hash-type */
|
||||||
|
|
||||||
|
if(shType == 1){
|
||||||
|
//SIGHASH_ALL 0x01 #t
|
||||||
|
|
||||||
|
} else if(shType == 2){
|
||||||
|
//SIGHASH_NONE 0x02 #t
|
||||||
|
clone.outs = [];
|
||||||
|
for (var i = 0; i < clone.ins.length; i++) {
|
||||||
|
if(index!=i){
|
||||||
|
clone.ins[i].sequence = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} else if(shType == 3){
|
||||||
|
//SIGHASH_SINGLE 0x03 #t
|
||||||
|
for (var i = 0; i < clone.outs.length; i++) {
|
||||||
|
if(index!=i){
|
||||||
|
clone.outs[i].value = new BigInteger('' + Math.round((0) * 1e8), 10);
|
||||||
|
clone.outs[i].script = coinjs.script();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} else if(shType >= 128){
|
||||||
|
//SIGHASH_ANYONECANPAY 0x80 #t
|
||||||
|
clone.ins = [this.ins[index]];
|
||||||
|
clone.ins[0].script = this.ins[index].script;
|
||||||
|
if(shType>128){
|
||||||
|
if(shType==129){
|
||||||
|
// SIGHASH_ALL + SIGHASH_ANYONECANPAY
|
||||||
|
} else if(shType==130){
|
||||||
|
// SIGHASH_NONE + SIGHASH_ANYONECANPAY #t
|
||||||
|
clone.outs = [];
|
||||||
|
} else if(shType==131){
|
||||||
|
// SIGHASH_SINGLE + SIGHASH_ANYONECANPAY
|
||||||
|
for (var i = 0; i < clone.outs.length; i++) {
|
||||||
|
if(index!=i){
|
||||||
|
clone.outs[i].value = new BigInteger('' + Math.round((0) * 1e8), 10);
|
||||||
|
clone.outs[i].script = coinjs.script();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
var extract = this.extractScriptKey(index);
|
var extract = this.extractScriptKey(index);
|
||||||
clone.ins[index].script = coinjs.script(extract['script']);
|
clone.ins[index].script = coinjs.script(extract['script']);
|
||||||
|
|
||||||
var buffer = Crypto.util.hexToBytes(clone.serialize());
|
var buffer = Crypto.util.hexToBytes(clone.serialize());
|
||||||
buffer = buffer.concat(coinjs.numToBytes(parseInt(1),4));
|
buffer = buffer.concat(coinjs.numToBytes(parseInt(shType), 4));
|
||||||
var hash = Crypto.SHA256(buffer, {asBytes: true});
|
var hash = Crypto.SHA256(buffer, {asBytes: true});
|
||||||
var r = Crypto.util.bytesToHex(Crypto.SHA256(hash, {asBytes: true}));
|
var r = Crypto.util.bytesToHex(Crypto.SHA256(hash, {asBytes: true}));
|
||||||
return r;
|
return r;
|
||||||
|
@ -967,7 +1018,7 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
/* generate a signature from a transaction hash */
|
/* generate a signature from a transaction hash */
|
||||||
r.transactionSig = function(index, wif){
|
r.transactionSig = function(index, wif, sigHashType){
|
||||||
|
|
||||||
function serializeSig(r, s) {
|
function serializeSig(r, s) {
|
||||||
var rBa = r.toByteArraySigned();
|
var rBa = r.toByteArraySigned();
|
||||||
|
@ -988,7 +1039,8 @@
|
||||||
return sequence;
|
return sequence;
|
||||||
}
|
}
|
||||||
|
|
||||||
var hash = Crypto.util.hexToBytes(this.transactionHash(index));
|
var shType = sigHashType || 1;
|
||||||
|
var hash = Crypto.util.hexToBytes(this.transactionHash(index, shType));
|
||||||
|
|
||||||
if(hash){
|
if(hash){
|
||||||
var curve = EllipticCurve.getSECCurveByName("secp256k1");
|
var curve = EllipticCurve.getSECCurveByName("secp256k1");
|
||||||
|
@ -1013,7 +1065,7 @@
|
||||||
};
|
};
|
||||||
|
|
||||||
var sig = serializeSig(r, s);
|
var sig = serializeSig(r, s);
|
||||||
sig.push(parseInt(1, 10));
|
sig.push(parseInt(shType, 10));
|
||||||
|
|
||||||
return Crypto.util.bytesToHex(sig);
|
return Crypto.util.bytesToHex(sig);
|
||||||
} else {
|
} else {
|
||||||
|
@ -1084,9 +1136,10 @@
|
||||||
};
|
};
|
||||||
|
|
||||||
/* sign a "standard" input */
|
/* sign a "standard" input */
|
||||||
r.signinput = function(index, wif){
|
r.signinput = function(index, wif, sigHashType){
|
||||||
var key = coinjs.wif2pubkey(wif);
|
var key = coinjs.wif2pubkey(wif);
|
||||||
var signature = this.transactionSig(index, wif);
|
var shType = sigHashType || 1;
|
||||||
|
var signature = this.transactionSig(index, wif, shType);
|
||||||
var s = coinjs.script();
|
var s = coinjs.script();
|
||||||
s.writeBytes(Crypto.util.hexToBytes(signature));
|
s.writeBytes(Crypto.util.hexToBytes(signature));
|
||||||
s.writeBytes(Crypto.util.hexToBytes(key['pubkey']));
|
s.writeBytes(Crypto.util.hexToBytes(key['pubkey']));
|
||||||
|
@ -1095,8 +1148,9 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
/* signs a time locked / hodl input */
|
/* signs a time locked / hodl input */
|
||||||
r.signhodl = function(index, wif){
|
r.signhodl = function(index, wif, sigHashType){
|
||||||
var signature = this.transactionSig(index, wif);
|
var shType = sigHashType || 1;
|
||||||
|
var signature = this.transactionSig(index, wif, shType);
|
||||||
var redeemScript = this.ins[index].script.buffer
|
var redeemScript = this.ins[index].script.buffer
|
||||||
var s = coinjs.script();
|
var s = coinjs.script();
|
||||||
s.writeBytes(Crypto.util.hexToBytes(signature));
|
s.writeBytes(Crypto.util.hexToBytes(signature));
|
||||||
|
@ -1106,7 +1160,7 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
/* sign a multisig input */
|
/* sign a multisig input */
|
||||||
r.signmultisig = function(index, wif){
|
r.signmultisig = function(index, wif, sigHashType){
|
||||||
|
|
||||||
function scriptListPubkey(redeemScript){
|
function scriptListPubkey(redeemScript){
|
||||||
var r = {};
|
var r = {};
|
||||||
|
@ -1131,8 +1185,9 @@
|
||||||
}
|
}
|
||||||
|
|
||||||
var redeemScript = (this.ins[index].script.chunks[this.ins[index].script.chunks.length-1]==174) ? this.ins[index].script.buffer : this.ins[index].script.chunks[this.ins[index].script.chunks.length-1];
|
var redeemScript = (this.ins[index].script.chunks[this.ins[index].script.chunks.length-1]==174) ? this.ins[index].script.buffer : this.ins[index].script.chunks[this.ins[index].script.chunks.length-1];
|
||||||
var sighash = Crypto.util.hexToBytes(this.transactionHash(index));
|
var shType = sigHashType || 1;
|
||||||
var signature = Crypto.util.hexToBytes(this.transactionSig(index, wif));
|
var sighash = Crypto.util.hexToBytes(this.transactionHash(index, shType));
|
||||||
|
var signature = Crypto.util.hexToBytes(this.transactionSig(index, wif, shType));
|
||||||
var s = coinjs.script();
|
var s = coinjs.script();
|
||||||
|
|
||||||
s.writeOp(0);
|
s.writeOp(0);
|
||||||
|
|
|
@ -1125,10 +1125,10 @@ $(document).ready(function() {
|
||||||
r += (obj.message) ? ' '+obj.message : '';
|
r += (obj.message) ? ' '+obj.message : '';
|
||||||
r = (r!='') ? r : ' Failed to broadcast'; // build response
|
r = (r!='') ? r : ' Failed to broadcast'; // build response
|
||||||
$("#rawTransactionStatus").addClass('alert-danger').removeClass('alert-success').removeClass("hidden").html(r).prepend('<span class="glyphicon glyphicon-exclamation-sign"></span>');
|
$("#rawTransactionStatus").addClass('alert-danger').removeClass('alert-success').removeClass("hidden").html(r).prepend('<span class="glyphicon glyphicon-exclamation-sign"></span>');
|
||||||
console.error(JSON.stringify(data, null, 4));
|
// console.error(JSON.stringify(data, null, 4));
|
||||||
},
|
},
|
||||||
success: function(data) {
|
success: function(data) {
|
||||||
console.info(JSON.stringify(data, null, 4));
|
// console.info(JSON.stringify(data, null, 4));
|
||||||
if((data.status && data.data) && data.status=='success'){
|
if((data.status && data.data) && data.status=='success'){
|
||||||
$("#rawTransactionStatus").addClass('alert-success').removeClass('alert-danger').removeClass("hidden").html(' Txid: ' + data.data.txid);
|
$("#rawTransactionStatus").addClass('alert-success').removeClass('alert-danger').removeClass("hidden").html(' Txid: ' + data.data.txid);
|
||||||
} else {
|
} else {
|
||||||
|
|
8
sha1sum
8
sha1sum
|
@ -1,9 +1,9 @@
|
||||||
---- Version 1.2 2016.07.28 ----
|
---- Version 1.2 2016.09.04 ----
|
||||||
77e4519962e2f6a9fc93342137dbb31c33b76b04 ./js/aes.js
|
77e4519962e2f6a9fc93342137dbb31c33b76b04 ./js/aes.js
|
||||||
3a09a8fc0cfe828b57fc798d668234d0490ee1a6 ./js/bootstrap-datetimepicker.min.js
|
3a09a8fc0cfe828b57fc798d668234d0490ee1a6 ./js/bootstrap-datetimepicker.min.js
|
||||||
253711c6d825de55a8360552573be950da180614 ./js/bootstrap.min.js
|
253711c6d825de55a8360552573be950da180614 ./js/bootstrap.min.js
|
||||||
97eff91b9b913dae9b25f5bb308a9599f2cbb16e ./js/coinbin.js
|
fe075342aed7c842d03aba10e1bf0d4239fc14cb ./js/coinbin.js
|
||||||
1bb89d9fc4147b53a963009af3e28d7928497947 ./js/coin.js
|
b93555d2e150a10adb02144d30230966fe03bbee ./js/coin.js
|
||||||
988565bc2cb402d63ed5c5fd7ff47c4278efc2c5 ./js/collapse.js
|
988565bc2cb402d63ed5c5fd7ff47c4278efc2c5 ./js/collapse.js
|
||||||
9ba5ede3d7f9d4c8fd623395f196adfdcf7e970f ./js/crypto-min.js
|
9ba5ede3d7f9d4c8fd623395f196adfdcf7e970f ./js/crypto-min.js
|
||||||
f7c09f2f5a721371e7d478050119f7e2d58e3ef9 ./js/crypto-sha256-hmac.js
|
f7c09f2f5a721371e7d478050119f7e2d58e3ef9 ./js/crypto-sha256-hmac.js
|
||||||
|
@ -30,4 +30,4 @@ de51a8494180a6db074af2dee2383f0a363c5b08 ./fonts/glyphicons-halflings-regular.s
|
||||||
278e49a86e634da6f2a02f3b47dd9d2a8f26210f ./fonts/glyphicons-halflings-regular.woff
|
278e49a86e634da6f2a02f3b47dd9d2a8f26210f ./fonts/glyphicons-halflings-regular.woff
|
||||||
44bc1850f570972267b169ae18f1cb06b611ffa2 ./fonts/glyphicons-halflings-regular.ttf
|
44bc1850f570972267b169ae18f1cb06b611ffa2 ./fonts/glyphicons-halflings-regular.ttf
|
||||||
b4d3a33913a0877684909f7edf8b79bf9192b0a7 ./README.md
|
b4d3a33913a0877684909f7edf8b79bf9192b0a7 ./README.md
|
||||||
23d2a58eee85cb6f344d44aa5eb1b9acf8869610 ./index.html
|
e4dd0465f6b4de21d0ac6f81deaa7872479ef705 ./index.html
|
||||||
|
|
Loading…
Reference in a new issue