This moves the EBUSY detection to devmapper.go, and then returns
a real ErrBusy that deviceset uses.
Docker-DCO-1.1-Signed-off-by: Alexander Larsson <alexl@redhat.com> (github: alexlarsson)
... | ... |
@@ -13,7 +13,6 @@ import ( |
13 | 13 |
"path" |
14 | 14 |
"path/filepath" |
15 | 15 |
"strconv" |
16 |
- "strings" |
|
17 | 16 |
"sync" |
18 | 17 |
"syscall" |
19 | 18 |
"time" |
... | ... |
@@ -62,7 +61,6 @@ type DeviceSet struct { |
62 | 62 |
TransactionId uint64 |
63 | 63 |
NewTransactionId uint64 |
64 | 64 |
nextFreeDevice int |
65 |
- sawBusy bool |
|
66 | 65 |
} |
67 | 66 |
|
68 | 67 |
type DiskUsage struct { |
... | ... |
@@ -387,10 +385,6 @@ func (devices *DeviceSet) log(level int, file string, line int, dmError int, mes |
387 | 387 |
return // Ignore _LOG_DEBUG |
388 | 388 |
} |
389 | 389 |
|
390 |
- if strings.Contains(message, "busy") { |
|
391 |
- devices.sawBusy = true |
|
392 |
- } |
|
393 |
- |
|
394 | 390 |
utils.Debugf("libdevmapper(%d): %s:%d (%d) %s", level, file, line, dmError, message) |
395 | 391 |
} |
396 | 392 |
|
... | ... |
@@ -710,12 +704,11 @@ func (devices *DeviceSet) removeDeviceAndWait(devname string) error { |
710 | 710 |
var err error |
711 | 711 |
|
712 | 712 |
for i := 0; i < 1000; i++ { |
713 |
- devices.sawBusy = false |
|
714 | 713 |
err = removeDevice(devname) |
715 | 714 |
if err == nil { |
716 | 715 |
break |
717 | 716 |
} |
718 |
- if !devices.sawBusy { |
|
717 |
+ if err != ErrBusy { |
|
719 | 718 |
return err |
720 | 719 |
} |
721 | 720 |
|
... | ... |
@@ -62,6 +62,9 @@ var ( |
62 | 62 |
ErrInvalidAddNode = errors.New("Invalide AddNoce type") |
63 | 63 |
ErrGetLoopbackBackingFile = errors.New("Unable to get loopback backing file") |
64 | 64 |
ErrLoopbackSetCapacity = errors.New("Unable set loopback capacity") |
65 |
+ ErrBusy = errors.New("Device is Busy") |
|
66 |
+ |
|
67 |
+ dmSawBusy bool |
|
65 | 68 |
) |
66 | 69 |
|
67 | 70 |
type ( |
... | ... |
@@ -512,7 +515,11 @@ func removeDevice(name string) error { |
512 | 512 |
if task == nil { |
513 | 513 |
return err |
514 | 514 |
} |
515 |
+ dmSawBusy = false |
|
515 | 516 |
if err = task.Run(); err != nil { |
517 |
+ if dmSawBusy { |
|
518 |
+ return ErrBusy |
|
519 |
+ } |
|
516 | 520 |
return fmt.Errorf("Error running removeDevice") |
517 | 521 |
} |
518 | 522 |
return nil |
... | ... |
@@ -4,12 +4,23 @@ package devmapper |
4 | 4 |
|
5 | 5 |
import "C" |
6 | 6 |
|
7 |
+import ( |
|
8 |
+ "strings" |
|
9 |
+) |
|
10 |
+ |
|
7 | 11 |
// Due to the way cgo works this has to be in a separate file, as devmapper.go has |
8 | 12 |
// definitions in the cgo block, which is incompatible with using "//export" |
9 | 13 |
|
10 | 14 |
//export DevmapperLogCallback |
11 | 15 |
func DevmapperLogCallback(level C.int, file *C.char, line C.int, dm_errno_or_class C.int, message *C.char) { |
16 |
+ msg := C.GoString(message) |
|
17 |
+ if level < 7 { |
|
18 |
+ if strings.Contains(msg, "busy") { |
|
19 |
+ dmSawBusy = true |
|
20 |
+ } |
|
21 |
+ } |
|
22 |
+ |
|
12 | 23 |
if dmLogger != nil { |
13 |
- dmLogger.log(int(level), C.GoString(file), int(line), int(dm_errno_or_class), C.GoString(message)) |
|
24 |
+ dmLogger.log(int(level), C.GoString(file), int(line), int(dm_errno_or_class), msg) |
|
14 | 25 |
} |
15 | 26 |
} |