Getting back into it...

This commit is contained in:
Caleb Gardner
2021-02-23 22:26:15 -06:00
parent 3691e1f486
commit 8a91e1a1c1
3 changed files with 63 additions and 16 deletions
+18 -12
View File
@@ -35,30 +35,36 @@ type superblock struct {
//SuperblockFlags is the series of flags describing how a squashfs archive is packed.
type SuperblockFlags struct {
//If true, inodes are stored uncompressed
//If true, inodes are stored uncompressed.
UncompressedInodes bool
//If true, data is stored uncompressed
//If true, data is stored uncompressed.
UncompressedData bool
check bool
//If true, fragments are stored uncompressed
//If true, fragments are stored uncompressed.
UncompressedFragments bool
//If true, ALL data is stored in sequential data blocks instead of utilizing fragments
//If true, ALL data is stored in sequential data blocks instead of utilizing fragments.
NoFragments bool
//If true, the last block of data will always be stored as a fragment if it's less then the block size.
AlwaysFragments bool
//If true, duplicate files are only stored once.
Duplicates bool
//If true, the export table is populated
//If true, duplicate files are only stored once. (Currently unsupported)
RemoveDuplicates bool
//If true, the export table is populated. (Currently unsupported)
Exportable bool
//If true, the xattr table is uncompressed
//If true, the xattr table is uncompressed. (Currently unsupported)
UncompressedXattr bool
//If true, the xattr table is not populated
//If true, the xattr table is not populated. (Currently unsupported)
NoXattr bool
compressorOptions bool
//If true, the UID/GID table is stored uncompressed
//If true, the UID/GID table is stored uncompressed.
UncompressedIDs bool
}
//DefaultFlags are the default SuperblockFlags that are used.
var DefaultFlags = SuperblockFlags{
RemoveDuplicates: true,
Exportable: true,
}
//GetFlags returns a SuperblockFlags for a given superblock.
func (s *superblock) GetFlags() SuperblockFlags {
return SuperblockFlags{
@@ -68,7 +74,7 @@ func (s *superblock) GetFlags() SuperblockFlags {
UncompressedFragments: s.Flags&0x8 == 0x8,
NoFragments: s.Flags&0x10 == 0x10,
AlwaysFragments: s.Flags&0x20 == 0x20,
Duplicates: s.Flags&0x40 == 0x40,
RemoveDuplicates: s.Flags&0x40 == 0x40,
Exportable: s.Flags&0x80 == 0x80,
UncompressedXattr: s.Flags&0x100 == 0x100,
NoXattr: s.Flags&0x200 == 0x200,
@@ -98,7 +104,7 @@ func (s *SuperblockFlags) ToUint() uint16 {
if s.AlwaysFragments {
out = out | 0x20
}
if s.Duplicates {
if s.RemoveDuplicates {
out = out | 0x40
}
if s.Exportable {
+31 -2
View File
@@ -3,6 +3,7 @@ package squashfs
import (
"errors"
"io"
"io/fs"
"log"
"os"
"path"
@@ -29,6 +30,9 @@ type Writer struct {
//Currently Duplicates, Exportable, UncompressedXattr, NoXattr values are ignored
Flags SuperblockFlags
allowErrors bool
//variables used when actually writing.
superblock superblock
}
//NewWriter creates a new with the default options (Gzip compression and allow errors)
@@ -54,6 +58,7 @@ func NewWriterWithOptions(compressionType int, allowErrors bool) (*Writer, error
compressionType: compressionType,
allowErrors: allowErrors,
BlockSize: uint32(1048576),
Flags: DefaultFlags,
}, nil
}
@@ -95,7 +100,8 @@ func (w *Writer) AddFileTo(filepath string, file *os.File) error {
return errors.New("File already exists at " + filepath)
}
var holder fileHolder
holder.path, holder.name = path.Split(filepath)
holder.path = path.Dir(filepath)
holder.name = path.Base(filepath)
holder.reader = file
stat, err := file.Stat()
if err != nil {
@@ -167,12 +173,35 @@ func (w *Writer) AddReaderTo(filepath string, reader io.Reader) error {
return errors.New("File already exists at " + filepath)
}
var holder fileHolder
holder.path, holder.name = path.Split(filepath)
holder.path = path.Dir(filepath)
holder.name = path.Base(filepath)
holder.reader = reader
w.structure[holder.path] = append(w.structure[holder.path], &holder)
return nil
}
//AddFolderTo adds a folder at the given path. IF the folder is already present, it sets the folder's permissions.
//If the path points to a non-folder (such as a file or symlink), an error is returned
func (w *Writer) AddFolderTo(folderpath string, permission fs.FileMode) error {
folderpath = path.Clean(folderpath)
tmp := w.holderAt(folderpath)
if tmp != nil {
if !tmp.folder {
return errors.New("Path is not a folder: " + folderpath)
}
tmp.perm = int(permission.Perm())
return nil
}
file := fileHolder{
path: path.Dir(folderpath),
name: path.Base(folderpath),
perm: int(permission | fs.ModePerm),
folder: true,
}
w.structure[file.path] = append(w.structure[file.path], &file)
return nil
}
//Remove tries to remove the file(s) at the given filepath. If wildcards are used, it will remove all files that match.
//Returns true if one or more files are removed.
func (w *Writer) Remove(filepath string) bool {
+14 -2
View File
@@ -4,8 +4,18 @@ import (
"errors"
"io"
"math"
"path"
)
func (w *Writer) fixFolders() error {
for folder := range w.structure {
if folder == "/" {
continue
}
dir, name := path.Dir(folder), path.Base(folder)
}
}
//WriteTo attempts to write the archive to the given io.Writer.
func (w *Writer) WriteTo(write io.Writer) (int64, error) {
if w.BlockSize > 1048576 {
@@ -13,8 +23,10 @@ func (w *Writer) WriteTo(write io.Writer) (int64, error) {
} else if w.BlockSize < 4096 {
w.BlockSize = 4096
}
//TODO: set forced Flag values
_ = superblock{
w.Flags.RemoveDuplicates = false
w.Flags.Exportable = false
w.Flags.NoXattr = true
w.superblock = superblock{
Magic: magic,
BlockSize: w.BlockSize,
BlockLog: uint16(math.Log2(float64(w.BlockSize))),