我不是一个不安全的软件包专家 - 我也不是一个经验丰富的C程序员。我正尝试在go中使用mmap syscall读取一个大文件> 1G。我做mmap和munmap的原因有很多,而不是读取,写入I/O。这是在旁边 - 我可以在测试中写入文件,当我从文件读取时,我可以确定字节长度匹配,但我无法读取此字符串文件的内容:(可以有人建议一些阅读?需要做进一步走一点,这里的一些代码,我做了样品的测试:mmap系统调用使用Golang的读取
filename := "/tmp/dd_file.db"
f, err := os.OpenFile(filename, os.O_RDWR, 0666)
defer f.Close()
if err != nil {
fmt.Printf("error opening file: %v", err)
}
stat, _ := f.Stat()
size := stat.Size()
fmt.Printf("[READ-ONLY] : size was : %+v\n", size)
got := make([]byte, size)
if _, err := f.ReadAt(got, 0); err != nil && err != io.EOF {
panic(err)
}
want, err := ioutil.ReadFile(filename)
if err != nil {
fmt.Printf("[READ-ONLY] : ioutil.ReadFile: %v", err)
}
// going to change the file size now, punch in a few things
t := unsafe.Sizeof("")
if err != nil {
fmt.Println(err)
os.Exit(1)
}
_, err = f.Seek(int64(t-1), 0)
if err != nil {
fmt.Println(err)
os.Exit(1)
}
_, err = f.Write([]byte(" "))
if err != nil {
fmt.Println(err)
os.Exit(1)
}
mmap, err := syscall.Mmap(int(f.Fd()), 0, int(t), syscall.PROT_READ|syscall.PROT_WRITE, syscall.MAP_SHARED)
if err != nil {
fmt.Println(err)
os.Exit(1)
}
// not too sure on reading data on string - doesnt work as expected.
map_array := (*[10000]string)(unsafe.Pointer(&mmap[0]))
map_array[0] = "yellow!"
err = syscall.Munmap(mmap)
if err != nil {
fmt.Println(err)
os.Exit(1)
}
newStat, _ := f.Stat()
newSize := newStat.Size()
fmt.Printf("[mmap() RW] : size was : %+v\n", newSize)
got = make([]byte, newSize)
if _, err := f.ReadAt(got, 0); err != nil && err != io.EOF {
panic(err)
}
if len(got) == len(want) {
fmt.Println("well the lengths are equal atleast??!")
}
if !bytes.Equal(got, want) {
fmt.Printf("\n [mmap() RW] : works! got %d \n want %d", len(got), len(want))
}
显然这工作正常 - 但如果我想通过mmap()的上mmapped文件读取,怎么做我从这些字节中读取字符串(我有一种感觉,在某处我可能需要使用编码包,但是随后StringHeader在不安全的文档上使我困惑)
建议:
也许我不明白你的意思。如果你正在使用'mmap',是不是该文件的内容可以作为'[] byte'?“。要获取字符串,可以使用'string(mmap [:100])'< - 将前100个字节转换为字符串。或者你可以使用['bytes.Buffer'](https://golang.org/pkg/bytes/#Buffer)(但可能不是你想要的,因为你避免使用io.reader/io.writer模式) – putu
I要避免读者 - 但我的问题是,我怀疑,通过mmap写入字符串字节它不是冲洗合法字符只是一些控制字符 - 我怀疑我的编码可能会搞砸 - 任何建议? –
看看['https://github.com/riobard/go-mmap'](https://github.com/riobard/go-mmap)。该软件包可以用作'mmap'用法的参考。为了将字符串写入'mmap',你可以做'copy(mmap,[] byte(“Your string”))''。 – putu