Skip to content

Commit df2fbdf

Browse files
fuzz-marshal-float-64ptr
1 parent 34fdeeb commit df2fbdf

File tree

3 files changed

+203
-35
lines changed

3 files changed

+203
-35
lines changed

.github/workflows/main.yml

Lines changed: 85 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,90 @@ jobs:
2525
- run: go vet
2626
- name: Run unit tests
2727
run: go test -v -tags unit -race
28+
Fuzz:
29+
timeout-minutes: 15
30+
needs:
31+
- build
32+
name: Fuzz tests
33+
runs-on: ubuntu-latest
34+
strategy:
35+
fail-fast: false
36+
matrix:
37+
go: [ '1.19', '1.20' ]
38+
cassandra_version: [ '4.0.8', '4.1.1' ]
39+
auth: [ "false" ]
40+
compressor: [ "snappy" ]
41+
tags: [ "cassandra", "integration", "ccm", "fuzz" ]
42+
steps:
43+
- uses: actions/checkout@v2
44+
- uses: actions/setup-go@v2
45+
with:
46+
go-version: ${{ matrix.go }}
47+
- uses: actions/cache@v2
48+
id: gomod-cache
49+
with:
50+
path: ~/go/pkg/mod
51+
key: ${{ runner.os }}-go-${{ hashFiles('go.mod') }}
52+
restore-keys: |
53+
${{ runner.os }}-go-
54+
- name: Install CCM
55+
run: pip install "git+https://github.com/riptano/ccm.git@${CCM_VERSION}"
56+
- name: Start cassandra nodes
57+
run: |
58+
VERSION=${{ matrix.cassandra_version }}
59+
keypath="$(pwd)/testdata/pki"
60+
conf=(
61+
"client_encryption_options.enabled: true"
62+
"client_encryption_options.keystore: $keypath/.keystore"
63+
"client_encryption_options.keystore_password: cassandra"
64+
"client_encryption_options.require_client_auth: true"
65+
"client_encryption_options.truststore: $keypath/.truststore"
66+
"client_encryption_options.truststore_password: cassandra"
67+
"concurrent_reads: 2"
68+
"concurrent_writes: 2"
69+
"write_request_timeout_in_ms: 5000"
70+
"read_request_timeout_in_ms: 5000"
71+
)
72+
73+
if [[ $VERSION == 3.*.* ]]; then
74+
conf+=(
75+
"rpc_server_type: sync"
76+
"rpc_min_threads: 2"
77+
"rpc_max_threads: 2"
78+
"enable_user_defined_functions: true"
79+
"enable_materialized_views: true"
80+
)
81+
elif [[ $VERSION == 4.0.* ]]; then
82+
conf+=(
83+
"enable_user_defined_functions: true"
84+
"enable_materialized_views: true"
85+
)
86+
else
87+
conf+=(
88+
"user_defined_functions_enabled: true"
89+
"materialized_views_enabled: true"
90+
)
91+
fi
92+
93+
ccm remove test || true
94+
95+
ccm create test -v $VERSION -n 3 -d --vnodes --jvm_arg="-Xmx256m -XX:NewSize=100m"
96+
ccm updateconf "${conf[@]}"
97+
98+
export JVM_EXTRA_OPTS=" -Dcassandra.test.fail_writes_ks=test -Dcassandra.custom_query_handler_class=org.apache.cassandra.cql3.CustomPayloadMirroringQueryHandler"
99+
100+
ccm start --wait-for-binary-proto --verbose
101+
ccm status
102+
ccm node1 nodetool status
103+
104+
args="-gocql.timeout=60s -runssl -proto=4 -rf=3 -clusterSize=3 -autowait=2000ms -compressor=${{ matrix.compressor }} -gocql.cversion=$VERSION -cluster=$(ccm liveset) ./..."
105+
106+
echo "args=$args" >> $GITHUB_ENV
107+
echo "JVM_EXTRA_OPTS=$JVM_EXTRA_OPTS" >> $GITHUB_ENV
108+
- name: Run Fuzz tests
109+
run: |
110+
export JVM_EXTRA_OPTS="${{env.JVM_EXTRA_OPTS}}"
111+
go test -v -tags "${{ matrix.tags }} gocql_debug" -fuzz Fuzz -fuzztime 30s -parallel=1 -timeout=5m -race ${{ env.args }}
28112
integration-cassandra:
29113
timeout-minutes: 15
30114
needs:
@@ -198,4 +282,4 @@ jobs:
198282
- name: Integration tests
199283
run: |
200284
export JVM_EXTRA_OPTS="${{env.JVM_EXTRA_OPTS}}"
201-
go test -v -run=TestAuthentication -tags "${{ matrix.tags }} gocql_debug" -timeout=15s -runauth ${{ env.args }}
285+
go test -v -run=TestAuthentication -tags "${{ matrix.tags }} gocql_debug" -timeout=15s -runauth ${{ env.args }}

fuzz.go

Lines changed: 0 additions & 34 deletions
This file was deleted.

fuzz_cassandra_test.go

Lines changed: 118 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,118 @@
1+
//go:build fuzz
2+
// +build fuzz
3+
4+
package gocql
5+
6+
import (
7+
"bytes"
8+
"fmt"
9+
"testing"
10+
)
11+
12+
// FuzzMarshalFloat64Ptr aimed to repeatedly test float64 marshaling with generated inputs based on seed corpus.
13+
func FuzzMarshalFloat64Ptr(f *testing.F) {
14+
f.Add(float64(7500), float64(7500.00))
15+
16+
f.Fuzz(func(t *testing.T, num, numWithPoints float64) {
17+
session := createSession(t)
18+
19+
defer session.Close()
20+
21+
if err := createTable(session, "CREATE TABLE IF NOT EXISTS gocql_test.float_test (id double, test double, primary key (id))"); err != nil {
22+
t.Fatal("create table:", err)
23+
}
24+
25+
if err := session.Query(`TRUNCATE TABLE gocql_test.float_test`).Exec(); err != nil {
26+
t.Fatal("truncate table:", err)
27+
}
28+
29+
if err := session.Query(`INSERT INTO float_test (id,test) VALUES (?,?)`, numWithPoints, &num).Exec(); err != nil {
30+
t.Fatal("insert float64:", err)
31+
}
32+
})
33+
}
34+
35+
func FuzzTracing(f *testing.F) {
36+
f.Add(42)
37+
38+
f.Fuzz(func(t *testing.T, id int) {
39+
session := createSession(t)
40+
defer session.Close()
41+
42+
if err := createTable(session, `CREATE TABLE gocql_test.trace (id int primary key)`); err != nil {
43+
t.Fatal("create:", err)
44+
}
45+
46+
buf := &bytes.Buffer{}
47+
trace := &traceWriter{session: session, w: buf}
48+
if err := session.Query(`INSERT INTO trace (id) VALUES (?)`, id).Trace(trace).Exec(); err != nil {
49+
t.Fatal("insert:", err)
50+
} else if buf.Len() == 0 {
51+
t.Fatal("insert: failed to obtain any tracing")
52+
}
53+
trace.mu.Lock()
54+
buf.Reset()
55+
trace.mu.Unlock()
56+
57+
var value int
58+
if err := session.Query(`SELECT id FROM trace WHERE id = ?`, id).Trace(trace).Scan(&value); err != nil {
59+
t.Fatal("select:", err)
60+
} else if value != id {
61+
t.Fatalf("value: expected %d, got %d", id, value)
62+
} else if buf.Len() == 0 {
63+
t.Fatal("select: failed to obtain any tracing")
64+
}
65+
66+
// also works from session tracer
67+
session.SetTrace(trace)
68+
trace.mu.Lock()
69+
buf.Reset()
70+
trace.mu.Unlock()
71+
if err := session.Query(`SELECT id FROM trace WHERE id = ?`, id).Scan(&value); err != nil {
72+
t.Fatal("select:", err)
73+
}
74+
if buf.Len() == 0 {
75+
t.Fatal("select: failed to obtain any tracing")
76+
}
77+
})
78+
}
79+
func FuzzDurationType(f *testing.F) {
80+
f.Add(int32(1), int32(500), int32(0x7FFFFFFF), int64(0x7FFFFFFFFFFFFFFF))
81+
82+
f.Fuzz(func(t *testing.T, id, month, day int32, nanoseconds int64) {
83+
84+
session := createSession(t)
85+
defer session.Close()
86+
87+
fmt.Println("\nLOL")
88+
fmt.Printf("\nid:%v.\nmonth:%v.\nday:%v.\nnanoseconds:%v\n", id, month, day, nanoseconds)
89+
if session.cfg.ProtoVersion < 4 {
90+
t.Skip("Duration type is not supported. Please use protocol version >= 4 and cassandra version >= 3.11")
91+
}
92+
93+
if err := createTable(session, `CREATE TABLE gocql_test.duration_table (
94+
k int primary key, v duration
95+
)`); err != nil {
96+
t.Fatal("create:", err)
97+
}
98+
99+
duration := Duration{
100+
Months: month,
101+
Days: day,
102+
Nanoseconds: nanoseconds,
103+
}
104+
105+
if err := session.Query(`INSERT INTO gocql_test.duration_table (k, v) VALUES (?, ?)`, id, duration).Exec(); err != nil {
106+
t.Fatal(err)
107+
}
108+
109+
var scanedID int
110+
var selectedDuration Duration
111+
if err := session.Query(`SELECT k, v FROM gocql_test.duration_table`).Scan(&scanedID, &selectedDuration); err != nil {
112+
t.Fatal(err)
113+
}
114+
if selectedDuration.Months != duration.Months || selectedDuration.Days != duration.Days || selectedDuration.Nanoseconds != duration.Nanoseconds {
115+
t.Fatalf("Unexpeted value returned, expected=%v, received=%v", duration, selectedDuration)
116+
}
117+
})
118+
}

0 commit comments

Comments
 (0)