Skip to content

Commit

Permalink
Merge remote-tracking branch 'upstream/master'
Browse files Browse the repository at this point in the history
  • Loading branch information
pooler committed Apr 16, 2020
2 parents 4d7d640 + 872380a commit e8da16f
Show file tree
Hide file tree
Showing 7 changed files with 48 additions and 45 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ bin/
.idea
.mypy_cache
.vscode
electrum-ltc_data

# icons
electrum_ltc/gui/kivy/theming/light-0.png
Expand Down
2 changes: 1 addition & 1 deletion electrum_ltc/channel_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -242,7 +242,7 @@ class ChannelDB(SqlDB):

def __init__(self, network: 'Network'):
path = os.path.join(get_headers_dir(network.config), 'gossip_db')
super().__init__(network, path, commit_interval=100)
super().__init__(network.asyncio_loop, path, commit_interval=100)
self.lock = threading.RLock()
self.num_nodes = 0
self.num_channels = 0
Expand Down
13 changes: 9 additions & 4 deletions electrum_ltc/commands.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,7 @@
from .address_synchronizer import TX_HEIGHT_LOCAL
from .mnemonic import Mnemonic
from .lnutil import SENT, RECEIVED
from .lnutil import LnFeatures
from .lnutil import ln_dummy_address
from .lnpeer import channel_id_from_funding_tx
from .plugin import run_hook
Expand Down Expand Up @@ -965,18 +966,21 @@ async def help(self):

# lightning network commands
@command('wn')
async def add_peer(self, connection_string, timeout=20, wallet: Abstract_Wallet = None):
await wallet.lnworker.add_peer(connection_string)
async def add_peer(self, connection_string, timeout=20, gossip=False, wallet: Abstract_Wallet = None):
lnworker = self.network.lngossip if gossip else wallet.lnworker
await lnworker.add_peer(connection_string)
return True

@command('wn')
async def list_peers(self, wallet: Abstract_Wallet = None):
async def list_peers(self, gossip=False, wallet: Abstract_Wallet = None):
lnworker = self.network.lngossip if gossip else wallet.lnworker
return [{
'node_id':p.pubkey.hex(),
'address':p.transport.name(),
'initialized':p.is_initialized(),
'features': str(LnFeatures(p.features)),
'channels': [c.funding_outpoint.to_str() for c in p.channels.values()],
} for p in wallet.lnworker.peers.values()]
} for p in lnworker.peers.values()]

@command('wpn')
async def open_channel(self, connection_string, amount, push_amount=0, password=None, wallet: Abstract_Wallet = None):
Expand Down Expand Up @@ -1165,6 +1169,7 @@ def eval_bool(x: str) -> bool:
'from_height': (None, "Only show transactions that confirmed after given block height"),
'to_height': (None, "Only show transactions that confirmed before given block height"),
'iknowwhatimdoing': (None, "Acknowledge that I understand the full implications of what I am about to do"),
'gossip': (None, "Apply command to gossip node instead of wallet"),
}


Expand Down
13 changes: 6 additions & 7 deletions electrum_ltc/interface.py
Original file line number Diff line number Diff line change
Expand Up @@ -463,13 +463,12 @@ async def save_certificate(self):

async def get_certificate(self):
sslc = ssl.SSLContext()
try:
async with _RSClient(session_factory=RPCSession,
host=self.host, port=self.port,
ssl=sslc, proxy=self.proxy) as session:
return session.transport._asyncio_transport._ssl_protocol._sslpipe._sslobj.getpeercert(True)
except ValueError:
return None
async with _RSClient(session_factory=RPCSession,
host=self.host, port=self.port,
ssl=sslc, proxy=self.proxy) as session:
asyncio_transport = session.transport._asyncio_transport # type: asyncio.BaseTransport
ssl_object = asyncio_transport.get_extra_info("ssl_object") # type: ssl.SSLObject
return ssl_object.getpeercert(binary_form=True)

async def get_block_header(self, height, assert_mode):
self.logger.info(f'requesting block header {height} in mode {assert_mode}')
Expand Down
9 changes: 5 additions & 4 deletions electrum_ltc/lnpeer.py
Original file line number Diff line number Diff line change
Expand Up @@ -74,6 +74,7 @@ def __init__(self, lnworker: Union['LNGossip', 'LNWallet'], pubkey:bytes, transp
self.lnworker = lnworker
self.privkey = self.transport.privkey # local privkey
self.features = self.lnworker.features
self.their_features = 0
self.node_ids = [self.pubkey, privkey_to_pubkey(self.privkey)]
self.network = lnworker.network
self.channel_db = lnworker.network.channel_db
Expand Down Expand Up @@ -200,15 +201,15 @@ def on_init(self, payload):
if self._received_init:
self.logger.info("ALREADY INITIALIZED BUT RECEIVED INIT")
return
their_features = LnFeatures(int.from_bytes(payload['features'], byteorder="big"))
self.their_features = LnFeatures(int.from_bytes(payload['features'], byteorder="big"))
their_globalfeatures = int.from_bytes(payload['globalfeatures'], byteorder="big")
their_features |= their_globalfeatures
self.their_features |= their_globalfeatures
# check transitive dependencies for received features
if not their_features.validate_transitive_dependecies():
if not self.their_features.validate_transitive_dependecies():
raise GracefulDisconnect("remote did not set all dependencies for the features they sent")
# check if features are compatible, and set self.features to what we negotiated
try:
self.features = ln_compare_features(self.features, their_features)
self.features = ln_compare_features(self.features, self.their_features)
except IncompatibleLightningFeatures as e:
self.initialized.set_exception(e)
raise GracefulDisconnect(f"{str(e)}")
Expand Down
49 changes: 23 additions & 26 deletions electrum_ltc/lnworker.py
Original file line number Diff line number Diff line change
Expand Up @@ -392,6 +392,29 @@ def on_proxy_changed(self, event, *args):
peer.close_and_cleanup()
self._clear_addr_retry_times()

@log_exceptions
async def add_peer(self, connect_str: str) -> Peer:
node_id, rest = extract_nodeid(connect_str)
peer = self._peers.get(node_id)
if not peer:
if rest is not None:
host, port = split_host_port(rest)
else:
addrs = self.channel_db.get_node_addresses(node_id)
if not addrs:
raise ConnStringFormatError(_('Don\'t know any addresses for node:') + ' ' + bh2u(node_id))
host, port, timestamp = self.choose_preferred_address(addrs)
port = int(port)
# Try DNS-resolving the host (if needed). This is simply so that
# the caller gets a nice exception if it cannot be resolved.
try:
await asyncio.get_event_loop().getaddrinfo(host, port)
except socket.gaierror:
raise ConnStringFormatError(_('Hostname does not resolve (getaddrinfo failed)'))
# add peer
peer = await self._add_peer(host, port, node_id)
return peer


class LNGossip(LNWorker):
max_age = 14*24*3600
Expand Down Expand Up @@ -716,9 +739,6 @@ async def on_channel_update(self, chan):
self.logger.info('REBROADCASTING CLOSING TX')
await self.network.try_broadcasting(force_close_tx, 'force-close')




@log_exceptions
async def _open_channel_coroutine(self, *, connect_str: str, funding_tx: PartialTransaction,
funding_sat: int, push_sat: int,
Expand Down Expand Up @@ -750,29 +770,6 @@ def add_new_channel(self, chan):
channels_db[chan.channel_id.hex()] = chan.storage
self.wallet.save_backup()

@log_exceptions
async def add_peer(self, connect_str: str) -> Peer:
node_id, rest = extract_nodeid(connect_str)
peer = self._peers.get(node_id)
if not peer:
if rest is not None:
host, port = split_host_port(rest)
else:
addrs = self.channel_db.get_node_addresses(node_id)
if not addrs:
raise ConnStringFormatError(_('Don\'t know any addresses for node:') + ' ' + bh2u(node_id))
host, port, timestamp = self.choose_preferred_address(addrs)
port = int(port)
# Try DNS-resolving the host (if needed). This is simply so that
# the caller gets a nice exception if it cannot be resolved.
try:
await asyncio.get_event_loop().getaddrinfo(host, port)
except socket.gaierror:
raise ConnStringFormatError(_('Hostname does not resolve (getaddrinfo failed)'))
# add peer
peer = await self._add_peer(host, port, node_id)
return peer

def mktx_for_open_channel(self, *, coins: Sequence[PartialTxInput], funding_sat: int,
fee_est=None) -> PartialTransaction:
dummy_address = ln_dummy_address()
Expand Down
6 changes: 3 additions & 3 deletions electrum_ltc/sql_db.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,9 @@ def wrapper(self, *args, **kwargs):

class SqlDB(Logger):

def __init__(self, network, path, commit_interval=None):
def __init__(self, asyncio_loop, path, commit_interval=None):
Logger.__init__(self)
self.network = network
self.asyncio_loop = asyncio_loop
self.path = path
self.commit_interval = commit_interval
self.db_requests = queue.Queue()
Expand All @@ -34,7 +34,7 @@ def run_sql(self):
self.logger.info("Creating database")
self.create_database()
i = 0
while self.network.asyncio_loop.is_running():
while self.asyncio_loop.is_running():
try:
future, func, args, kwargs = self.db_requests.get(timeout=0.1)
except queue.Empty:
Expand Down

0 comments on commit e8da16f

Please sign in to comment.