Add code for partition mounting
This commit is contained in:
parent
3483a665c4
commit
4c1e7a4310
166
main.go
166
main.go
@ -1,57 +1,137 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"flag"
|
||||
"fmt"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"strings"
|
||||
"syscall"
|
||||
)
|
||||
|
||||
var (
|
||||
perm = flag.String("perm", "/perm", "new val for perm")
|
||||
perm = flag.String("perm", "/perm", "new val for perm")
|
||||
gloaderHome = "/perm/gloader"
|
||||
)
|
||||
|
||||
func main() {
|
||||
os.MkdirAll("/home/timmy/dltest", 0777)
|
||||
flag.Parse()
|
||||
gloaderHome = filepath.Join(*perm, "gloader")
|
||||
os.MkdirAll(gloaderHome, 0777)
|
||||
err := mount()
|
||||
if err != nil {
|
||||
log.Println(err)
|
||||
os.Exit(1)
|
||||
}
|
||||
d := newDownloader()
|
||||
d.DataDir = "/home/timmy/dltest"
|
||||
d.Start("tcp", ":8080")
|
||||
d.DataDir = filepath.Join(gloaderHome, "data")
|
||||
d.Start("tcp", ":8844")
|
||||
}
|
||||
|
||||
// func mount() error {
|
||||
// var (
|
||||
// partUUID string
|
||||
// partUUIDb []byte
|
||||
// err error
|
||||
// dataStat os.FileInfo
|
||||
// dataDir = filepath.Join(*perm, "downloader/data")
|
||||
// )
|
||||
// partUUIDb, err = ioutil.ReadFile(filepath.Join(*perm, "downloader/partition"))
|
||||
// if err != nil || string(partUUIDb) == "" {
|
||||
// return nil
|
||||
// }
|
||||
// partUUID = string(partUUIDb)
|
||||
// dataStat, err = os.Stat(dataDir)
|
||||
// if err != nil {
|
||||
// if errors.Is(err, os.ErrNotExist) {
|
||||
// err = os.MkdirAll(dataDir, 0o755)
|
||||
// if err != nil {
|
||||
// return fmt.Errorf("error creating datadir: %w", err)
|
||||
// }
|
||||
// } else {
|
||||
// return fmt.Errorf("error mounting datadir: %w", err)
|
||||
// }
|
||||
// }
|
||||
// if dataStat.IsDir() {
|
||||
// var folder *os.File
|
||||
// folder, err = os.Open(dataDir)
|
||||
// if err != nil {
|
||||
// return fmt.Errorf("error mounting datadir: %w", err)
|
||||
// }
|
||||
// _, err = folder.Readdir(1)
|
||||
// if errors.Is(err, io.EOF) {
|
||||
// fmt.Printf("mount %s %s", partUUID, dataDir)
|
||||
// return nil
|
||||
// }
|
||||
// return fmt.Errorf("error mounting datadir: %w", err)
|
||||
// }
|
||||
// return fmt.Errorf("error mounting datadir: data dir %s is not a directory", dataDir)
|
||||
// }
|
||||
func mount() error {
|
||||
var (
|
||||
partUUIDb []byte
|
||||
partUUID string
|
||||
dev string
|
||||
err error
|
||||
dataStat os.FileInfo
|
||||
dataDir = filepath.Join(gloaderHome, "data")
|
||||
)
|
||||
partUUIDb, err = ioutil.ReadFile(filepath.Join(gloaderHome, "partition"))
|
||||
partUUID = strings.TrimSpace(string(partUUIDb))
|
||||
if err != nil || partUUID == "" {
|
||||
return nil
|
||||
}
|
||||
dataStat, err = os.Stat(dataDir)
|
||||
if err != nil {
|
||||
if errors.Is(err, os.ErrNotExist) {
|
||||
err = os.MkdirAll(dataDir, 0o755)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error creating datadir: %w", err)
|
||||
}
|
||||
dataStat, err = os.Stat(dataDir)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error mounting datadir: %w", err)
|
||||
}
|
||||
} else {
|
||||
return fmt.Errorf("error mounting datadir: %w", err)
|
||||
}
|
||||
}
|
||||
if dataStat.IsDir() {
|
||||
var folder *os.File
|
||||
folder, err = os.Open(dataDir)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error mounting datadir: %w", err)
|
||||
}
|
||||
_, err = folder.Readdir(1)
|
||||
if errors.Is(err, io.EOF) {
|
||||
fmt.Printf("mount %s %s", partUUID, dataDir)
|
||||
dev, err = findPartUUID(partUUID)
|
||||
if err != nil {
|
||||
return fmt.Errorf("error mounting datadir: %w", err)
|
||||
}
|
||||
err = syscall.Mount(dev, dataDir, "ext4", 0, "")
|
||||
if err != nil {
|
||||
return fmt.Errorf("error mounting datadir: %w", err)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
return fmt.Errorf("error mounting datadir: %w", err)
|
||||
}
|
||||
return fmt.Errorf("error mounting datadir: data dir %s is not a directory", dataDir)
|
||||
}
|
||||
|
||||
func findPartUUID(uuid string) (string, error) {
|
||||
var dev string
|
||||
err := filepath.Walk("/sys/block", func(path string, info os.FileInfo, err error) error {
|
||||
if err != nil {
|
||||
log.Printf("findPartUUID: %v", err)
|
||||
return nil
|
||||
}
|
||||
if info.Mode()&os.ModeSymlink == 0 {
|
||||
return nil
|
||||
}
|
||||
devname := "/dev/" + filepath.Base(path)
|
||||
f, err := os.Open(devname)
|
||||
if err != nil {
|
||||
log.Printf("findPartUUID: %v", err)
|
||||
return nil
|
||||
}
|
||||
defer f.Close()
|
||||
if _, err := f.Seek(440, io.SeekStart); err != nil {
|
||||
var se syscall.Errno
|
||||
if errors.As(err, &se) && se == syscall.EINVAL {
|
||||
// Seek()ing empty loop devices results in EINVAL.
|
||||
return nil
|
||||
}
|
||||
log.Printf("findPartUUID: %v(%T)", err, err.(*os.PathError).Err)
|
||||
return nil
|
||||
}
|
||||
var diskSig struct {
|
||||
ID uint32
|
||||
Trailer uint16
|
||||
}
|
||||
if err := binary.Read(f, binary.LittleEndian, &diskSig); err != nil {
|
||||
log.Printf("findPartUUID: %v", err)
|
||||
return nil
|
||||
}
|
||||
if fmt.Sprintf("%08x", diskSig.ID) == uuid && diskSig.Trailer == 0 {
|
||||
dev = devname
|
||||
// TODO: abort early with sentinel error code
|
||||
return nil
|
||||
}
|
||||
return nil
|
||||
})
|
||||
if err != nil {
|
||||
return "", err
|
||||
}
|
||||
if dev == "" {
|
||||
return "", fmt.Errorf("PARTUUID=%s not found", uuid)
|
||||
}
|
||||
return dev, nil
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user