@ -127,6 +127,10 @@ var cnUtil = function(currencyConfig)
}
throw "ret_val_boolstring_to_bool given illegal input"
}
function api _safe _wordset _name ( wordset _name )
{
return wordset _name . charAt ( 0 ) . toUpperCase ( ) + wordset _name . substr ( 1 ) // capitalizes first letter
}
//
var config = { } ; // shallow copy of initConfig
for ( var key in currencyConfig ) {
@ -149,6 +153,50 @@ var cnUtil = function(currencyConfig)
return mnemonic . mn _random ( 64 ) ;
} ;
this . is _subaddress = function ( addr , nettype ) {
const args =
{
address : addr ,
nettype _string : nettype _utils . nettype _to _API _string ( nettype )
} ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . is _subaddress ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return ret _val _boolstring _to _bool ( ret . retVal ) ;
} ;
this . is _integrated _address = function ( addr , nettype ) {
const args =
{
address : addr ,
nettype _string : nettype _utils . nettype _to _API _string ( nettype )
} ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . is _integrated _address ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return ret _val _boolstring _to _bool ( ret . retVal ) ;
} ;
this . new _payment _id = function ( ) {
const args = { } ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . new _payment _id ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return ret . retVal ;
} ;
this . new _ _int _addr _from _addr _and _short _pid = function (
address ,
short _pid ,
@ -174,9 +222,17 @@ var cnUtil = function(currencyConfig)
return ret . retVal ;
} ;
this . create _address = function ( seed , nettype )
{
// TODO:
this . new _fake _address _for _rct _tx = function ( nettype )
{ // TODO: possibly support sending random_scalar from JS to emscripten to avoid emscripten random
const args = { nettype _string : nettype _utils . nettype _to _API _string ( nettype ) } ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . new _fake _address _for _rct _tx ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return ret . retVal ;
} ;
this . decode _address = function ( address , nettype )
@ -201,20 +257,106 @@ var cnUtil = function(currencyConfig)
}
} ;
this . is _subaddress = function ( addr , nettype ) {
this . newly _created _wallet = function (
wordset _name ,
nettype
) {
const args =
{
address : addr ,
wordset_name : api _safe _wordset _name ( wordset _name ) ,
nettype _string : nettype _utils . nettype _to _API _string ( nettype )
} ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . is_subaddress ( args _str ) ;
const ret _string = CNCrypto . newly_created _wallet ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return ret _val _boolstring _to _bool ( ret . retVal )
return { // calling these out so as to provide a stable ret val interface
mnemonic _string : ret . mnemonic _string ,
sec _seed _string : ret . sec _seed _string ,
address _string : ret . address _string ,
pub _viewKey _string : ret . pub _viewKey _string ,
sec _viewKey _string : ret . sec _viewKey _string ,
pub _spendKey _string : ret . pub _spendKey _string ,
sec _spendKey _string : ret . sec _spendKey _string
} ;
} ;
this . mnemonic _from _seed = function (
seed _string ,
wordset _name
) {
const args =
{
seed _string : seed _string ,
wordset _name : api _safe _wordset _name ( wordset _name )
} ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . mnemonic _from _seed ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return ret . retVal ;
} ;
this . seed _and _keys _from _mnemonic = function (
mnemonic _string ,
wordset _name
) {
const args =
{
mnemonic _string : mnemonic _string ,
wordset _name : api _safe _wordset _name ( wordset _name )
} ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . seed _and _keys _from _mnemonic ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return { // calling these out so as to provide a stable ret val interface
sec _seed _string : ret . sec _seed _string ,
address _string : ret . address _string ,
pub _viewKey _string : ret . pub _viewKey _string ,
sec _viewKey _string : ret . sec _viewKey _string ,
pub _spendKey _string : ret . pub _spendKey _string ,
sec _spendKey _string : ret . sec _spendKey _string
} ;
} ;
this . validate _components _for _login = function (
address _string ,
sec _viewKey _string ,
sec _spendKey _string ,
seed _string ,
nettype
) {
const args =
{
address _string : address _string ,
sec _viewKey _string : sec _viewKey _string ,
sec _spendKey _string : sec _spendKey _string ,
seed _string : seed _string ,
nettype _string : nettype _utils . nettype _to _API _string ( nettype )
} ;
const args _str = JSON . stringify ( args ) ;
const CNCrypto = loaded _CNCrypto ( ) ;
const ret _string = CNCrypto . validate _components _for _login ( args _str ) ;
const ret = JSON . parse ( ret _string ) ;
if ( typeof ret . err _msg !== 'undefined' && ret . err _msg ) {
throw ret . err _msg // TODO: maybe return this somehow
}
return { // calling these out so as to provide a stable ret val interface
isValid : ret _val _boolstring _to _bool ( ret . isValid ) ,
isInViewOnlyMode : ret _val _boolstring _to _bool ( ret . isInViewOnlyMode ) ,
pub _viewKey _string : ret . pub _viewKey _string ,
pub _spendKey _string : ret . pub _spendKey _string
} ;
} ;
this . generate _key _image = function (
@ -322,101 +464,6 @@ var cnUtil = function(currencyConfig)
throw "Not enough outputs to mix with" ;
}
}
// TODO
} ;
this . estimateRctSize = function ( inputs , mixin , outputs , extra _size , bulletproof )
{
// keeping this in JS instead of C++ for now b/c it's much faster to access, and we don't have to make it asynchronous by waiting for the module to load
bulletproof = bulletproof == true ? true : false
extra _size = extra _size || 40
//
var size = 0 ;
// tx prefix
// first few bytes
size += 1 + 6 ;
size += inputs * ( 1 + 6 + ( mixin + 1 ) * 2 + 32 ) ;
// vout
size += outputs * ( 6 + 32 ) ;
// extra
size += extra _size ;
// rct signatures
// type
size += 1 ;
// rangeSigs
if ( bulletproof )
size += ( ( 2 * 6 + 4 + 5 ) * 32 + 3 ) * outputs ;
else
size += ( 2 * 64 * 32 + 32 + 64 * 32 ) * outputs ;
// MGs
size += inputs * ( 64 * ( mixin + 1 ) + 32 ) ;
// mixRing - not serialized, can be reconstructed
/* size += 2 * 32 * (mixin+1) * inputs; */
// pseudoOuts
size += 32 * inputs ;
// ecdhInfo
size += 2 * 32 * outputs ;
// outPk - only commitment is saved
size += 32 * outputs ;
// txnFee
size += 4 ;
// const logStr = `estimated rct tx size for ${inputs} at mixin ${mixin} and ${outputs} : ${size} (${((32 * inputs/*+1*/) + 2 * 32 * (mixin+1) * inputs + 32 * outputs)}) saved)`
// console.log(logStr)
return size ;
} ;
this . is _tx _unlocked = function ( unlock _time , blockchain _height ) {
if ( ! config . maxBlockNumber ) {
throw "Max block number is not set in config!" ;
}
if ( unlock _time < config . maxBlockNumber ) {
// unlock time is block height
return blockchain _height >= unlock _time ;
} else {
// unlock time is timestamp
var current _time = Math . round ( new Date ( ) . getTime ( ) / 1000 ) ;
return current _time >= unlock _time ;
}
} ;
this . tx _locked _reason = function ( unlock _time , blockchain _height ) {
if ( unlock _time < config . maxBlockNumber ) {
// unlock time is block height
var numBlocks = unlock _time - blockchain _height ;
if ( numBlocks <= 0 ) {
return "Transaction is unlocked" ;
}
var unlock _prediction = moment ( ) . add (
numBlocks * config . avgBlockTime ,
"seconds" ,
) ;
return (
"Will be unlocked in " +
numBlocks +
" blocks, ~" +
unlock _prediction . fromNow ( true ) +
", " +
unlock _prediction . calendar ( ) +
""
) ;
} else {
// unlock time is timestamp
var current _time = Math . round ( new Date ( ) . getTime ( ) / 1000 ) ;
var time _difference = unlock _time - current _time ;
if ( time _difference <= 0 ) {
return "Transaction is unlocked" ;
}
var unlock _moment = moment ( unlock _time * 1000 ) ;
return (
"Will be unlocked " +
unlock _moment . fromNow ( ) +
", " +
unlock _moment . calendar ( )
) ;
}
} ;
function assert ( stmt , val ) {