Skip to content
Snippets Groups Projects
Commit 6371c488 authored by Robert Martin-Legene's avatar Robert Martin-Legene
Browse files

Merge branch 'master' into dev

parents 5ec702e5 24e3e9b7
No related branches found
No related tags found
No related merge requests found
...@@ -5,11 +5,9 @@ cache ...@@ -5,11 +5,9 @@ cache
bin/env bin/env
network/node network/node
network/bootnode network/bootnode
network/contracts/*
network/*.pid network/*.pid
test2network*/node test2network*/node
test2network*/bootnode test2network*/bootnode
test2network*/contracts/*
test2network/*.pid test2network/*.pid
node_modules node_modules
src/*/*.bin src/*/*.bin
......
LGPLv2-only
\ No newline at end of file
#!/bin/bash
if [ -z "${BFAHOME}" ]; then echo "\$BFAHOME not set. Did you source bfa/bin/env ?" >&2; exit 1; fi
source ${BFAHOME}/bin/libbfa.sh || exit 1
exec geth --datadir ${BFANODEDIR} --networkid ${BFANETWORKID} "$@"
#!/usr/bin/node
// 20200828 Robert Martin-Legene
// License: GPLv2-only
// (c) Secretaria Legal y Tecnica, Presidencia De La Nacion, Argentina
// Looks for the contract you're specifying as argument.
// Tries to show you all the events that contract has ever logged on the blockchain.
// The contract's ABI must be in a text file in ${BFANETWORKDIR}/contracts/${contractaddr}/abi
const Web3 = require( "web3" );
const fs = require( "fs" );
const web3 = new Web3( "http://127.0.0.1:8545" );
function writeEvent(ev)
{
console.log("");
console.log( "Block number: " + ev.blockNumber );
console.log( "TX hash: " + ev.transactionHash );
console.log( "Event name: " + ev.event );
Object.keys( ev.returnValues ).forEach(
function writeEventValue( value )
{
// Will skip keys which are made entirely of digits.
if ( ! value.match(/^[0-9]+$/) )
{
console.log( "* " + value + ": " + ev.returnValues[value] )
}
}
);
}
function gotPastEvents( e, result )
{
// We are called a single time.
// Either success or failure.
if ( e )
{
console.error( e );
process.exit( 1 );
}
result.forEach( writeEvent );
console.log( "\n" + result.length + " events." );
}
var contractname = process.argv[2];
if ( contractname === undefined )
{
console.error( "Usage: " + process.argv[1] + " <contractname|contractaddr>" );
process.exit( 1 );
}
if ( process.env.BFANETWORKDIR === undefined )
{
console.error( "$BFANETWORKDIR must be defined" );
process.exit( 1 );
}
var pathprefix = process.env.BFANETWORKDIR + "/contracts/";
var filename;
if ( fs.existsSync( contractname ))
filename = contractname;
else
if ( fs.existsSync( contractname.toLowerCase() ))
filename = contractname.toLowerCase();
else
if ( fs.existsSync( pathprefix + contractname ))
filename = pathprefix + contractname;
else
if ( fs.existsSync( pathprefix + contractname.toLowerCase() ))
filename = pathprefix + contractname.toLowerCase();
if ( filename === undefined )
{
console.error( "Contract not found." );
process.exit( 1 );
}
var contractaddr = filename;
var dirname = "";
var idx = filename.lastIndexOf("/");
if ( idx > -1 )
{
dirname = filename.substr( 0, idx+1 );
filename = filename.substr( idx+1 )
contractaddr = filename;
}
var stats = fs.lstatSync( dirname + filename );
if ( stats.isSymbolicLink() )
{
let linkname = fs.readlinkSync( dirname + filename, { encoding: 'utf8' } );
filename = dirname + linkname;
contractaddr = linkname;
}
filename += "/abi";
var abi_str = fs.readFileSync( filename, { encoding: 'utf8' } );
var abi = JSON.parse( abi_str );
var contract = new web3.eth.Contract( abi, contractaddr );
console.log( "Address: " + contractaddr );
contract.getPastEvents( "allEvents", { fromBlock: "earliest", toBlock: "latest" }, gotPastEvents);
...@@ -28,19 +28,16 @@ function info ...@@ -28,19 +28,16 @@ function info
# Runs as the owner of the given directory, and in the given directory # Runs as the owner of the given directory, and in the given directory
function runasownerof function runasownerof
{ {
path=$1 local where=$1 precmd=
precmd=
shift 1 shift 1
pushd $path > /dev/null pushd $where > /dev/null
if [ $( stat --format=%u . ) -ne $UID ] if [ $( stat --format=%u . ) -ne $UID ]
then then
precmd="sudo --preserve-env --set-home -u $( stat --format=%U . ) PATH=${PATH}" precmd="sudo --preserve-env --shell --set-home --user=$( stat --format=%U . ) PATH=${PATH}"
fi fi
unset path
${precmd} "$@" ${precmd} "$@"
rv=$? local rv=$?
popd > /dev/null popd > /dev/null
unset precmd
return $rv return $rv
} }
...@@ -66,56 +63,7 @@ function nodejsinstall ...@@ -66,56 +63,7 @@ function nodejsinstall
aptinstall nodejs aptinstall nodejs
info "Installing nodejs modules (will show many warnings)" info "Installing nodejs modules (will show many warnings)"
runasownerof ${BFAHOME} npm install runasownerof ${BFAHOME} npm install
} runasownerof ${BFAHOME} npm audit fix
function golanginstall
{
if [ ! -d /usr/local/go ]
then
info "Downloading package of go binaries."
mkdir -p ${NEW}
cd ${NEW}
local arch=$( uname -m )
case "${arch}" in
x86_64)
arch=amd64
;;
*)
echo "We have no recipe for how to build on your \"${arch}\" platform." >&2
exit 1
;;
esac
#Download go*.linux-${ARCH}.tar.gz from https://golang.org/dl/
golangurl=$(
curl -f https://golang.org/dl/ 2>/dev/null |
grep linux-${arch}.tar.gz |
grep downloadBox |
sed 's/.*href="//;s/".*//' |
head -1
)
name=$( basename $golangurl )
if [ -r "$name" ]
then
# If we have the download, check if it is corrupt
tar -ztf "$name" >/dev/null 2>&1 ||
rm -f "$name"
fi
if [ ! -r "$name" ]
then
curl -f -O $golangurl ||
rm -f "$name"
fi
# Integrity checking the archive
tar -xzf "$name"
info "Unpacking $name into /usr/local"
tar -C /usr/local -xzf go*.tar.gz
fi
if [ $( expand < ~bfa/.bashrc | grep -E "^PATH=.*/usr/local/go/bin" | wc -l ) -eq 0 ]
then
echo "PATH=\${PATH}:/usr/local/go/bin" >> ~bfa/.bashrc
fi
export PATH=${PATH}:/usr/local/go/bin
} }
function gethinstall function gethinstall
...@@ -142,13 +90,14 @@ function gethinstall ...@@ -142,13 +90,14 @@ function gethinstall
function initgenesis function initgenesis
{ {
( (
HOME=$( echo ~bfa )
source ${BFAHOME}/bin/env source ${BFAHOME}/bin/env
BFANETWORKDIR=${BFANETWORKDIR:-${BFAHOME}/network} BFANETWORKDIR=${BFANETWORKDIR:-${BFAHOME}/network}
BFANODEDIR=${BFANODEDIR:-${BFANETWORKDIR}/node} BFANODEDIR=${BFANODEDIR:-${BFANETWORKDIR}/node}
if [ ! -d "${BFANODEDIR}" -o ! -d "${BFANODEDIR}/geth/chaindata" ] if [ ! -d "${BFANODEDIR}" -o ! -d "${BFANODEDIR}/geth/chaindata" ]
then then
info "Node is not initialised. Initialising with genesis." info "Node is not initialised. Initialising with genesis."
geth --networkid ${BFANETWORKID} --cache 0 --datadir "${BFANODEDIR}" init "${BFANETWORKDIR}/genesis.json" runasownerof "${BFAHOME}" geth --networkid ${BFANETWORKID} --cache 0 --datadir "${BFANODEDIR}" init "${BFANETWORKDIR}/genesis.json"
chown -R bfa:bfa ~bfa chown -R bfa:bfa ~bfa
fi fi
) )
...@@ -259,11 +208,10 @@ grep -q Ubuntu /etc/issue && apt-add-repository multiverse ...@@ -259,11 +208,10 @@ grep -q Ubuntu /etc/issue && apt-add-repository multiverse
# #
apt update apt update
# development tools # development tools
aptinstall dirmngr apt-transport-https curl git curl build-essential sudo software-properties-common aptinstall dirmngr apt-transport-https curl git curl build-essential sudo software-properties-common golang
aptinstall jq libjson-perl libwww-perl libclass-accessor-perl aptinstall jq libjson-perl libwww-perl libclass-accessor-perl
userconfig userconfig
nodejsinstall nodejsinstall
golanginstall
gethinstall gethinstall
initgenesis initgenesis
cronit cronit
......
...@@ -167,13 +167,16 @@ module.exports = class Libbfa ...@@ -167,13 +167,16 @@ module.exports = class Libbfa
}); });
socket.on("error", (e) => { socket.on("error", (e) => {
console.error(e); console.error(e);
err = e; err = e;
}); });
socket.on("close", () => { socket.on("close", () => {
if ( result === undefined )
err = 'Error undefined (close)'
else
if ( result.error && result.error.code && result.error.message ) if ( result.error && result.error.code && result.error.message )
err = 'Error ' + result.error.code + ": "+ result.error.message; err = 'Error ' + result.error.code + ": "+ result.error.message;
else else
result = result.result; result = result.result;
callback( err, result ); callback( err, result );
}); });
} }
......
...@@ -156,25 +156,24 @@ function gotAdminPeers( err, nodelist ) ...@@ -156,25 +156,24 @@ function gotAdminPeers( err, nodelist )
// Try to connect to a random node if we have very few peers // Try to connect to a random node if we have very few peers
if ( nowpeers.length < 5 ) if ( nowpeers.length < 5 )
{ {
var candidatenew = []; var candidate = [];
// find candidate nodes which we can connect to // find candidate nodes which we can connect to
// (it comes from peers.cache) // (it comes from peers.cache)
peerscache.forEach( peerscache.forEach(
function(acachedpeer) { function(acachedpeer) {
if ( // Add "a cached peer" to "candidate" peers
// Add "a cached peer" to "candidate new" peers // if the cached peer is not in the list of currently
// if the cached peer is not in the list of current node. // connected nodes.
currentnodes.find( function(element) { element.info != acachedpeer } ) if ( ! currentnodes.includes( acachedpeer ) )
)
{ {
candidatenew.push( acachedpeer ); candidate.push( acachedpeer );
} }
} }
); );
if ( candidatenew.length > 0 ) if ( candidate.length > 0 )
{ {
var i = Math.floor( Math.random() * candidatenew.length ); var i = Math.floor( Math.random() * candidate.length );
var enode = candidatenew[i]; var enode = candidate[i];
console.log( console.log(
"We have " "We have "
+ nowpeers.length + nowpeers.length
...@@ -311,6 +310,10 @@ function unlock() ...@@ -311,6 +310,10 @@ function unlock()
function timer() function timer()
{ {
if ( bfa.sockettype == 'ipc' && ! bfa.fs.existsSync( bfa.socketurl ) )
{
return;
}
if ( netid == 0 ) if ( netid == 0 )
{ {
web3.eth.net.getId() web3.eth.net.getId()
...@@ -318,7 +321,7 @@ function timer() ...@@ -318,7 +321,7 @@ function timer()
netid = x; netid = x;
} ) } )
.catch( err => { .catch( err => {
console.error("monitor.js non-fatal: "+err) console.log( "monitor.js waiting for geth to open socket." );
}); });
return; return;
} }
......
#!/usr/bin/node
const Web3 = require( 'web3' );
// make sure we die early if this is not installed
const dummy = require( 'web3-eth-accounts' );
const fs = require( 'fs' );
var web3 = new Web3( 'http://localhost:8545/' );
var myArgs = process.argv.slice(2);
var myaccount = myArgs[0];
var proof = myArgs[1];
var password = myArgs[2] || '';
var contractaddr;
var networkid;
var chainid;
var rawdata;
var estimate;
if ( myArgs.length < 2 || myArgs.length > 3 )
{
let myname = process.argv[1].replace(/^.*\//, '');
console.error( "Wrong number of arguments.");
console.error( "Usage: " + myname + " <account> <proof> [<privatekeypassword>]");
process.exit( 1 );
}
function findMatchingFile( needle, accountdir )
{
return new Promise(
function(resolve, reject)
{
// strip leading '0x' from the needle, if present
// also lowercase the name
needle = needle.replace(/^0x/, '').toLowerCase();
let haystack = fs.readdirSync( accountdir, 'utf8' );
haystack.forEach(
(filename) => {
if ( filename.toLowerCase().endsWith('--'+needle) )
resolve(accountdir + filename);
}
);
reject( 'Account not found. Try specifying the absolute path to your key file, or set one of $BFAHOME $BFANETWORKDIR $BFANODEDIR $KEYSTORE' );
}
);
}
function findaccountfile( accountfile )
{
return new Promise(
function( resolve, reject )
{
// find account file
// is it actually just a file?
if ( accountfile.includes('/') )
{
resolve( accountfile );
return;
}
let accountdir;
// if not a file, then look (only) at the most specific directory we have been told about.
if ( process.env.KEYSTORE !== undefined )
accountdir = process.env.KEYSTORE;
else
if ( process.env.BFANODEDIR !== undefined )
accountdir = process.env.BFANODEDIR + '/keystore/';
else
if ( process.env.BFANETWORKDIR !== undefined )
accountdir = process.env.BFANETWORKDIR + '/node/keystore/';
else
if ( process.env.BFAHOME !== undefined )
accountdir = process.env.BFAHOME + '/network/node/keystore/';
else
accountdir = process.env.HOME + '.geth/keystore';
findMatchingFile( myaccount, accountdir )
.then( resolve )
.catch( reject );
}
);
}
function loadaccount( path )
{
return new Promise(
function( resolve, reject )
{
let contents = fs.readFileSync( path, 'utf8' );
fs.readFile( path, 'utf8', (err,data) => {
if ( err )
{
reject( err );
return;
}
let keystore;
try {
keystore = JSON.parse( data );
}
catch(e)
{
reject( e );
return;
}
let w;
try {
w = web3.eth.accounts.wallet.decrypt( [keystore], password );
}
catch(e)
{
reject( e );
return;
}
// Make sure we have the address properly written (instead of a
// filename) if that was given as parameter when starting the program.
if ( w === undefined )
{
reject( "Unable to decrypt the key file." );
return;
}
myaccount = w[0]["address"];
resolve();
});
}
);
}
function gasestimate(method)
{
return new Promise(
function( resolve, reject )
{
method.estimateGas()
.then( g => { estimate = g } )
.then( resolve )
}
);
}
function getnetworkid()
{
return new Promise(
function( resolve, reject )
{
web3.eth.net.getId()
.then( id => {
networkid = id;
if ( networkid == 0xb10c4d39a )
{
contractaddr = "0xc3cF96aF51d3c41DfBE428dE75a8E5597d4D7A7B";
chainid = 0xbfa2018;
}
else
{
reject( "There is insufficient information to function on this chain." );
return;
}
resolve();
});
}
);
}
function getnonce( account )
{
return new Promise(
function( resolve, reject )
{
// Cuantas transacciones ya hemos hecho?
web3.eth.getTransactionCount( account )
.then( txcount => {
nonce = txcount;
resolve();
});
}
);
}
function prepareCall()
{
var abi = [
{
"name" : "hash",
"type" : "function",
"inputs" : [ { "name": "key", "type": "string" } ],
"outputs" : [ { "name": "", "type": "bytes32" } ],
"constant" : true,
"payable" : false,
"stateMutability" : "pure"
},
{
"name" : "proveControl",
"type" : "function",
"inputs" : [ { "name": "key", "type": "string" } ],
"outputs" : [ { "name": "", "type": "bool" } ],
"constant" : false,
"payable" : false,
"stateMutability" : "nonpayable"
}
];
return new Promise(
function(resolve, reject)
{
let p1 = getnetworkid();
let p2 = getnonce( myaccount );
Promise.all([ p1, p2 ])
.then( () => {
if ( contractaddr === undefined )
{
reject( "The contract address is not defined for this network." );
return;
}
// Creá una instancia del contrato
var contractInstance = new web3.eth.Contract(abi, contractaddr );
//Estimá el gas que vas a gastar
let method = contractInstance.methods.proveControl( proof );
// contractInstance.methods.hash(proof).call().then( console.log );
rawdata = method.encodeABI();
gasestimate( method )
.then( resolve );
});
}
);
}
function signrawtx()
{
//Generá una transacción
let promise = web3.eth.accounts.signTransaction(
{
"from" : myaccount,
"to" : contractaddr,
"nonce" : nonce,
"value" : 0,
"data" : rawdata,
"gas" : estimate,
"gasPrice" : 1000000000,
"common" :
{
"customChain" :
{
"name" : "BFA 2018",
"chainId" : chainid,
"networkId" : networkid
}
}
},
web3.eth.accounts.wallet[0].privateKey
);
return promise;
}
function printReceipt( r )
{
console.log( "blockNumber: " + r.blockNumber );
console.log( "transactionHash: " + r.transactionHash );
console.log( "Status: " + (r.status?'Transaction successful':'Transaction failed') );
}
findaccountfile( myaccount )
.then( (path)=> { return loadaccount(path) } )
// prepara la instancia del contrato
.then ( prepareCall )
// Firma "offline"
.then( () => { return signrawtx() })
// Manda la transaccion a la blockchain
.then( tx => {
console.log( "Sending this transaction: " + tx.rawTransaction );
console.log( "TX hash: " + tx.transactionHash );
//process.exit( 0 );
web3.eth.sendSignedTransaction( tx.rawTransaction )
//Obtené el recibo.
.once( 'receipt', printReceipt )
.catch( (e) => { console.error( "It would seem that the transaction has failed:\n" + e)} );
})
.catch( e => {
console.error( "Oh no. Something most definitely seems to have gone wrong. What I was told is:" );
console.error( e );
});
...@@ -10,46 +10,73 @@ bootnodekeyfile=${BFANETWORKDIR}/bootnode/key ...@@ -10,46 +10,73 @@ bootnodekeyfile=${BFANETWORKDIR}/bootnode/key
# Bail out if anything fails. # Bail out if anything fails.
trap "exit 1" ERR trap "exit 1" ERR
# Detect children dying # Detect children dying
trap "reaper" SIGINT SIGCHLD trap "reaper" SIGCHLD
unset LOGDIR LOGPIPE PIDIDX trap "killprocs" SIGTERM
declare -A PIDIDX trap "killallprocs" EXIT
trap "killallprocs" SIGTERM unset LOGPIPE PIDIDX ALLPIDIDX TMPDIR SHUTTING_DOWN
declare -A PIDIDX ALLPIDIDX
SHUTTING_DOWN=0
function reaper() function reaper()
{ {
local wecare=0 local reaped_a_child_status=0
# Find out which child died
for pid in ${!PIDIDX[*]} for pid in ${!PIDIDX[*]}
do do
kill -0 $pid 2>/dev/null && continue kill -0 $pid 2>/dev/null && continue
reaped_a_child_status=1
local rc=0 local rc=0
wait $pid || rc=$? || true wait $pid || rc=$? || true
echo "*** ${PIDIDX[$pid]} (pid $pid) has exited with value $rc" local name=${PIDIDX[$pid]}
echo "*** $name (pid $pid) has exited with value $rc"
if [ $name = 'geth' ]; then geth_rc_status=$rc; fi
unset PIDIDX[$pid] unset PIDIDX[$pid]
wecare=1
done done
test $wecare = 1 || return # Return if we didn't find out which child died.
# kill all - an extra kill doesn't hurt. I hope. if [ $reaped_a_child_status = 0 ]; then return; fi
# Kill all other registered processes
for pid in ${!PIDIDX[*]} for pid in ${!PIDIDX[*]}
do do
# don't kill log.sh, because it may still be logging for us kill -0 $pid 2>/dev/null || continue
if [ "${PIDIDX[$pid]}" != "log.sh" ] echo "*** Killing ${PIDIDX[$pid]} (pid $pid)."
then kill $pid || true
echo "*** Killing ${PIDIDX[$pid]} (pid $pid)."
kill $pid || true
fi
done done
max=30
} }
function killallprocs() function killprocs()
{ {
SHUTTING_DOWN=1
if [ ${#PIDIDX[*]} -gt 0 ] if [ ${#PIDIDX[*]} -gt 0 ]
then then
echo "*** Killing all remaining processes: ${PIDIDX[*]} (${!PIDIDX[*]})." echo "*** Killing all remaining processes: ${PIDIDX[*]} (${!PIDIDX[*]})."
kill -KILL ${!PIDIDX[*]} 2>/dev/null || true kill ${!PIDIDX[*]} 2>/dev/null || true
fi fi
} }
function killallprocs()
{
# merge the 2 pid list, to make killing and echoing easier
for pid in ${!ALLPIDIDX[*]}
do
PIDIDX[$pid]=${ALLPIDIDX[$pid]}
unset ALLPIDIDX[$pid]
done
killprocs
if [ -n "$TMPDIR" -a -e "$TMPDIR" ]
then
rm -rf "$TMPDIR"
fi
}
function startgeth()
{
echo "***" Starting geth $*
# "NoPruning=true" means "--gcmode archive"
geth --config ${BFATOML} $* &
gethpid=$!
PIDIDX[${gethpid}]="geth"
}
# You can start as: # You can start as:
# BFAHOME=/home/bfa/bfa singlestart.sh # BFAHOME=/home/bfa/bfa singlestart.sh
# singlestart.sh /home/bfa/bfa # singlestart.sh /home/bfa/bfa
...@@ -75,8 +102,19 @@ else ...@@ -75,8 +102,19 @@ else
fi fi
source ${BFAHOME}/bin/libbfa.sh source ${BFAHOME}/bin/libbfa.sh
TMPDIR=$( mktemp -d )
mknod ${TMPDIR}/sleeppipe p
sleep 987654321 > ${TMPDIR}/sleeppipe &
ALLPIDIDX[$!]='sleep'
if [ "$VIRTUALIZATION" = "DOCKER" ] if [ "$VIRTUALIZATION" = "DOCKER" ]
then then
echo
echo
echo
echo
date
echo $0 startup
echo
echo "See log info with \"docker logs\"" echo "See log info with \"docker logs\""
else else
echo "Logging mostly everything to ${BFANODEDIR}/log" echo "Logging mostly everything to ${BFANODEDIR}/log"
...@@ -86,21 +124,40 @@ else ...@@ -86,21 +124,40 @@ else
# Docker has it's own logging facility, so we will not use our own # Docker has it's own logging facility, so we will not use our own
# logging functionality if we're in docker. # logging functionality if we're in docker.
echo "*** Setting up logging." echo "*** Setting up logging."
# Clean up logging LOGPIPE=${TMPDIR}/logpipe
LOGDIR=$( mktemp -d )
trap "rm -rf ${LOGDIR}" EXIT
LOGPIPE=${LOGDIR}/logpipe
mknod ${LOGPIPE} p mknod ${LOGPIPE} p
${BFAHOME}/bin/log.sh ${BFANODEDIR}/log < ${LOGPIPE} & ${BFAHOME}/bin/log.sh ${BFANODEDIR}/log < ${LOGPIPE} &
PIDIDX[$!]="log.sh" # Separate pididx for processes we don't want to send signals to
# until in the very end.
ALLPIDIDX[$!]="log.sh"
exec > ${LOGPIPE} 2>&1 exec > ${LOGPIPE} 2>&1
fi fi
echo "*** Starting geth." function sleep()
# "NoPruning=true" means "--gcmode archive" {
geth --config ${BFATOML} & read -t ${1:-1} < ${TMPDIR}/sleeppipe || true
PIDIDX[$!]="geth" }
# Start a sync
startgeth --exitwhensynced
echo "*** Starting monitor.js"
monitor.js &
PIDIDX[$!]="monitor.js"
# geth will exit when it has synced, then we kill it's monitor.
# Then wait here for their exit status to get reaped
while [ "${#PIDIDX[*]}" -gt 0 ]; do sleep 1; done
# if it went well, start a normal geth (to run "forever")
test $geth_rc_status = 0 || exit $geth_rc_status
test "$SHUTTING_DOWN" != 0 && exit 0
# regular geth
startgeth
# monitor
echo "*** Starting monitor.js"
monitor.js &
PIDIDX[$!]="monitor.js"
# bootnode # bootnode
if [ -r "$bootnodekeyfile" ] if [ -r "$bootnodekeyfile" ]
then then
...@@ -109,16 +166,4 @@ then ...@@ -109,16 +166,4 @@ then
PIDIDX[$!]="bootnode" PIDIDX[$!]="bootnode"
fi fi
echo "*** Starting monitor.js" while [ "${#PIDIDX[*]}" -gt 0 ]; do sleep 1; done
monitor.js &
PIDIDX[$!]="monitor.js"
max=-1
# Exit if only 1 process remains - we hope it is log.sh, but either way,
# it is time to end.
while [ "${#PIDIDX[*]}" -gt 1 -a $max -ne 0 ]
do
sleep 1
max=$(( $max - 1 ))
done
killallprocs
...@@ -11,7 +11,7 @@ bootARIUv6="enode://${enodeARIU}@[2800:110:44:6300::aad2:2db3]:30301" ...@@ -11,7 +11,7 @@ bootARIUv6="enode://${enodeARIU}@[2800:110:44:6300::aad2:2db3]:30301"
enodeUNC="82b66b13d7addcf9ffe1e4e972a105f6ccf50557161c4a0978a5d9ce595ababde609ea8a49897ae89b1d41e90551cb2e9241363238593e950ca68bd5af7c24d6" enodeUNC="82b66b13d7addcf9ffe1e4e972a105f6ccf50557161c4a0978a5d9ce595ababde609ea8a49897ae89b1d41e90551cb2e9241363238593e950ca68bd5af7c24d6"
bootUNCv4="enode://${enodeUNC}@[200.16.28.28]:30301" bootUNCv4="enode://${enodeUNC}@[200.16.28.28]:30301"
enodeDGSI="59ae768ecdee632e0daceccb6f71b215392eba89230d626573f2fb4e9c0786c9a661027ab7343820ca63d96fe48ffd81ed1bf6e4d512f0ba50ec072c9efd9e4e" enodeDGSI="ddbf37799e8d33b0c42dddbda713037b17d14696b29ecf424ca3d57bb47db78a467505e22c5f2b709a98c3d55ac8ecbf4610765385317dd51049438f498881c6"
bootDGSIv4="enode://${enodeDGSI}@[200.108.146.100]:30301" bootDGSIv4="enode://${enodeDGSI}@[200.108.146.100]:30301"
bootnodes="${bootARIUv6},${bootARIUv4},${bootUNCv4},${bootDGSIv4}" bootnodes="${bootARIUv6},${bootARIUv4},${bootUNCv4},${bootDGSIv4}"
......
...@@ -60,8 +60,12 @@ function unlockall() ...@@ -60,8 +60,12 @@ function unlockall()
{ {
var wallets = new Array(); var wallets = new Array();
web3.bfa.personal.listWallets( web3.bfa.personal.listWallets(
function pushone(x) function pushone(err,x)
{ {
if ( err )
bye( 1, err );
if ( x == undefined )
bye( 1, "wallets not defined" );
var failures = 0; var failures = 0;
var promises = new Array(); var promises = new Array();
var i = x.length; var i = x.length;
......
...@@ -59,7 +59,7 @@ HTTPCors = ["*"] ...@@ -59,7 +59,7 @@ HTTPCors = ["*"]
omitempty = "" omitempty = ""
IPCPath = "geth.ipc" IPCPath = "geth.ipc"
HTTPPort = 8545 HTTPPort = 8545
HTTPVirtualHosts = ["localhost"] HTTPVirtualHosts = ["*"]
HTTPModules = ["net", "web3", "eth", "clique"] HTTPModules = ["net", "web3", "eth", "clique"]
WSHost = "0.0.0.0" WSHost = "0.0.0.0"
WSPort = 8546 WSPort = 8546
......
[
{
"name": "proofOfControlWeiAmountChanged",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": false, "name": "amount", "type": "uint256" }
]
},
{
"name": "limitChanged",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "distr", "type": "address" },
{ "indexed": true, "name": "ben", "type": "address" },
{ "indexed": false, "name": "newLimit", "type": "uint256" }
]
},
{
"name": "suitorApproved",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "suitor", "type": "address" }
]
},
{
"name": "suitorNotApproved",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "suitor", "type": "address" }
]
},
{
"name": "kickedDistributor",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "kicked", "type": "address" }
]
},
{
"name": "suitorAdded",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "suitor", "type": "address" },
{ "indexed": true, "name": "distr", "type": "address" }
]
},
{
"name": "addedBeneficiary",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "distr", "type": "address" },
{ "indexed": true, "name": "added", "type": "address" },
{ "indexed": false, "name": "limit", "type": "uint256" }
]
},
{
"name": "kickedBeneficiary",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "distr", "type": "address" },
{ "indexed": true, "name": "kicked", "type": "address" }
]
},
{
"name": "addedDistributor",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "added", "type": "address" },
{ "indexed": false, "name": "top", "type": "uint256" }
]
},
{
"name": "replenished",
"type": "event",
"anonymous": false,
"inputs": [
{ "indexed": true, "name": "distr", "type": "address" },
{ "indexed": false, "name": "amount", "type": "uint256" }
]
},
{
"name": "addBeneficiary",
"type": "function",
"constant": false,
"inputs": [
{ "name": "acc", "type": "address" },
{ "name": "limit", "type": "uint256" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"name": "addSuitor",
"type": "function",
"constant": false,
"inputs": [
{ "name": "add", "type": "address" },
{ "name": "password", "type": "bytes32" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": true,
"stateMutability": "payable"
},
{
"name": "changeLimit",
"type": "function",
"constant": false,
"inputs": [
{ "name": "acc", "type": "address" },
{ "name": "limit", "type": "uint256" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"name": "kickBeneficiary",
"type": "function",
"constant": false,
"inputs": [
{ "name": "acc", "type": "address" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"name": "kickDistributor",
"type": "function",
"constant": false,
"inputs": [
{ "name": "acc", "type": "address" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"name": "addDistributor",
"type": "function",
"constant": false,
"inputs": [
{ "name": "acc", "type": "address" },
{ "name": "top", "type": "uint256" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"name": "proveControl",
"type": "function",
"constant": false,
"inputs": [
{ "name": "key", "type": "string" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"name": "replenish",
"type": "function",
"constant": false,
"inputs": [
{ "name": "acc", "type": "address" },
{ "name": "amount", "type": "uint256" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": true,
"stateMutability": "payable"
},
{
"name": "replenishAll",
"type": "function",
"constant": false,
"inputs": [],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": true,
"stateMutability": "payable"
},
{
"name": "replenishList",
"type": "function",
"constant": false,
"inputs": [
{ "name": "accs", "type": "address[]" },
{ "name": "amounts", "type": "uint256[]" }
],
"outputs": [],
"payable": true,
"stateMutability": "payable"
},
{
"name": "setProofOfControlWeiAmount",
"type": "function",
"constant": false,
"inputs": [
{ "name": "amount", "type": "uint256" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "nonpayable"
},
{
"type": "constructor",
"inputs": [],
"payable": true,
"stateMutability": "payable"
},
{
"name": "getBeneficiariesCount",
"type": "function",
"constant": true,
"inputs": [],
"outputs": [
{ "name": "", "type": "uint256" }
],
"payable": false,
"stateMutability": "view"
},
{
"name": "getBeneficiaryLimit",
"type": "function",
"constant": true,
"inputs": [
{ "name": "acc", "type": "address" }
],
"outputs": [
{ "name": "", "type": "uint256" }
],
"payable": false,
"stateMutability": "view"
},
{
"name": "getDistributorLimit",
"type": "function",
"constant": true,
"inputs": [
{ "name": "acc", "type": "address" }
],
"outputs": [
{ "name": "", "type": "uint256" }
],
"payable": false,
"stateMutability": "view"
},
{
"name": "getProofOfControlWeiAmount",
"type": "function",
"constant": true,
"inputs": [],
"outputs": [
{ "name": "", "type": "uint256" }
],
"payable": false,
"stateMutability": "view"
},
{
"name": "hash",
"type": "function",
"constant": true,
"inputs": [
{ "name": "key", "type": "string" }
],
"outputs": [
{ "name": "", "type": "bytes32" }
],
"payable": false,
"stateMutability": "pure"
},
{
"name": "isBeneficiary",
"type": "function",
"constant": true,
"inputs": [
{ "name": "add", "type": "address" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "view"
},
{
"name": "isDistributor",
"type": "function",
"constant": true,
"inputs": [
{ "name": "add", "type": "address" }
],
"outputs": [
{ "name": "", "type": "bool" }
],
"payable": false,
"stateMutability": "view"
}
]
0xc3cf96af51d3c41dfbe428de75a8e5597d4d7a7b
\ No newline at end of file
[Eth]
NetworkId = 47525974938
SyncMode = "fast"
NoPruning = false
DatabaseCache = 2048
[Node]
DataDir = "/home/bfa/bfa/network/node"
HTTPHost = "0.0.0.0"
HTTPCors = ["*"]
IPCPath = "geth.ipc"
HTTPPort = 8545
HTTPVirtualHosts = ["*"]
HTTPModules = ["net", "web3", "eth", "clique"]
WSHost = "0.0.0.0"
WSPort = 8546
WSModules = ["net", "web3", "eth", "clique"]
[Node.P2P]
BootstrapNodes = ["enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@[2800:110:44:6300::aad2:2db3]:30301", "enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@170.210.45.179:30301", "enode://82b66b13d7addcf9ffe1e4e972a105f6ccf50557161c4a0978a5d9ce595ababde609ea8a49897ae89b1d41e90551cb2e9241363238593e950ca68bd5af7c24d6@200.16.28.28:30301", "enode://59ae768ecdee632e0daceccb6f71b215392eba89230d626573f2fb4e9c0786c9a661027ab7343820ca63d96fe48ffd81ed1bf6e4d512f0ba50ec072c9efd9e4e@200.108.146.100:30301"]
BootstrapNodesV5 = ["enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@[2800:110:44:6300::aad2:2db3]:30301", "enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@170.210.45.179:30301", "enode://82b66b13d7addcf9ffe1e4e972a105f6ccf50557161c4a0978a5d9ce595ababde609ea8a49897ae89b1d41e90551cb2e9241363238593e950ca68bd5af7c24d6@200.16.28.28:30301", "enode://59ae768ecdee632e0daceccb6f71b215392eba89230d626573f2fb4e9c0786c9a661027ab7343820ca63d96fe48ffd81ed1bf6e4d512f0ba50ec072c9efd9e4e@200.108.146.100:30301"]
...@@ -7,7 +7,8 @@ ...@@ -7,7 +7,8 @@
"bignumber.js": "^9.0.0", "bignumber.js": "^9.0.0",
"request": "^2.88.0", "request": "^2.88.0",
"require": "^2.4.20", "require": "^2.4.20",
"web3": "^1.0.0-beta.55", "web3": "^1.2.11",
"web3-eth-accounts": "^1.2.11",
"xmlhttprequest-ssl": "^1.5.5" "xmlhttprequest-ssl": "^1.5.5"
}, },
"repository": { "repository": {
......
...@@ -59,7 +59,7 @@ HTTPCors = ["*"] ...@@ -59,7 +59,7 @@ HTTPCors = ["*"]
omitempty = "" omitempty = ""
IPCPath = "geth.ipc" IPCPath = "geth.ipc"
HTTPPort = 8545 HTTPPort = 8545
HTTPVirtualHosts = ["localhost"] HTTPVirtualHosts = ["*"]
HTTPModules = ["net", "web3", "eth", "clique"] HTTPModules = ["net", "web3", "eth", "clique"]
WSHost = "0.0.0.0" WSHost = "0.0.0.0"
WSPort = 8546 WSPort = 8546
......
[Eth]
NetworkId = 55555000000
SyncMode = "fast"
NoPruning = false
DatabaseCache = 2048
[Node]
DataDir = "/home/bfa/bfa/test2network/node"
HTTPHost = "0.0.0.0"
HTTPCors = ["*"]
IPCPath = "geth.ipc"
HTTPPort = 8545
HTTPVirtualHosts = ["*"]
HTTPModules = ["net", "web3", "eth", "clique"]
WSHost = "0.0.0.0"
WSPort = 8546
WSModules = ["net", "web3", "eth", "clique"]
[Node.P2P]
BootstrapNodes = ["enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@[2800:110:44:6300::aad2:2db3]:30301", "enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@170.210.45.179:30301", "enode://82b66b13d7addcf9ffe1e4e972a105f6ccf50557161c4a0978a5d9ce595ababde609ea8a49897ae89b1d41e90551cb2e9241363238593e950ca68bd5af7c24d6@200.16.28.28:30301", "enode://59ae768ecdee632e0daceccb6f71b215392eba89230d626573f2fb4e9c0786c9a661027ab7343820ca63d96fe48ffd81ed1bf6e4d512f0ba50ec072c9efd9e4e@200.108.146.100:30301"]
BootstrapNodesV5 = ["enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@[2800:110:44:6300::aad2:2db3]:30301", "enode://7ec4dd9d5e1a2b29d6b60aa9f95677c0c3a5f9306e73d65dd3bcbfda3737a8c509b02d1eab763ce39f18cfe96423df7ee544d6c36191ec17f59ade75bc99d358@170.210.45.179:30301", "enode://82b66b13d7addcf9ffe1e4e972a105f6ccf50557161c4a0978a5d9ce595ababde609ea8a49897ae89b1d41e90551cb2e9241363238593e950ca68bd5af7c24d6@200.16.28.28:30301", "enode://59ae768ecdee632e0daceccb6f71b215392eba89230d626573f2fb4e9c0786c9a661027ab7343820ca63d96fe48ffd81ed1bf6e4d512f0ba50ec072c9efd9e4e@200.108.146.100:30301"]
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment