From 911df4c03bc3a1b28f9e88c715d56a1054ccae88 Mon Sep 17 00:00:00 2001 From: Philip O'Toole Date: Fri, 30 Jul 2021 17:25:46 -0400 Subject: [PATCH] Don't leak a database if deserialization fails Fixes https://github.com/rqlite/rqlite/issues/837. --- db/db.go | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/db/db.go b/db/db.go index 0395c65b..9df311db 100644 --- a/db/db.go +++ b/db/db.go @@ -139,7 +139,7 @@ func LoadInMemoryWithDSN(dbPath, dsn string) (*DB, error) { // DeserializeInMemoryWithDSN loads an in-memory database with that contained // in the byte slide, with the specified DSN. The byte slice must not be changed // or garbage-collected until after this function returns. -func DeserializeInMemoryWithDSN(b []byte, dsn string) (*DB, error) { +func DeserializeInMemoryWithDSN(b []byte, dsn string) (retDB *DB, retErr error) { tmpDB, err := OpenInMemoryWithDSN(dsn) if err != nil { return nil, fmt.Errorf("DeserializeInMemoryWithDSN: %s", err.Error()) @@ -173,6 +173,12 @@ func DeserializeInMemoryWithDSN(b []byte, dsn string) (*DB, error) { if err != nil { return nil, fmt.Errorf("DeserializeInMemoryWithDSN: %s", err.Error()) } + defer func() { + // Don't leak a database if deserialization fails. + if retErr != nil { + db.Close() + } + }() if err := copyDatabase(db, tmpDB); err != nil { return nil, fmt.Errorf("DeserializeInMemoryWithDSN: %s", err.Error())