@@ -243,10 +243,6 @@ func getAllMountpoints() ([]string, error) {
243
243
func getMountpoint (path string ) (string , error ) {
244
244
// get mountpoints from /proc/self/mountinfo on Linux
245
245
// getfsstat(2) used on Mac (BSD)
246
- mountpoints , err := mountinfo .GetMounts (nil )
247
- if err != nil {
248
- return "" , err
249
- }
250
246
251
247
fi , err := os .Lstat (path )
252
248
if err != nil {
@@ -255,26 +251,42 @@ func getMountpoint(path string) (string, error) {
255
251
256
252
fromInfo , ok := fi .Sys ().(* syscall.Stat_t )
257
253
if ! ok {
258
- return "" , fmt .Errorf ("get stat(2) dev_ino " )
254
+ return "" , fmt .Errorf ("get stat(2) st_dev " )
259
255
}
260
256
261
- for _ , m := range mountpoints {
262
- mi , err := os .Stat (m .Mountpoint )
257
+ // this list could contain duplicate (bind) mount paths for the filesystem we are looking for,
258
+ // any one of them qualifies as $topdir
259
+ mountpoints , err := mountinfo .GetMounts (func (i * mountinfo.Info ) (skip bool , stop bool ) {
260
+ // skip bind mounts into subdirectories
261
+ if i .Root != "/" {
262
+ return true , false
263
+ }
264
+
265
+ mi , err := os .Stat (i .Mountpoint )
263
266
if err != nil {
264
- continue
267
+ return true , false
265
268
}
266
269
267
270
mountInfo , ok := mi .Sys ().(* syscall.Stat_t )
268
271
if ! ok {
269
- continue
272
+ return true , false
270
273
}
271
274
272
- if fromInfo .Dev == mountInfo .Dev {
273
- return m . Mountpoint , nil
275
+ if mountInfo .Dev != fromInfo .Dev {
276
+ return true , false
274
277
}
278
+
279
+ return false , false
280
+ })
281
+ if err != nil {
282
+ return "" , err
283
+ }
284
+
285
+ if len (mountpoints ) == 0 {
286
+ return "" , fmt .Errorf ("no mount for device %d" , fromInfo .Dev )
275
287
}
276
288
277
- return "" , fmt . Errorf ( "no mount for device %d" , fromInfo . Dev )
289
+ return mountpoints [ 0 ]. Mountpoint , nil
278
290
}
279
291
280
292
func useHomeTrash (path string ) (sameFS bool , err error ) {
0 commit comments