Skip to content

Commit f711f7d

Browse files
committed
solverrpc: Detect exited csppsolver process
If the csppsolver process was successfully started, but has since exited (due to crash, or killed by a signal), a new error is returned. This error condition will need to be checked by mixclient so it can disable root solving attempts for future mix runs.
1 parent 3c81672 commit f711f7d

File tree

1 file changed

+33
-0
lines changed

1 file changed

+33
-0
lines changed

solverrpc/rpc.go

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package solverrpc
22

33
import (
4+
"errors"
45
"io"
56
"math/big"
67
"net/rpc"
@@ -13,6 +14,10 @@ import (
1314
// Roots if the process is named differently or if an absolute path is needed.
1415
var SolverProcess = "csppsolver"
1516

17+
// ErrSolverProcessExited indicates that the solver process was started, but
18+
// has since exited (possibly due to a crash, or a signal which killed it).
19+
var ErrSolverProcessExited = errors.New("solver process exited")
20+
1621
type solverProcess struct {
1722
cmd *exec.Cmd
1823
stdin io.WriteCloser
@@ -44,6 +49,7 @@ var (
4449
once sync.Once
4550
onceErr error
4651
client *rpc.Client
52+
cmdDone = make(chan struct{})
4753
)
4854

4955
func startSolver() {
@@ -68,6 +74,19 @@ func startSolver() {
6874
stdin: stdin,
6975
stdout: stdout,
7076
})
77+
go func() {
78+
cmd.Wait()
79+
close(cmdDone)
80+
}()
81+
}
82+
83+
func checkExit() error {
84+
select {
85+
case <-cmdDone:
86+
return ErrSolverProcessExited
87+
default:
88+
return nil
89+
}
7190
}
7291

7392
// StartSolver starts the solver's background process. This can be used to
@@ -85,6 +104,10 @@ func RootFactors(a []*big.Int, F *big.Int) ([]*big.Int, []int, error) {
85104
return nil, nil, err
86105
}
87106

107+
if err := checkExit(); err != nil {
108+
return nil, nil, err
109+
}
110+
88111
var args struct {
89112
A []*big.Int
90113
F *big.Int
@@ -97,6 +120,9 @@ func RootFactors(a []*big.Int, F *big.Int) ([]*big.Int, []int, error) {
97120
}
98121
err := client.Call("Solver.RootFactors", args, &result)
99122
if err != nil {
123+
if exitErr := checkExit(); exitErr != nil {
124+
err = exitErr
125+
}
100126
return nil, nil, err
101127
}
102128
return result.Roots, result.Exponents, nil
@@ -114,6 +140,10 @@ func Roots(a []*big.Int, F *big.Int) ([]*big.Int, error) {
114140
return nil, err
115141
}
116142

143+
if err := checkExit(); err != nil {
144+
return nil, err
145+
}
146+
117147
var args struct {
118148
A []*big.Int
119149
F *big.Int
@@ -126,6 +156,9 @@ func Roots(a []*big.Int, F *big.Int) ([]*big.Int, error) {
126156
}
127157
err := client.Call("Solver.Roots", args, &result)
128158
if err != nil {
159+
if exitErr := checkExit(); exitErr != nil {
160+
err = exitErr
161+
}
129162
return nil, err
130163
}
131164
if result.RepeatedRoot != nil {

0 commit comments

Comments
 (0)