Skip to content

Commit

Permalink
Use upstream AES-XTS VFS for sqlite; Make sqlite API more adaptable
Browse files Browse the repository at this point in the history
Signed-off-by: Ben Krieger <[email protected]>
  • Loading branch information
ben-krieger committed Oct 17, 2024
1 parent fd239a9 commit 159dea1
Show file tree
Hide file tree
Showing 6 changed files with 33 additions and 387 deletions.
2 changes: 1 addition & 1 deletion examples/cmd/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ func server() error { //nolint:gocyclo
if dbPath == "" {
return errors.New("db flag is required")
}
state, err := sqlite.New(dbPath, dbPass)
state, err := sqlite.Open(dbPath, dbPass)
if err != nil {
return err
}
Expand Down
8 changes: 4 additions & 4 deletions sqlite/go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,12 @@ replace github.com/fido-device-onboard/go-fdo => ../

require (
github.com/fido-device-onboard/go-fdo v0.0.0-00010101000000-000000000000
github.com/ncruces/go-sqlite3 v0.18.4
golang.org/x/crypto v0.27.0
github.com/ncruces/go-sqlite3 v0.19.1-0.20241017164609-963524449be2
golang.org/x/crypto v0.28.0
)

require (
github.com/ncruces/julianday v1.0.0 // indirect
github.com/tetratelabs/wazero v1.8.0 // indirect
golang.org/x/sys v0.25.0 // indirect
github.com/tetratelabs/wazero v1.8.1 // indirect
golang.org/x/sys v0.26.0 // indirect
)
9 changes: 9 additions & 0 deletions sqlite/go.sum
Original file line number Diff line number Diff line change
@@ -1,12 +1,21 @@
github.com/ncruces/go-sqlite3 v0.18.4 h1:Je8o3y33MDwPYY/Cacas8yCsuoUzpNY/AgoSlN2ekyE=
github.com/ncruces/go-sqlite3 v0.18.4/go.mod h1:4HLag13gq1k10s4dfGBhMfRVsssJRT9/5hYqVM9RUYo=
github.com/ncruces/go-sqlite3 v0.19.1-0.20241017164609-963524449be2 h1:KcdeukIB8CLTFViQA/5ui06IjmZnJxVNiqwYV2i1yxI=
github.com/ncruces/go-sqlite3 v0.19.1-0.20241017164609-963524449be2/go.mod h1:yL4ZNWGsr1/8pcLfpPW1RT1WFdvyeHonrgIwwi4rvkg=
github.com/ncruces/julianday v1.0.0 h1:fH0OKwa7NWvniGQtxdJRxAgkBMolni2BjDHaWTxqt7M=
github.com/ncruces/julianday v1.0.0/go.mod h1:Dusn2KvZrrovOMJuOt0TNXL6tB7U2E8kvza5fFc9G7g=
github.com/tetratelabs/wazero v1.8.0 h1:iEKu0d4c2Pd+QSRieYbnQC9yiFlMS9D+Jr0LsRmcF4g=
github.com/tetratelabs/wazero v1.8.0/go.mod h1:yAI0XTsMBhREkM/YDAK/zNou3GoiAce1P6+rp/wQhjs=
github.com/tetratelabs/wazero v1.8.1 h1:NrcgVbWfkWvVc4UtT4LRLDf91PsOzDzefMdwhLfA550=
github.com/tetratelabs/wazero v1.8.1/go.mod h1:yAI0XTsMBhREkM/YDAK/zNou3GoiAce1P6+rp/wQhjs=
golang.org/x/crypto v0.27.0 h1:GXm2NjJrPaiv/h1tb2UH8QfgC/hOf/+z0p6PT8o1w7A=
golang.org/x/crypto v0.27.0/go.mod h1:1Xngt8kV6Dvbssa53Ziq6Eqn0HqbZi5Z6R0ZpwQzt70=
golang.org/x/crypto v0.28.0 h1:GBDwsMXVQi34v5CCYUm2jkJvu4cbtru2U4TN2PSyQnw=
golang.org/x/crypto v0.28.0/go.mod h1:rmgy+3RHxRZMyY0jjAJShp2zgEdOqj2AO7U0pYmeQ7U=
golang.org/x/sys v0.25.0 h1:r+8e+loiHxRqhXVl6ML1nO3l1+oFoWbnlu2Ehimmi34=
golang.org/x/sys v0.25.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/sys v0.26.0 h1:KHjCJyddX0LoSTb3J+vWpupP9p0oznkqVk/IfjymZbo=
golang.org/x/sys v0.26.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA=
golang.org/x/text v0.18.0 h1:XvMDiNzPAl0jr17s6W9lcaIhGUfUORdGCNsuLmPG224=
golang.org/x/text v0.18.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY=
golang.org/x/text v0.19.0 h1:kTxAhCbGbxhK0IwgSKiMO5awPoDQ0RpfiVYBfK860YM=
30 changes: 18 additions & 12 deletions sqlite/sqlite.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,16 +24,16 @@ import (
"strings"
"time"

"github.com/ncruces/go-sqlite3/driver" // Load database/sql driver
_ "github.com/ncruces/go-sqlite3/embed" // Load sqlite WASM binary
"github.com/ncruces/go-sqlite3/driver" // Load database/sql driver
_ "github.com/ncruces/go-sqlite3/embed" // Load sqlite WASM binary
_ "github.com/ncruces/go-sqlite3/vfs/xts" // Encryption VFS

"github.com/fido-device-onboard/go-fdo"
"github.com/fido-device-onboard/go-fdo/cbor"
"github.com/fido-device-onboard/go-fdo/cose"
"github.com/fido-device-onboard/go-fdo/custom"
"github.com/fido-device-onboard/go-fdo/kex"
"github.com/fido-device-onboard/go-fdo/protocol"
_ "github.com/fido-device-onboard/go-fdo/sqlite/xts" // Encryption VFS
)

// DB implements FDO server state persistence.
Expand All @@ -44,29 +44,36 @@ type DB struct {
db *sql.DB
}

// New creates or opens a SQLite database file using a single non-pooled
// Open creates or opens a SQLite database file using a single non-pooled
// connection. If a password is specified, then the xts VFS will be used
// with a text key.
func New(filename, password string) (*DB, error) {
func Open(filename, password string) (*DB, error) {
var query string
if password != "" {
query += fmt.Sprintf("?vfs=xts&_pragma=textkey(%q)", password)
query += fmt.Sprintf("?vfs=xts&_pragma=textkey(%q)&_pragma=temp_store(memory)", password)
}
connector, err := (&driver.SQLite{}).OpenConnector("file:" + filepath.Clean(filename) + query)
if err != nil {
return nil, fmt.Errorf("error creating sqlite connector: %w", err)
}
db := sql.OpenDB(connector)
return Init(db)
if err := Init(db); err != nil {
return nil, err
}
return New(db), nil
}

// New creates a DB. The expected tables must already be created and pragmas
// must already be set, including foreign_keys=ON.
func New(db *sql.DB) *DB { return &DB{db: db} }

// Init ensures all tables are created and pragma are set. It does not
// recognize if tables have been created with invalid schemas.
//
// In most cases, New should be used, which implicitly calls Init. However,
// Init can be useful for alternative SQLite connections that do not use a
// local file, such as Cloudflare D1.
func Init(db *sql.DB) (*DB, error) {
func Init(db *sql.DB) error {
stmts := []string{
`PRAGMA foreign_keys = ON`,
`CREATE TABLE IF NOT EXISTS secrets
Expand Down Expand Up @@ -153,13 +160,12 @@ func Init(db *sql.DB) (*DB, error) {
if _, err := db.Exec(sql); err != nil {
_ = db.Close()
if strings.Contains(err.Error(), "file is not a database") {
return nil, fmt.Errorf("file is not a database: likely due to incorrect or missing database password")
return fmt.Errorf("file is not a database: likely due to incorrect or missing database password")
}
return nil, fmt.Errorf("error creating tables: %w", err)
return fmt.Errorf("error creating tables: %w", err)
}
}

return &DB{db: db}, nil
return nil
}

// Close closes the database connection.
Expand Down
2 changes: 1 addition & 1 deletion sqlite/sqlite_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ func newDB(t *testing.T) (_ *sqlite.DB, cleanup func() error) {
cleanup = func() error { return os.Remove("db.test") }
_ = cleanup()

state, err := sqlite.New("db.test", "test_password")
state, err := sqlite.Open("db.test", "test_password")
if err != nil {
t.Fatal(err)
}
Expand Down
Loading

0 comments on commit 159dea1

Please sign in to comment.