@@ -31,6 +31,7 @@ import (
31
31
"github.com/docker/machine/libmachine/log"
32
32
libvirt "github.com/libvirt/libvirt-go"
33
33
"github.com/pkg/errors"
34
+ "k8s.io/minikube/pkg/util/retry"
34
35
)
35
36
36
37
// Replace with hardcoded range with CIDR
@@ -47,16 +48,14 @@ const networkTmpl = `
47
48
</network>
48
49
`
49
50
50
- // waiting time for libvirt ops to settle
51
- const nap = 100 * time .Microsecond
52
-
53
51
// setupNetwork ensures that the network with `name` is started (active)
54
52
// and has the autostart feature set.
55
53
func setupNetwork (conn * libvirt.Connect , name string ) error {
56
54
n , err := conn .LookupNetworkByName (name )
57
55
if err != nil {
58
56
return errors .Wrapf (err , "checking network %s" , name )
59
57
}
58
+ defer func () { _ = n .Free () }()
60
59
61
60
// always ensure autostart is set on the network
62
61
autostart , err := n .GetAutostart ()
@@ -79,7 +78,6 @@ func setupNetwork(conn *libvirt.Connect, name string) error {
79
78
return errors .Wrapf (err , "starting network %s" , name )
80
79
}
81
80
}
82
-
83
81
return nil
84
82
}
85
83
@@ -110,17 +108,14 @@ func (d *Driver) ensureNetwork() error {
110
108
return errors .Wrapf (err , "deleting inoperable network %s" , d .PrivateNetwork )
111
109
}
112
110
log .Debugf ("Successfully deleted %s network" , d .PrivateNetwork )
113
- time .Sleep (nap )
114
111
if err := d .createNetwork (); err != nil {
115
112
return errors .Wrapf (err , "recreating inoperable network %s" , d .PrivateNetwork )
116
113
}
117
114
log .Debugf ("Successfully recreated %s network" , d .PrivateNetwork )
118
- time .Sleep (nap )
119
115
if err := setupNetwork (conn , d .PrivateNetwork ); err != nil {
120
116
return err
121
117
}
122
118
log .Debugf ("Successfully activated %s network" , d .PrivateNetwork )
123
- time .Sleep (nap )
124
119
}
125
120
126
121
return nil
@@ -140,13 +135,16 @@ func (d *Driver) createNetwork() error {
140
135
141
136
// network: default
142
137
// It is assumed that the libvirt/kvm installation has already created this network
143
- if _ , err := conn .LookupNetworkByName (d .Network ); err != nil {
138
+ netd , err := conn .LookupNetworkByName (d .Network )
139
+ if err != nil {
144
140
return errors .Wrapf (err , "network %s doesn't exist" , d .Network )
145
141
}
142
+ defer func () { _ = netd .Free () }()
146
143
147
144
// network: private
148
145
// Only create the private network if it does not already exist
149
- if _ , err := conn .LookupNetworkByName (d .PrivateNetwork ); err != nil {
146
+ netp , err := conn .LookupNetworkByName (d .PrivateNetwork )
147
+ if err != nil {
150
148
// create the XML for the private network from our networkTmpl
151
149
tmpl := template .Must (template .New ("network" ).Parse (networkTmpl ))
152
150
var networkXML bytes.Buffer
@@ -161,10 +159,26 @@ func (d *Driver) createNetwork() error {
161
159
}
162
160
163
161
// and finally create it
164
- if err := network .Create (); err != nil {
162
+ log .Debugf ("Trying to create network %s..." , d .PrivateNetwork )
163
+ create := func () error {
164
+ if err := network .Create (); err != nil {
165
+ return err
166
+ }
167
+ active , err := network .IsActive ()
168
+ if err == nil && active {
169
+ return nil
170
+ }
171
+ return errors .Errorf ("retrying %v" , err )
172
+ }
173
+ if err := retry .Local (create , 10 * time .Second ); err != nil {
165
174
return errors .Wrapf (err , "creating network %s" , d .PrivateNetwork )
166
175
}
167
176
}
177
+ defer func () {
178
+ if netp != nil {
179
+ _ = netp .Free ()
180
+ }
181
+ }()
168
182
169
183
return nil
170
184
}
@@ -183,13 +197,13 @@ func (d *Driver) deleteNetwork() error {
183
197
log .Debugf ("Checking if network %s exists..." , d .PrivateNetwork )
184
198
network , err := conn .LookupNetworkByName (d .PrivateNetwork )
185
199
if err != nil {
186
- if libvirtErr , ok := err .(libvirt. Error ); ok && libvirtErr .Code == libvirt .ERR_NO_NETWORK {
200
+ if lvErr ( err ) .Code == libvirt .ERR_NO_NETWORK {
187
201
log .Warnf ("Network %s does not exist. Skipping deletion" , d .PrivateNetwork )
188
202
return nil
189
203
}
190
-
191
204
return errors .Wrapf (err , "failed looking for network %s" , d .PrivateNetwork )
192
205
}
206
+ defer func () { _ = network .Free () }()
193
207
log .Debugf ("Network %s exists" , d .PrivateNetwork )
194
208
195
209
err = d .checkDomains (conn )
@@ -198,25 +212,59 @@ func (d *Driver) deleteNetwork() error {
198
212
}
199
213
200
214
// when we reach this point, it means it is safe to delete the network
201
- log . Debugf ( "Trying to destroy network %s..." , d . PrivateNetwork )
215
+
202
216
// cannot destroy an inactive network - try to activate it first
203
- active , err := network .IsActive ()
204
- if err == nil && ! active {
205
- log .Debugf ("Trying to reactivate network %s first..." , d .PrivateNetwork )
206
- _ = network .Create ()
207
- time .Sleep (nap )
217
+ log .Debugf ("Trying to reactivate network %s first (if needed)..." , d .PrivateNetwork )
218
+ activate := func () error {
219
+ active , err := network .IsActive ()
220
+ if err == nil && active {
221
+ return nil
222
+ }
223
+ if err != nil {
224
+ return err
225
+ }
226
+ // inactive, try to activate
227
+ if err := network .Create (); err != nil {
228
+ return err
229
+ }
230
+ return errors .Errorf ("needs confirmation" ) // confirm in the next cycle
208
231
}
209
- err = network .Destroy ()
210
- if err != nil {
211
- return errors .Wrap (err , "network destroy" )
232
+ if err := retry .Local (activate , 10 * time .Second ); err != nil {
233
+ log .Debugf ("Reactivating network %s failed, will continue anyway..." , d .PrivateNetwork )
234
+ }
235
+
236
+ log .Debugf ("Trying to destroy network %s..." , d .PrivateNetwork )
237
+ destroy := func () error {
238
+ if err := network .Destroy (); err != nil {
239
+ return err
240
+ }
241
+ active , err := network .IsActive ()
242
+ if err == nil && ! active {
243
+ return nil
244
+ }
245
+ return errors .Errorf ("retrying %v" , err )
246
+ }
247
+ if err := retry .Local (destroy , 10 * time .Second ); err != nil {
248
+ return errors .Wrap (err , "destroying network" )
212
249
}
213
- time . Sleep ( nap )
250
+
214
251
log .Debugf ("Trying to undefine network %s..." , d .PrivateNetwork )
215
- err = network .Undefine ()
216
- if err != nil {
217
- return errors .Wrap (err , "network undefine" )
252
+ undefine := func () error {
253
+ if err := network .Undefine (); err != nil {
254
+ return err
255
+ }
256
+ netp , err := conn .LookupNetworkByName (d .PrivateNetwork )
257
+ if netp != nil {
258
+ _ = netp .Free ()
259
+ }
260
+ if lvErr (err ).Code == libvirt .ERR_NO_NETWORK {
261
+ return nil
262
+ }
263
+ return errors .Errorf ("retrying %v" , err )
264
+ }
265
+ if err := retry .Local (undefine , 10 * time .Second ); err != nil {
266
+ return errors .Wrap (err , "undefining network" )
218
267
}
219
- time .Sleep (nap )
220
268
221
269
return nil
222
270
}
@@ -301,7 +349,6 @@ func (d *Driver) lookupIP() (string, error) {
301
349
if err != nil {
302
350
return "" , errors .Wrap (err , "getting connection and domain" )
303
351
}
304
-
305
352
defer conn .Close ()
306
353
307
354
libVersion , err := conn .GetLibVersion ()
@@ -323,6 +370,7 @@ func (d *Driver) lookupIPFromStatusFile(conn *libvirt.Connect) (string, error) {
323
370
if err != nil {
324
371
return "" , errors .Wrap (err , "looking up network by name" )
325
372
}
373
+ defer func () { _ = network .Free () }()
326
374
327
375
bridge , err := network .GetBridgeName ()
328
376
if err != nil {
0 commit comments