tupshin / cassandra-rs

Apache License 2.0
50 stars 16 forks source link

Segfault when preparing invalid query #14

Closed davideagen closed 8 years ago

davideagen commented 8 years ago

I inadvertently mispelled the table name of my query. This caused the app to segfault with this stack trace:

Program terminated with signal SIGSEGV, Segmentation fault.
#0  0x000055fdeeafb003 in cass::Atomic<int>::fetch_sub(int, cass::MemoryOrder)
    ()
[Current thread is 1 (Thread 0x7f25d5e0c800 (LWP 5278))]
warning: Missing auto-load script at offset 0 in section .debug_gdb_scripts
of file /home/david/dev/rust/caspreptest/target/debug/caspreptest.
Use `info auto-load python-scripts [REGEXP]' to list them.
b(gdb) bt
#0  0x000055fdeeafb003 in cass::Atomic<int>::fetch_sub(int, cass::MemoryOrder)
    ()
#1  0x000055fdeeb18f2a in cass::RefCounted<cass::Prepared>::dec_ref() const ()
#2  0x000055fdeeb17f54 in cass_prepared_free ()
#3  0x000055fdeeaf8d24 in cassandra::cassandra::prepared::PreparedStatement.Drop::drop (self=0x7ffc61936aa8)
    at /home/david/.cargo/registry/src/github.com-88ac128001ac3a9a/cassandra-0.6.3/src/cassandra/prepared.rs:24
#4  0x000055fdeeaf8cbd in cassandra..prepared..PreparedStatement::drop.14743::hfcbf84fa845250d5 () at ../src/libcore/fmt/mod.rs:1301
#5  0x000055fdeeaf8c69 in cassandra::cassandra::error::CassError::wrap<cassandra::cassandra::prepared::PreparedStatement> (self=..., wrappee=...)
    at /home/david/.cargo/registry/src/github.com-88ac128001ac3a9a/cassandra-0.6.3/src/cassandra/error.rs:138
#6  0x000055fdeeaf8b82 in cassandra::cassandra::future::PreparedFuture::error_code (self=0x7ffc61936bf8)
    at /home/david/.cargo/registry/src/github.com-88ac128001ac3a9a/cassandra-0.6.3/src/cassandra/future.rs:220
#7  0x000055fdeeaf8b0f in cassandra::cassandra::future::PreparedFuture::wait (
    self=0x7ffc61936bf8)
    at /home/david/.cargo/registry/src/github.com-88ac128001ac3a9a/cassandra-0.6.3/src/cassandra/future.rs:213
#8  0x000055fdeeae8c1c in caspreptest::main () at src/main.rs:14

Rather than crash, an error result should be returned. It appears by the stacktrace that the code attempts to do that but when the PreparedStatement's Drop method is called it leads to the segfault.

Test code to reproduce the issue. Anything wrong with the query will cause it to segfault in the call to wait().

extern crate cassandra;
use cassandra::Cluster;
use cassandra::ContactPoints;
use std::str::FromStr;

fn main() {
    let seeds = "127.0.0.1";
    let mut cluster = Cluster::new();
    let contact_points = ContactPoints::from_str(seeds).unwrap();
    cluster.set_contact_points(contact_points).unwrap();
    cluster.set_load_balance_round_robin();
    let session = cluster.connect().unwrap();
    static USERS_INSERT:&'static str = 
        "INSERT into example.non_exist_table (non_exist_field) values(?);";
    session.prepare(USERS_INSERT).unwrap().wait().unwrap(); // Crashes on wait()
}

This occurs with cassandra 0.6.3, cassandra-sys 0.4.1, DataStax cpp-driver 2.2.2, and Rustc 1.6.0.