forked from blockchain/unused-My-Wallet
-
Notifications
You must be signed in to change notification settings - Fork 0
/
signer.min.js
1 lines (1 loc) · 27.8 KB
/
signer.min.js
1
function exceptionToString(b){var a="";for(var c in b){a+="property: "+c+" value: ["+b[c]+"]\n"}return"toString(): value: ["+b.toString()+"]"}function generateNewMiniPrivateKey(){while(true){MyWallet._seed();var c=new Bitcoin.ECKey(false);var b="S"+Bitcoin.Base58.encode(c.priv).substr(0,21);var f=Crypto.SHA256(b+"?",{asBytes:true});if(f[0]==0){var a=Crypto.SHA256(b,{asBytes:true});var d=new Bitcoin.ECKey(a);if(MyWallet.addPrivateKey(d)){return{key:d,miniKey:b}}}}}function IsCanonicalSignature(c){if(c.length<9){throw"Non-canonical signature: too short"}if(c.length>73){throw"Non-canonical signature: too long"}var b=c[c.length-1];if(b!=SIGHASH_ALL&&b!=SIGHASH_NONE&&b!=SIGHASH_SINGLE&&b!=SIGHASH_ANYONECANPAY){throw"Non-canonical signature: unknown hashtype byte "+b}if(c[0]!=48){throw"Non-canonical signature: wrong type"}if(c[1]!=c.length-3){throw"Non-canonical signature: wrong length marker"}var a=c[3];if(5+a>=c.length){throw"Non-canonical signature: S length misplaced"}var f=c[5+a];if(a+f+7!=c.length){throw"Non-canonical signature: R+S length mismatch"}var d=4;if(c[d-2]!=2){throw"Non-canonical signature: R value type mismatch"}if(a==0){throw"Non-canonical signature: R length is zero"}if(c[d+0]&128){throw"Non-canonical signature: R value negative"}if(a>1&&(c[d+0]==0)&&!(c[d+1]&128)){throw"Non-canonical signature: R value excessively padded"}var d=6+a;if(c[d-2]!=2){throw"Non-canonical signature: S value type mismatch"}if(f==0){throw"Non-canonical signature: S length is zero"}if(c[d+0]&128){throw"Non-canonical signature: S value negative"}if(f>1&&(c[d+0]==0)&&!(c[d+1]&128)){throw"Non-canonical signature: S value excessively padded"}return true}try{if(typeof window=="undefined"||!window){var window={};self.addEventListener("message",function(f){var d=f.data;try{switch(d.cmd){case"seed":seed_large_int32_array(Crypto.util.bytesToWords(Crypto.util.hexToBytes(d.seed)));break;case"decrypt":var b=Crypto.AES.decrypt(d.data,d.password,{mode:new Crypto.mode.CBC(Crypto.pad.iso10126),iterations:d.pbkdf2_iterations});self.postMessage({cmd:"on_decrypt",data:b});break;case"load_resource":importScripts(d.path);break;case"sign_input":var a=new Bitcoin.Transaction(d.tx);var c=new Bitcoin.Script(d.connected_script);var g=signInput(a,d.outputN,d.priv_to_use,c);if(g){self.postMessage({cmd:"on_sign",script:g,outputN:d.outputN})}else{throw"Unknown Error Signing Script "+d.outputN}break;default:throw"Unknown Command"}}catch(f){self.postMessage({cmd:"on_error",e:exceptionToString(f)})}},false)}}catch(e){}function showPrivateKeyModal(h,a,i){var d=$("#private-key-modal");d.modal({keyboard:true,backdrop:"static",show:true});d.center();d.find(".address").text(i);var f=null;var c=false;var b=null;var g=d.find('input[name="key"]');g.val("");d.find(".qrcodeicon span").click(function(){d.modal("hide");MyWallet.scanQRCode(function(j){console.log("Scanned "+j);d.modal("show");g.val(j);d.find(".btn.btn-primary").trigger("click")},function(j){d.modal("show");MyWallet.makeNotice("error","misc-error",j)})});d.find(".btn.btn-primary").unbind().click(function(){var j=$.trim(g.val());try{if(j.length==0){throw"You must enter a private key to import"}var l=MyWallet.detectPrivateKeyFormat(j);console.log("PK Format "+l);if(l=="bip38"){d.modal("hide");loadScript("wallet-legacy/import-export",function(){MyWallet.getPassword($("#import-private-key-password"),function(m){ImportExport.parseBIP38toECKey(j,m,function(n,o){f=n;c=o;d.modal("hide");if(f){h(f)}else{a(b)}},a)},a)},a);return}f=MyWallet.privateKeyStringToKey(j,l);c=(l=="compsipa");if(f==null){throw"Could not decode private key"}}catch(k){b="Error importing private key "+k}d.modal("hide");if(f){h(f)}else{a(b)}});d.find(".btn.btn-secondary").unbind().click(function(){d.modal("hide");a("User Cancelled")})}function resolveAddress(a){a=$.trim(a);try{return new Bitcoin.Address(a).toString()}catch(f){}a=a.toLowerCase();var h=MyWallet.getAddressBook();for(var c in h){var d=MyWallet.getAddressBookLabel(c);if(d.toLowerCase()==a){return $.trim(c)}}var g=MyWallet.getAllAddresses();for(var b=0;b<g.length;++b){var c=g[b];var d=MyWallet.getAddressLabel(c);if(d&&d.toLowerCase()==a){return c}}return null}function startTxUI(a,i,f,c){function j(){a.find('input[name="send-value"]').val("");a.find('input[name="send-to-address"]').val("")}try{a.find("input,select,button").prop("disabled",true);f.addListener({on_success:function(k){a.find("input,select,button").prop("disabled",false)},on_start:function(k){a.find("input,select,button").prop("disabled",true)},on_error:function(k){a.find("input,select,button").prop("disabled",false)}});var g=0;a.find('input[name="send-value"]').each(function(){g+=parseFloat($(this).val())});var d=true;if(g>precisionFromBTC(10)){if(i=="email"||i=="sms"){throw"Cannot Send More Than 10 BTC via email or sms"}else{if(i=="quick"){i="custom";d=false}}}else{if(i=="shared"&&g<precisionFromBTC(0.1)){throw"The Minimum Amount You Can Send Shared is "+formatPrecision(precisionFromBTC(0.1))}else{if(i=="shared"&&g>precisionFromBTC(250)){throw"The Maximum Amount You Can Send Shared is "+formatPrecision(precisionFromBTC(250))}}}if(i=="custom"||i=="shared"){var b={on_error:function(k){if(this.modal){this.modal.modal("hide")}},on_success:function(){j()},on_start:function(){var k=this;this.modal=$("#new-transaction-modal");this.modal.modal({keyboard:false,backdrop:"static",show:true});this.modal.find(".offline-transaction").hide();this.modal.find("#missing-private-key").hide();this.modal.find("#review-tx").hide();this.modal.find(".modal-header h3").html("Creating transaction");this.modal.find("#tx-sign-progress").hide();this.modal.find(".btn.btn-primary").prop("disabled",true);this.modal.find(".btn.btn-primary").text("Send Transaction");this.modal.find(".btn.btn-secondary").unbind().click(function(){if(k.modal){k.modal.modal("hide")}k.cancel()})},on_begin_signing:function(){$("#tx-sign-progress").show().find(".t").text(this.tx.ins.length)},on_sign_progress:function(k){$("#tx-sign-progress").find(".n").text(k)},on_finish_signing:function(){$("#tx-sign-progress").hide()}};f.addListener(b);if(d){f.ask_for_fee=function(n,m){var k=this;if(k.modal){k.modal.modal("hide")}var l=$("#ask-for-fee");l.modal({keyboard:false,backdrop:"static",show:true});l.find(".btn.btn-primary").unbind().click(function(){l.modal("hide");n()});l.find(".btn.btn-secondary").unbind().click(function(){l.modal("hide");m()});l.unbind().on("hidden",function(){if(k.modal){k.modal.modal("show")}})};f.ask_to_increase_fee=function(q,p,n,l){var k=this;if(k.modal){k.modal.modal("hide")}var o=$("#ask-to-increase-fee");o.modal({keyboard:false,backdrop:"static",show:true});var r=o.find(".modal-body");var m=r.find("span");m.eq(0).text(formatSymbol(n.intValue(),symbol_btc));m.eq(1).text(formatSymbol(l.intValue(),symbol_btc));o.find(".btn.btn-primary").unbind().click(function(){o.modal("hide");q()});o.find(".btn.btn-secondary").unbind().click(function(){o.modal("hide");p()});o.unbind().on("hidden",function(){if(k.modal){k.modal.modal("show")}})}}f.ask_to_send=function(){var k=this;try{k.modal.find(".modal-header h3").html(k.ready_to_send_header);k.modal.find("#missing-private-key").hide();k.modal.find("#review-tx").show();setReviewTransactionContent(k.modal,k.tx,k.type);setAdv(false);k.modal.center();var l=k.modal.find(".btn.btn-primary");MyWallet.setLoadingText("Checking Connectivity");$.ajax({timeout:60000,type:"GET",url:root+"ping",data:{format:"plain",date:new Date().getTime()},success:function(){l.removeAttr("disabled");l.text("Send Transaction");l.unbind().click(function(){l.prop("disabled",true);if(k.modal){k.modal.modal("hide")}k.send()})},error:function(){if(k.generated_addresses.length>0){if(k.modal){k.modal.modal("hide")}k.error("Cannot Send Offline Transaction With New Change Address");return}k.modal.find(".modal-header h3").html("Created Offline Transaction.");l.removeAttr("disabled");l.text("Show Offline Instructions");l.unbind().click(function(){l.prop("disabled",true);k.modal.find("#missing-private-key").hide();k.modal.find("#review-tx").hide();k.modal.find(".offline-transaction").show();var n=k.tx.serialize();var o=Crypto.util.bytesToHex(n);k.modal.find('.offline-transaction textarea[name="data"]').val(o)});k.modal.center()}})}catch(m){k.error(m)}}}else{if(i=="quick"||i=="email"||i=="dice"||i=="sms"){var b={on_error:function(k){a.find(".send").show();if(this.p){this.p.hide()}},on_success:function(){try{a.find(".send").show();if(i!="dice"){j()}if(this.p){this.p.hide()}}catch(k){console.log(k)}},on_start:function(){this.p=a.find(".progress");a.find(".send").hide();this.p.show();this.p.children().css("width","10%")},on_begin_signing:function(){this.p.children().css("width","25%")},on_sign_progress:function(k){this.p.children().css("width",25+((100/this.tx.ins.length)*k)+"%")},on_finish_signing:function(){this.p.children().css("width","100%")}};f.addListener(b);if(i=="sms"){f.ask_to_send=function(){try{var k=this;MyWallet.securePost("send-via",{type:"sms",to:k.sms_data.number,priv:k.sms_data.miniKey,hash:Crypto.util.bytesToHex(k.tx.getHash().reverse())},function(){k.send()},function(m){k.error(m?m.responseText:null)})}catch(l){k.error(l)}}}else{if(i=="email"){f.ask_to_send=function(){var k=this;var l=$("#send-email-modal");try{MyWallet.securePost("wallet",{method:"get-info",format:"json"},function(n){try{l.modal({keyboard:true,backdrop:"static",show:true});var p=n.alias;if(p==null){p=n.email}if(p==null){p="Shared"}l.find(".amount").text(formatBTC(k.email_data.amount.toString()));l.find(".email").text(k.email_data.email);l.find(".frame").html('<iframe frameBorder="0" style="box-sizing:border-box;width:100%;height:100%" src="'+root+"email-template?from_name="+p+"&amount="+k.email_data.amount+'&priv=Preview&type=send-bitcoins-get"></iframe>');l.find(".btn.btn-secondary").unbind().click(function(){k.cancel();l.modal("hide")});l.find(".btn.btn-primary").unbind().click(function(){l.modal("hide");try{MyWallet.securePost("send-via",{type:"email",to:k.email_data.email,priv:k.email_data.priv,hash:Crypto.util.bytesToHex(k.tx.getHash().reverse())},function(r){k.send()},function(r){k.error(r?r.responseText:null)})}catch(q){k.error(q)}})}catch(o){l.modal("hide");k.error(o)}},function(n){l.modal("hide");k.error("Error Getting Account Data")})}catch(m){l.modal("hide");k.error(m)}}}}}}f.insufficient_funds=function(m,k,p,o){var l=this;if(l.modal){l.modal.modal("hide")}var n=$("#insufficient-funds");n.find(".amount-required").text(formatBTC(m));n.find(".amount-available").text(formatBTC(k));n.modal({keyboard:false,backdrop:"static",show:true});n.find(".btn.btn-primary").unbind().click(function(){n.modal("hide");p()});n.find(".btn.btn-secondary").unbind().click(function(){n.modal("hide");o()});n.unbind().on("hidden",function(){if(l.modal){l.modal.modal("show")}})};f.ask_for_private_key=function(m,l,n){var k=this;if(k.modal){k.modal.modal("hide")}showPrivateKeyModal(function(p,o){if(k.modal){k.modal.modal("show")}m(p,o)},function(o){if(k.modal){k.modal.modal("show")}l(o)},n)};f.type=i;if(MyWallet.getFeePolicy()==1){f.base_fee=BigInteger.valueOf(100000);f.fee=BigInteger.valueOf(100000)}else{if(MyWallet.getFeePolicy()==-1){f.base_fee=BigInteger.valueOf(10000);f.ask_for_fee=function(l,k){k()}}}(function(k){MyWallet.getSecondPassword(function(){try{var m=a.find('select[name="from"]');var s=m.val();if(s==null||s=="any"){k.from_addresses=MyWallet.getActiveAddresses()}else{if(m.attr("multiple")=="multiple"){k.from_addresses=s}else{k.from_addresses=[s]}}var w=a.find('textarea[name="public-note"]').val();if(w!=null&&w.length>0){if(w.length>255){throw"Notes are restricted to 255 characters in length"}k.note=w}var r=$.trim(a.find('select[name="change"]').val());if(r.length>0){if(r=="new"){var t=MyWallet.generateNewKey();if(!t||!t.addr){throw"Error Generating New Address"}var o=t.addr;k.change_address=new Bitcoin.Address(o);k.generated_addresses.push(o)}else{if(r!="any"){try{k.change_address=new Bitcoin.Address(r)}catch(v){throw"Invalid change address: "+v}}}}var q=a.find('input[name="fees"]').val();if(q!=null&&q.length>0){var l=precisionToSatoshiBN(q);if(l.compareTo(BigInteger.ZERO)>=0){k.fee=l;k.did_specify_fee_manually=true}}var n=a.find(".recipient");if(n.length==0){throw"A transaction must have at least one recipient"}var u=n.length;var p=function(){if(u==0){k.error("Nothing to send.");return}if(k.to_addresses.length<u){return}if(k.to_addresses.length>u){k.error("We seem to have more recipients than required. Unknown error");return}k.start()};n.each(function(){try{var y=$(this);var z=y.find('input[name="send-value"]');var K=y.find('input[name="send-to-address"]');var G=y.find('input[name="send-to-email"]');var B=y.find('input[name="send-to-sms"]');var I=0;try{I=precisionToSatoshiBN(z.val());if(I==null||I.compareTo(BigInteger.ZERO)<=0){throw"You must enter a value greater than zero"}}catch(E){console.log(E);if(z.data("optional")==true){--u;return true}else{throw"Invalid send amount"}}if(K.length>0){var C=$.trim(K.val()).replace(/[\u200B-\u200D\uFEFF]/g,"");if(C==null||C.length==0){throw"You must enter a bitcoin address for each recipient"}else{var H=resolveAddress(C);if(i=="shared"){if(!H){throw"Invalid Bitcoin Address"}MyWallet.setLoadingText("Creating Forwarding Address");MyWallet.securePost("forwarder",{action:"create-mix",address:H,shared:true,format:"json"},function(M){try{if(M.destination!=H){throw"Mismatch between requested and returned destination address"}if(M.fee_percent!=MyWallet.getMixerFee()){MyWallet.get_history();throw"The mixer fee may have changed"}k.to_addresses.push({address:new Bitcoin.Address(M.input_address),value:I});p()}catch(L){k.error(L)}},function(L){k.error(L?L.responseText:null)})}else{if(H){k.to_addresses.push({address:new Bitcoin.Address(H),value:I})}else{if(C.length<10){BlockchainAPI.resolve_firstbits(C,function(L){try{k.to_addresses.push({address:new Bitcoin.Address(L),value:I});p()}catch(M){k.error(M)}},function(){k.error("Invalid to address: "+C)});return false}else{k.error("Invalid to address: "+C)}}}}}else{if(B.length>0){var D=$.trim(B.val());if(D.charAt(0)=="0"){D=D.substring(1)}if(D.charAt(0)!="+"){D="+"+y.find('select[name="sms-country-code"]').val()+D}var F=generateNewMiniPrivateKey();var H=F.key.getBitcoinAddress().toString();MyWallet.setAddressTag(H,2);MyWallet.setAddressLabel(H,D+" Sent Via SMS");k.generated_addresses.push(H);k.to_addresses.push({address:new Bitcoin.Address(H),value:I});if(k.sms_data){throw"Cannot send to more than one SMS recipient at a time"}k.sms_data={number:D,miniKey:F.miniKey}}else{if(G.length>0){var J=$.trim(G.val());function x(N){var M=N.lastIndexOf("@");var L=N.lastIndexOf(".");return(M<L&&M>0&&N.indexOf("@@")==-1&&L>2&&(N.length-L)>2)}if(x(J)){var A=MyWallet.generateNewKey();if(!A||!A.addr){throw"Error Generating New Address"}var H=A.addr;MyWallet.setAddressTag(H,2);MyWallet.setAddressLabel(H,J+" Sent Via Email");k.generated_addresses.push(H);k.to_addresses.push({address:new Bitcoin.Address(H),value:I});if(k.email_data){throw"Cannot send to more than one email recipient at a time"}k.email_data={email:J,priv:B58.encode(A.key.priv),amount:I}}else{throw"Invalid Email Address"}}}}}catch(E){console.log(E);k.error(E)}});p()}catch(v){k.error(v)}},function(){k.error()})})(f)}catch(h){f.error(h)}return f}function signInput(i,c,b,m,k){k=k?k:SIGHASH_ALL;var a=m.simpleOutPubKeyHash();var d=new Bitcoin.Address(a).toString();var n=new Bitcoin.ECKey(b);var j;if(n.getBitcoinAddress().toString()==d.toString()){j=false}else{if(n.getBitcoinAddressCompressed().toString()==d.toString()){j=true}else{throw"Private key does not match bitcoin address "+d.toString()+" = "+n.getBitcoinAddress().toString()+" | "+n.getBitcoinAddressCompressed().toString()}}var h=i.hashTransactionForSignature(m,c,k);var g=n.sign(h);var f=Bitcoin.ECDSA.serializeSig(g.r,g.s);f.push(k);if(!IsCanonicalSignature(f)){throw"IsCanonicalSignature returned false"}var l;if(j){l=Bitcoin.Script.createInputScript(f,n.getPubCompressed())}else{l=Bitcoin.Script.createInputScript(f,n.getPub())}if(l==null){throw"Error creating input script"}return l}function formatAddresses(b,f,a){var g="";if(f.length==1){var c=f[0].toString();if(a&&MyWallet.addressExists(c)&&MyWallet.getAddressLabel(c)){g=MyWallet.getAddressLabel(c)}else{if(a&&MyWallet.getAddressBookLabel(c)){g=MyWallet.getAddressBookLabel(c)}else{g=c}}}else{g="Escrow (<i>";for(var d=0;d<f.length;++d){g+=f[d].toString()+", "}g=g.substring(0,g.length-2);g+="</i> - "+b+" Required)"}return g}function setReviewTransactionContent(r,u,a){$("#rtc-hash").html(Crypto.util.bytesToHex(u.getHash()));$("#rtc-version").html(u.version);$("#rtc-from").html("");$("#rtc-to").html("");var v=BigInteger.ZERO;var t=BigInteger.ZERO;var n=BigInteger.ZERO;var g="send ";var q=true;var c=BigInteger.ZERO;for(var o=0;o<u.ins.length;++o){var k=u.ins[o];t=t.add(k.outpoint.value);n=n.add(k.outpoint.value);var f=null;try{f=new Bitcoin.Address(k.script.simpleInPubKeyHash())}catch(s){f="Unable To Decode Address"}$("#rtc-from").append(f+' <font color="green">'+formatBTC(k.outpoint.value.toString())+" <br />")}var j=true;for(var o=0;o<u.outs.length;++o){var p=u.outs[o];var d=p.value.slice();d.reverse();var w=new BigInteger(d);var h=[];var l=1;try{l=p.script.extractAddresses(h)}catch(s){console.log(s);h.push("Unknown Address!")}$("#rtc-to").append(formatAddresses(l,h)+' <font color="green">'+formatBTC(w.toString())+" </font><br />");v=v.add(w);t=t.subtract(w);if(h.length>1){if(!j){g+=" and "}g+="<b>"+formatBTC(w.toString())+"</b> to "+formatAddresses(l,h,true);q=false;n=n.subtract(w)}else{if(h.length>0){var b=h[0].toString();if(!MyWallet.addressExists(b)||MyWallet.getAddressTag(b)==2){if(w.compareTo(BigInteger.ZERO)==0){continue}if(!j){g+=" and "}if(a&&a=="shared"){g+="<b>"+formatBTC(w.toString())+"</b> Shared"}else{g+="<b>"+formatBTC(w.toString())+"</b> to "+formatAddresses(1,[b],true)}q=false}else{n=n.subtract(w);c=c.add(w)}}}j=false}if(t.compareTo(BigInteger.valueOf(1).multiply(BigInteger.valueOf(satoshi)))>=0){alert("Warning fees are very high for this transaction. Please double check each output!")}if(q==true){g="move <b>"+formatBTC(v.toString())+"</b> between your own bitcoin addresses"}$("#rtc-basic-summary").html(g);$("#rtc-effect").html("-"+formatBTC(n.toString()));$("#rtc-fees").html(formatBTC(t.toString()));$("#rtc-value").html(formatBTC(v.toString()))}function initNewTx(){var a={generated_addresses:[],to_addresses:[],fee:BigInteger.ZERO,extra_private_keys:{},listeners:[],is_cancelled:false,base_fee:BigInteger.valueOf(10000),min_free_output_size:BigInteger.valueOf(1000000),min_non_standard_output_size:BigInteger.valueOf(5460),allow_adjust:true,ready_to_send_header:"Transaction Ready to Send.",min_input_confirmations:0,do_not_use_unspent_cache:false,min_input_size:BigInteger.ZERO,did_specify_fee_manually:false,addListener:function(b){this.listeners.push(b)},invoke:function(b,f,g){for(var c in this.listeners){try{if(this.listeners[c][b]){this.listeners[c][b].call(this,f,g)}}catch(d){console.log(d)}}},start:function(){var b=this;try{b.invoke("on_start");BlockchainAPI.get_unspent(b.from_addresses,function(k){try{if(b.is_cancelled){throw"Transaction Cancelled"}if(k.unspent_outputs==null||k.unspent_outputs.length==0){throw"No Free Outputs To Spend"}var d=[];for(var h=0;h<k.unspent_outputs.length;++h){var f;try{f=new Bitcoin.Script(Crypto.util.hexToBytes(k.unspent_outputs[h].script));if(f.getOutType()=="Strange"){throw"Strange Script"}}catch(j){MyWallet.makeNotice("error","misc-error","Error decoding script: "+j);continue}var g={script:f,value:BigInteger.fromByteArrayUnsigned(Crypto.util.hexToBytes(k.unspent_outputs[h].value_hex)),tx_output_n:k.unspent_outputs[h].tx_output_n,tx_hash:k.unspent_outputs[h].tx_hash,confirmations:k.unspent_outputs[h].confirmations};d.push(g)}b.unspent=b.sortOutputs(d);b.makeTransaction()}catch(j){b.error(j)}},function(d){b.error(d)},b.min_input_confirmations,b.do_not_use_unspent_cache)}catch(c){b.error(c)}},sortOutputs:function(b){return b},isSelectedValueSufficient:function(b,c){return c.compareTo(b)==0||c.compareTo(b.add(this.min_free_output_size))>=0},makeTransaction:function(){var o=this;try{if(o.is_cancelled){throw"Transaction Cancelled"}o.selected_outputs=[];var j=BigInteger.ZERO;for(var q=0;q<o.to_addresses.length;++q){j=j.add(o.to_addresses[q].value)}var d=BigInteger.ZERO;if(o.fee!=null){j=j.add(o.fee)}var v=0;var c=[];var l=false;var y=o.unspent.slice(0);function k(z){if(!z.script){throw"Output script is null ("+z.tx_hash+":"+z.tx_output_n+")"}var B=new Bitcoin.Address(z.script.simpleOutPubKeyHash()).toString();var A=Crypto.util.bytesToBase64(Crypto.util.hexToBytes(z.tx_hash));var i=new Bitcoin.TransactionIn({outpoint:{hash:A,index:z.tx_output_n,value:z.value},script:z.script,sequence:4294967295});return{addr:B,input:i}}var u=false;while(true){for(var q=0;q<y.length;++q){var r=y[q];if(!r){continue}try{var p=k(r);if(!u&&MyWallet.isWatchOnly(p.addr)){continue}if(o.from_addresses!=null&&$.inArray(p.addr,o.from_addresses)==-1){continue}if(r.value.compareTo(o.min_input_size)<0){continue}if(o.isSelectedValueSufficient(j,r.value,[p.input])){o.selected_outputs=[p.input];y[q]=null;c=[p.addr];v=r.value.intValue()*r.confirmations;d=r.value;break}else{o.selected_outputs.push(p.input);y[q]=null;c.push(p.addr);v+=r.value.intValue()*r.confirmations;d=d.add(r.value);if(o.isSelectedValueSufficient(j,d,o.selected_outputs)){break}}}catch(t){MyWallet.makeNotice("info","tx-error",t)}}if(o.isSelectedValueSufficient(j,d,o.selected_outputs)){break}if(u){break}u=true}function h(){o.error("Insufficient funds. Value Needed "+formatBTC(j.toString())+". Available amount "+formatBTC(d.toString()))}var w=d.subtract(j);if(w.compareTo(BigInteger.ZERO)<0){if(o.to_addresses.length==1&&d.compareTo(BigInteger.ZERO)>0&&o.allow_adjust){o.insufficient_funds(j,d,function(){var i=o.to_addresses[0].value.add(w);if(i.compareTo(BigInteger.ZERO)>0&&i.compareTo(j)<=0){o.to_addresses[0].value=i;o.makeTransaction();return}else{h()}},function(){h()})}else{h()}return}if(o.selected_outputs.length==0){o.error("No Available Outputs To Spend.");return}var g=new Bitcoin.Transaction();for(var q=0;q<o.selected_outputs.length;q++){g.addInput(o.selected_outputs[q])}for(var q=0;q<o.to_addresses.length;++q){var m=o.to_addresses[q];if(m.m!=null){g.addOutputScript(Bitcoin.Script.createMultiSigOutputScript(m.m,m.pubkeys),m.value)}else{g.addOutput(m.address,m.value)}if(m.value.compareTo(o.min_free_output_size)<0){l=true}}var s=d.subtract(j);if(s.compareTo(o.min_non_standard_output_size)>0){if(o.change_address!=null){g.addOutput(o.change_address,s)}else{if(c.length>0){g.addOutput(new Bitcoin.Address(c[Math.floor(Math.random()*c.length)]),s)}else{g.addOutput(new Bitcoin.Address(MyWallet.getPreferredAddress()),s)}}if(s.compareTo(o.min_free_output_size)<0){l=true}}var b=g.serialize(g).length+(138*g.ins.length);v/=b;var f=Math.max(1,Math.ceil(parseFloat(b/1000)));var x=(!o.fee||o.fee.compareTo(o.base_fee)<0);var n=function(){o.fee=o.base_fee.multiply(BigInteger.valueOf(f));o.makeTransaction()};if(x&&(l||f>1)){if(o.fee&&o.did_specify_fee_manually){o.ask_to_increase_fee(function(){n()},function(){o.tx=g;o.determinePrivateKeys(function(){o.signInputs()})},o.fee,o.base_fee.multiply(BigInteger.valueOf(f)))}else{n()}}else{if(x&&(MyWallet.getRecommendIncludeFee()||v<77600000)){o.ask_for_fee(function(){n()},function(){o.tx=g;o.determinePrivateKeys(function(){o.signInputs()})})}else{o.tx=g;o.determinePrivateKeys(function(){o.signInputs()})}}}catch(t){this.error(t)}},ask_for_fee:function(c,b){c()},ask_to_increase_fee:function(f,d,c,b){f()},insufficient_funds:function(c,b,f,d){d()},determinePrivateKeys:function(k){var b=this;try{if(b.is_cancelled){throw"Transaction Cancelled"}if(b.selected_outputs.length!=b.tx.ins.length){throw"Selected Outputs Count != Tx Inputs Length"}var h={};for(var d=0;d<b.selected_outputs.length;++d){var c=b.selected_outputs[d].script;if(c==null){console.log("Output:");console.log(b.selected_outputs[d]);throw"determinePrivateKeys() Connected script is null"}if(c.priv_to_use==null){var g=c.simpleOutPubKeyHash();var f=new Bitcoin.Address(g).toString();if(h[f]){c.priv_to_use=h[f]}else{if(b.extra_private_keys&&b.extra_private_keys[f]){c.priv_to_use=Bitcoin.Base58.decode(b.extra_private_keys[f])}else{if(MyWallet.addressExists(f)&&!MyWallet.isWatchOnly(f)){try{c.priv_to_use=MyWallet.decodePK(MyWallet.getPrivateKey(f))}catch(j){console.log(j)}}}}if(c.priv_to_use==null){b.ask_for_private_key(function(i){try{if(f==i.getBitcoinAddress().toString()||f==i.getBitcoinAddressCompressed().toString()){b.extra_private_keys[f]=Bitcoin.Base58.encode(i.priv);b.determinePrivateKeys(k)}else{throw"The private key you entered does not match the bitcoin address"}}catch(l){b.error(l)}},function(i){b.from_addresses=$.grep(b.from_addresses,function(l){return l!=f});b.makeTransaction()},f);return false}else{h[f]=c.priv_to_use}}}k()}catch(j){b.error(j)}},signWebWorker:function(n,m){var b=false;var k=function(i){if(!b){m(i);b=true}};try{var p=this;var h=0;var o=Math.min(3,p.tx.ins.length);var c=new SecureRandom();p.worker=[];for(var d=0;d<o;++d){p.worker[d]=new Worker(MyWallet.getWebWorkerLoadPrefix()+"signer"+(min?".min.js":".js"));p.worker[d].addEventListener("message",function(q){var i=q.data;try{switch(i.cmd){case"on_sign":p.invoke("on_sign_progress",parseInt(i.outputN)+1);p.tx.ins[i.outputN].script=new Bitcoin.Script(i.script);++h;if(h==p.tx.ins.length){p.terminateWorkers();n()}break;case"on_message":console.log(i.message);break;case"on_error":throw i.e}}catch(q){p.terminateWorkers();k(q)}},false);p.worker[d].addEventListener("error",function(i){k(i)});p.worker[d].postMessage({cmd:"load_resource",path:MyWallet.getWebWorkerLoadPrefix()+"bitcoinjs"+(min?".min.js":".js")});var f=new Array(rng_psize);c.nextBytes(f);p.worker[d].postMessage({cmd:"seed",seed:Crypto.util.bytesToHex(f)})}for(var g=0;g<p.selected_outputs.length;++g){var l=p.selected_outputs[g].script;if(l==null){throw"signWebWorker() Connected Script Is Null"}p.worker[g%o].postMessage({cmd:"sign_input",tx:p.tx,outputN:g,priv_to_use:l.priv_to_use,connected_script:l})}}catch(j){k(j)}},signNormal:function(g,f){var c=this;var b=0;var d=function(){setTimeout(function(){if(c.is_cancelled){f();return}try{c.invoke("on_sign_progress",b+1);var h=c.selected_outputs[b].script;if(h==null){throw"signNormal() Connected Script Is Null"}var j=signInput(c.tx,b,h.priv_to_use,h);if(j){c.tx.ins[b].script=j;b++;if(b==c.tx.ins.length){g()}else{d()}}else{throw"Unknown error signing transaction"}}catch(i){f(i)}},1)};d()},signInputs:function(){var b=this;try{b.invoke("on_begin_signing");var d=function(){b.invoke("on_finish_signing");b.is_ready=true;b.ask_to_send()};MyWallet._seed();b.signWebWorker(d,function(f){console.log(f);b.signNormal(d,function(g){b.error(g)})})}catch(c){b.error(c)}},terminateWorkers:function(){if(this.worker){for(var b=0;b<this.worker.length;++b){try{this.worker[b].terminate()}catch(c){}}}},cancel:function(){if(!this.has_pushed){this.terminateWorkers();this.error("Transaction Cancelled")}},send:function(){var b=this;if(b.is_cancelled){b.error("This transaction has already been cancelled");return}if(!b.is_ready){b.error("Transaction is not ready to send yet");return}b.invoke("on_before_send");if(b.generated_addresses.length>0){b.has_saved_addresses=true;MyWallet.backupWallet("update",function(){b.pushTx()},function(){b.error("Error Backing Up Wallet. Cannot Save Newly Generated Keys.")})}else{b.pushTx()}},pushTx:function(){var b=this;if(b.is_cancelled){return}b.has_pushed=true;BlockchainAPI.push_tx(b.tx,b.note,function(c){b.success(c)},function(c){b.error(c)})},ask_for_private_key:function(c,b){b("Cannot ask for private key without user interaction disabled")},ask_to_send:function(){this.send()},error:function(b){if(this.is_cancelled){return}this.is_cancelled=true;if(!this.has_pushed&&this.generated_addresses.length>0){for(var c=0;c<this.generated_addresses.length;++c){MyWallet.deleteAddress(this.generated_addresses[c])}if(this.has_saved_addresses){MyWallet.backupWallet()}}this.invoke("on_error",b)},success:function(){this.invoke("on_success")}};a.addListener({on_error:function(b){console.log(b);if(b){MyWallet.makeNotice("error","tx-error",b)}},on_begin_signing:function(){this.start=new Date().getTime()},on_finish_signing:function(){console.log("Signing Took "+(new Date().getTime()-this.start)+"ms")}});return a};