add mft read method
This commit is contained in:
@@ -0,0 +1,141 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"b612.me/starlog"
|
||||
"b612.me/wincmd"
|
||||
"b612.me/wincmd/ntfs/mft"
|
||||
"b612.me/wincmd/ntfs/utf16"
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"io"
|
||||
"log"
|
||||
_ "net/http/pprof"
|
||||
"regexp"
|
||||
"runtime"
|
||||
"time"
|
||||
)
|
||||
|
||||
func main() {
|
||||
f, size, err := mft.GetMFTFile(`C:\`)
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
recordSize := int64(1024)
|
||||
i := int64(0)
|
||||
starlog.Infoln("start size is", size)
|
||||
alreadyGot := int64(0)
|
||||
maxRecordSize := size / recordSize
|
||||
if maxRecordSize > 1024 {
|
||||
maxRecordSize = 1024
|
||||
}
|
||||
for {
|
||||
for {
|
||||
if (size - alreadyGot) < maxRecordSize*recordSize {
|
||||
maxRecordSize--
|
||||
} else {
|
||||
break
|
||||
}
|
||||
}
|
||||
if maxRecordSize < 10 {
|
||||
maxRecordSize = 1
|
||||
}
|
||||
buf := make([]byte, maxRecordSize*recordSize)
|
||||
got, err := io.ReadFull(f, buf)
|
||||
if err != nil {
|
||||
if errors.Is(err, io.EOF) {
|
||||
break
|
||||
}
|
||||
log.Fatalln("Unable to read record data", err)
|
||||
}
|
||||
alreadyGot += int64(got)
|
||||
for j := int64(0); j < 1024*maxRecordSize; j += 1024 {
|
||||
record, err := mft.ParseRecord(buf[j : j+1024])
|
||||
if err != nil {
|
||||
// fmt.Println("Unable to parse MFT record", err)
|
||||
continue
|
||||
}
|
||||
|
||||
fname := record.FindAttributes(mft.AttributeTypeFileName)
|
||||
|
||||
for _, v := range fname {
|
||||
if (record.Flags&mft.RecordFlagIsIndex)>>3 == 0 && record.Flags&mft.RecordFlagInUse == 1 {
|
||||
filename := utf16.DecodeString(v.Data[66:], binary.LittleEndian)
|
||||
//data:=utf16.DecodeString(v.Data, binary.LittleEndian)
|
||||
if filename != "" {
|
||||
attbr := record.FindAttributes(mft.AttributeTypeStandardInformation)
|
||||
if len(attbr) == 0 {
|
||||
break
|
||||
}
|
||||
stand, _ := mft.ParseStandardInformation(attbr[0].Data)
|
||||
if stand.FileAttributes&mft.FileAttributeNormal == 1 {
|
||||
i++
|
||||
}
|
||||
//oo:=record.FindAttributes(mft.AttributeTypeData)
|
||||
//if len(oo)!=0 {
|
||||
// fmt.Println(oo[0].ActualSize)
|
||||
//}
|
||||
//r := binutil.NewLittleEndianReader(v.Data[:8])
|
||||
//fmt.Println(record.FileReference.ToUint64(), r.Uint64(0))
|
||||
//fmt.Println(filename)
|
||||
//log.Println("Read MFT record")
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
starlog.Infoln(i)
|
||||
|
||||
//go http.ListenAndServe("0.0.0.0:8888", nil)
|
||||
starlog.Debugln("开始获取Windows磁盘列表")
|
||||
lists, err := wincmd.ListDrivers()
|
||||
if err != nil {
|
||||
panic(err)
|
||||
}
|
||||
info := []wincmd.DiskInfo{}
|
||||
for _, v := range lists {
|
||||
data, err := wincmd.GetDiskInfo(v)
|
||||
if err != nil {
|
||||
continue
|
||||
}
|
||||
fmt.Println("获取到磁盘信息:", data)
|
||||
info = append(info, data)
|
||||
}
|
||||
starlog.Warningln("忽略非NTFS磁盘")
|
||||
var m runtime.MemStats
|
||||
for _, v := range info {
|
||||
if v.Format == "NTFS" && v.Driver == `C:\` {
|
||||
|
||||
starlog.Infoln("开始获取NTFS USN日志,磁盘:", v.Driver)
|
||||
fileLists, err := wincmd.ListUsnFileFn(v.Driver, func(name string, typed uint8) bool {
|
||||
return true
|
||||
if ok, _ := regexp.MatchString(`\.exe$`, name); ok {
|
||||
return true
|
||||
}
|
||||
return false
|
||||
})
|
||||
if err != nil {
|
||||
starlog.Panicln("获取失败", err)
|
||||
}
|
||||
fmt.Println(len(fileLists))
|
||||
return
|
||||
for k, _ := range fileLists {
|
||||
fmt.Println(k)
|
||||
}
|
||||
runtime.ReadMemStats(&m)
|
||||
log.Printf("Alloc = %v TotalAlloc = %v Sys = %v NumGC = %v\n", m.Alloc/1024, m.TotalAlloc/1024, m.Sys/1024, m.NumGC)
|
||||
runtime.GC()
|
||||
p := time.After(time.Second * 86400)
|
||||
for {
|
||||
select {
|
||||
case <-p:
|
||||
return
|
||||
case <-time.After(time.Second * 10):
|
||||
runtime.ReadMemStats(&m)
|
||||
log.Printf("Alloc = %v TotalAlloc = %v Sys = %v NumGC = %v\n", m.Alloc/1024, m.TotalAlloc/1024, m.Sys/1024, m.NumGC)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user