UnstoppableSwap / core

Bitcoin–Monero Cross-chain Atomic Swap (+ GUI)
GNU General Public License v3.0
19 stars 5 forks source link

Release build segfaults on quote request #95

Open binarybaron opened 1 month ago

binarybaron commented 1 month ago

When running the preview AppImage on linux (ubuntu 24), I get a segfault after requesting a quote from a provider.

: BlockTime { height: 2980178, timestamp: 1726934410 } }    
2024-09-21T16:00:10.622132731Z  INFO get_balance{balance=BalanceArgs { force_refresh: true } method="get_balance"}: Checked Bitcoin balance balance=0 BTC
2024-09-21T16:00:10.754434804Z DEBUG advancing offset within the current segment from 58009 to 58077    
2024-09-21T16:00:10.754861743Z DEBUG wrote lsns 58009-58076 to disk at offsets 58009-58076, maxed false complete_len 68    
2024-09-21T16:00:10.754886054Z DEBUG mark_interval(58009, 68)    
2024-09-21T16:00:10.754898005Z DEBUG new highest interval: 58009 - 58076    
2024-09-21T16:25:41.748385699Z  INFO buy_xmr{buy_xmr=BuyXmrArgs { seller: "/dns4/testnet.unstoppableswap.net/tcp/9839/p2p/12D3KooWGpVc1Bf9B7rTqP23BaLpWdJ9r6fdSU86TZ7GotuU1KYQ", bitcoin_change_address: None, monero_receive_address: Address { network: Stagenet, addr_type: SubAddress, public_spend: 22f6e4d45c86a8be2810e2fba7484c8d2c8be4f5d91f62cf28fccc36cf5252fa, public_view: ac7434fb2a7bc9672ef30704a8fef4cda5d20153fd41c6cf14a6a322e36cc4d3 } } method="buy_xmr"}: No --change-address supplied. Any change will be received to the internal wallet. internal_wallet_address=tb1q764n8zl2vxtl03p4d9m84k6lqrpyra7fpxyc3z
Segmentation fault (core dumped)
binarybaron commented 2 weeks ago

Output from rust-gdb with coredump file loaded:

rust-gdb target/release/swap
GNU gdb (Ubuntu 12.1-0ubuntu1~22.04.2) 12.1
Copyright (C) 2022 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "x86_64-linux-gnu".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<https://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
    <http://www.gnu.org/software/gdb/documentation/>.

For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from target/release/swap...
(No debugging symbols found in target/release/swap)
(gdb) core-file /var/lib/apport/coredump/core._root_testing-releases_core_target_release_swap.0.03d0badd-fe53-4c34-8e99-98a4c09445e5.3621066.733291890 
[New LWP 3621066]
[New LWP 3621067]
[New LWP 3621068]
[New LWP 3621071]
[New LWP 3621073]
[New LWP 3621070]
[New LWP 3621072]
[New LWP 3621069]
[New LWP 3621076]
[New LWP 3621077]
[New LWP 3621075]
[New LWP 3621074]
[New LWP 3621078]
warning: Section `.reg-xstate/3621066' in core file too small.
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
Core was generated by `./target/release/swap list-sellers --rendezvous-point /dns4/discover.unstoppabl'.
Program terminated with signal SIGSEGV, Segmentation fault.
warning: Section `.reg-xstate/3621066' in core file too small.
#0  0x000055b91d1471c0 in _ZN4sha26sha5123x8627sha512_compress_x86_64_avx217hacb649f105d99b90E.llvm.15251769145856391368 ()
[Current thread is 1 (Thread 0x7fe431a0c480 (LWP 3621066))]
(gdb) bt
#0  0x000055b91d1471c0 in _ZN4sha26sha5123x8627sha512_compress_x86_64_avx217hacb649f105d99b90E.llvm.15251769145856391368 ()
#1  0x000055b91d147046 in sha2::sha512::Engine512::finish ()
#2  0x000055b91d1470ff in <sha2::sha512::Sha512 as digest::fixed::FixedOutputDirty>::finalize_into_dirty ()
#3  0x000055b91d109b3c in <ed25519_dalek::secret::ExpandedSecretKey as core::convert::From<&ed25519_dalek::secret::SecretKey>>::from ()
#4  0x000055b91d0c28eb in <libp2p_core::identity::ed25519::Keypair as core::convert::From<libp2p_core::identity::ed25519::SecretKey>>::from
    ()
#5  0x000055b91c6a8f48 in swap::seed::Seed::derive_libp2p_identity ()
#6  0x000055b91c2ccbdf in <tracing::instrument::Instrumented<T> as core::future::future::Future>::poll ()
#7  0x000055b91c369b59 in swap::cli::api::request::list_sellers::{{closure}} ()
#8  0x000055b91c3732ba in swap::cli::command::parse_args_and_apply_defaults::{{closure}} ()
#9  0x000055b91c38ebc5 in tokio::runtime::park::CachedParkThread::block_on ()
#10 0x000055b91c0010ff in tokio::runtime::context::runtime::enter_runtime ()
#11 0x000055b91c1e2f71 in swap::main ()
#12 0x000055b91c21b353 in std::sys_common::backtrace::__rust_begin_short_backtrace ()
#13 0x000055b91c1aa76d in std::rt::lang_start::{{closure}} ()
#14 0x000055b91d2cbe90 in std::rt::lang_start_internal ()
#15 0x000055b91c1e314c in main ()
(gdb) info registers
Missing register name
(gdb) disassemble
Dump of assembler code for function _ZN4sha26sha5123x8627sha512_compress_x86_64_avx217hacb649f105d99b90E.llvm.15251769145856391368:
   0x000055b91d147160 <+0>: push   %rbp
   0x000055b91d147161 <+1>: push   %r15
   0x000055b91d147163 <+3>: push   %r14
   0x000055b91d147165 <+5>: push   %r13
   0x000055b91d147167 <+7>: push   %r12
   0x000055b91d147169 <+9>: push   %rbx
   0x000055b91d14716a <+10>:    sub    $0x378,%rsp
   0x000055b91d147171 <+17>:    xor    %r11d,%r11d
   0x000055b91d147174 <+20>:    test   $0x1,%dl
   0x000055b91d147177 <+23>:    mov    %rsi,0x60(%rsp)
   0x000055b91d14717c <+28>:    mov    %rdi,0x58(%rsp)
   0x000055b91d147181 <+33>:    je     0x55b91d1475bf <_ZN4sha26sha5123x8627sha512_compress_x86_64_avx217hacb649f105d99b90E.llvm.15251769145856391368+1119>
   0x000055b91d147187 <+39>:    mov    %rdx,0x8(%rsp)
   0x000055b91d14718c <+44>:    mov    (%rdi),%rdx
   0x000055b91d14718f <+47>:    mov    0x8(%rdi),%r13
   0x000055b91d147193 <+51>:    mov    0x10(%rdi),%rbx
   0x000055b91d147197 <+55>:    mov    0x18(%rdi),%rcx
   0x000055b91d14719b <+59>:    mov    0x20(%rdi),%r10
   0x000055b91d14719f <+63>:    mov    0x28(%rdi),%rax
   0x000055b91d1471a3 <+67>:    vmovdqu (%rsi),%xmm0
   0x000055b91d1471a7 <+71>:    vmovdqa 0x426e81(%rip),%xmm7        # 0x55b91d56e030
   0x000055b91d1471af <+79>:    vpshufb %xmm7,%xmm0,%xmm2
   0x000055b91d1471b4 <+84>:    vpaddq 0x426e84(%rip),%xmm2,%xmm0        # 0x55b91d56e040
   0x000055b91d1471bc <+92>:    mov    0x30(%rdi),%r14
=> 0x000055b91d1471c0 <+96>:    vmovdqa %xmm0,0xf8(%rsp)
   0x000055b91d1471c9 <+105>:   vmovdqu 0x10(%rsi),%xmm0
   0x000055b91d1471ce <+110>:   vpshufb %xmm7,%xmm0,%xmm3
   0x000055b91d1471d3 <+115>:   vpaddq 0x426e75(%rip),%xmm3,%xmm0        # 0x55b91d56e050
   0x000055b91d1471db <+123>:   vmovdqa %xmm0,0x108(%rsp)
   0x000055b91d1471e4 <+132>:   vmovdqu 0x20(%rsi),%xmm0
   0x000055b91d1471e9 <+137>:   vpshufb %xmm7,%xmm0,%xmm0
   0x000055b91d1471ee <+142>:   vpaddq 0x426e6a(%rip),%xmm0,%xmm1        # 0x55b91d56e060
   0x000055b91d1471f6 <+150>:   vmovdqa %xmm1,0x118(%rsp)
   0x000055b91d1471ff <+159>:   vmovdqu 0x30(%rsi),%xmm1
   0x000055b91d147204 <+164>:   vpshufb %xmm7,%xmm1,%xmm1
   0x000055b91d147209 <+169>:   vpaddq 0x426e5f(%rip),%xmm1,%xmm5        # 0x55b91d56e070
   0x000055b91d147211 <+177>:   vmovdqu 0x40(%rsi),%xmm4
   0x000055b91d147216 <+182>:   vpshufb %xmm7,%xmm4,%xmm4
binarybaron commented 2 weeks ago

The segfault seems to be coming from a call to this by libp2p.

binarybaron commented 2 weeks ago

I believe this function is the culprit. There are unsafe calls as a result of this function.

swap/src/seed.rs

pub fn derive_libp2p_identity(&self) -> identity::Keypair {
        let bytes = self.derive(b"NETWORK").derive(b"LIBP2P_IDENTITY").bytes();
        let key = identity::ed25519::SecretKey::from_bytes(bytes).expect("we always pass 32 bytes");

        identity::Keypair::Ed25519(key.into())
    }
binarybaron commented 2 weeks ago

https://github.com/libp2p/rust-libp2p/issues/5631

binarybaron commented 1 week ago

I'm assuming this is caused by some bug due to the mismatch in the old library (2 years old) and our new compiler version (1.79). I think we have a good shot at fixing this for now by:

  1. Try to re-produce this by compiling upstream with 1.79
  2. Downgrading to 1.74 rustc again. We'll have to replace the async trait function with a macro. Once we upgrade libp2p, we again upgrade to 1.79 / 1.80 again
  3. We could also try upgrading the sha256 library but I'm unsure it that'll work as it'll likely be incompatible with our old libp2p version

@Einliterflasche Maybe you can try this? I don't have a linux machine to try this on

Einliterflasche commented 1 week ago

We cannot downgrade rustc to 1.74 because Tauri requires newer versions (tauri@2.0.3 requires >=1.77.2 and tauri-plugin-cli@2.0.0 requires >=1.78). I just added the #[async_trait] attribute to swap::cli::api::Request] and it seems to work now (or at least, it doesn't immediatly segfault`):

Screenshot from 2024-10-17 09-55-09

binarybaron commented 1 week ago

New idea: use a different sha256 library

Einliterflasche commented 1 week ago

didn't work either. we'll have to complete the libp2p ugrade and until then release debug builds for our linux previews