-
Notifications
You must be signed in to change notification settings - Fork 13
/
mode.go
157 lines (126 loc) · 2.87 KB
/
mode.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
// SPDX-License-Identifier: ISC
// Copyright (c) 2014-2020 Bitmark Inc.
// Use of this source code is governed by an ISC
// license that can be found in the LICENSE file.
package mode
import (
"sync"
"github.com/bitmark-inc/bitmarkd/chain"
"github.com/bitmark-inc/bitmarkd/fault"
"github.com/bitmark-inc/logger"
)
// Mode - type to hold the mode
type Mode int
// all possible modes
const (
Stopped Mode = iota
Resynchronise
Normal
maximum
)
var globalData struct {
sync.RWMutex
log *logger.L
mode Mode
testing bool
chain string
// set once during initialise
initialised bool
}
// Initialise - set up the mode system
func Initialise(chainName string) error {
// ensure start up in resynchronise mode
globalData.Lock()
defer globalData.Unlock()
// no need to start if already started
if globalData.initialised {
return fault.AlreadyInitialised
}
globalData.log = logger.New("mode")
globalData.log.Info("starting…")
// default settings
globalData.chain = chainName
globalData.testing = false
globalData.mode = Resynchronise
// override for specific chain
switch chainName {
case chain.Bitmark:
// no change
case chain.Testing, chain.Local:
globalData.testing = true
default:
globalData.log.Criticalf("mode cannot handle chain: '%s'", chainName)
return fault.InvalidChain
}
// all data initialised
globalData.initialised = true
return nil
}
// Finalise - shutdown mode handling
func Finalise() error {
if !globalData.initialised {
return fault.NotInitialised
}
globalData.log.Info("shutting down…")
globalData.log.Flush()
Set(Stopped)
// finally...
globalData.initialised = false
globalData.log.Info("finished")
globalData.log.Flush()
return nil
}
// Set - change mode
func Set(mode Mode) {
if mode >= Stopped && mode < maximum {
globalData.Lock()
globalData.mode = mode
globalData.Unlock()
globalData.log.Infof("set: %s", mode)
} else {
globalData.log.Errorf("ignore invalid set: %d", mode)
}
}
// Is - detect mode
func Is(mode Mode) bool {
globalData.RLock()
defer globalData.RUnlock()
return mode == globalData.mode
}
// IsNot - detect mode
func IsNot(mode Mode) bool {
globalData.RLock()
defer globalData.RUnlock()
return mode != globalData.mode
}
// IsTesting - special for testing
func IsTesting() bool {
globalData.RLock()
defer globalData.RUnlock()
return globalData.testing
}
// ChainName - name of the current chain
func ChainName() string {
globalData.RLock()
defer globalData.RUnlock()
return globalData.chain
}
// String - current mode represented as a string
func String() string {
globalData.RLock()
defer globalData.RUnlock()
return globalData.mode.String()
}
// String - current mode represented as a string
func (m Mode) String() string {
switch m {
case Stopped:
return "Stopped"
case Resynchronise:
return "Resynchronise"
case Normal:
return "Normal"
default:
return "*Unknown*"
}
}