亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定
已解決430363個問題,去搜搜看,總會有你想問的

在 Go 中調用 mremap 不起作用,但沒有錯誤

在 Go 中調用 mremap 不起作用,但沒有錯誤

Go
慕的地8271018 2022-07-11 16:42:36
我正在嘗試mremap從 Go 獲取文件,但文件的大小似乎沒有改變,盡管返回errno了0. 當我嘗試訪問映射內存時,這會導致段錯誤。我已經包含了下面的代碼。實現類似于包中的mmap實現sys,所以我不確定這里出了什么問題:package mainimport (    "fmt"    "io/ioutil"    "log"    "os"    "reflect"    "unsafe"    "golang.org/x/sys/unix")// taken from <https://github.com/torvalds/linux/blob/f8394f232b1eab649ce2df5c5f15b0e528c92091/include/uapi/linux/mman.h#L8>const (    MREMAP_MAYMOVE = 0x1    // MREMAP_FIXED     = 0x2    // MREMAP_DONTUNMAP = 0x4)func mremap(data []byte, size int) ([]byte, error) {    header := (*reflect.SliceHeader)(unsafe.Pointer(&data))    mmapAddr, mmapSize, errno := unix.Syscall6(        unix.SYS_MREMAP,        header.Data,        uintptr(header.Len),        uintptr(size),        uintptr(MREMAP_MAYMOVE),        0,        0,    )    if errno != 0 {        return nil, fmt.Errorf("mremap failed with errno: %s", errno)    }    if mmapSize != uintptr(size) {        return nil, fmt.Errorf("mremap size mismatch: requested: %d got: %d", size, mmapSize)    }    header.Data = mmapAddr    header.Cap = size    header.Len = size    return data, nil}func main() {    log.SetFlags(log.LstdFlags | log.Lshortfile)    const mmPath = "/tmp/mm_test"    // create a file for mmap with 1 byte of data.    // this should take up 1 block on disk (4096 bytes).    err := ioutil.WriteFile(mmPath, []byte{0x1}, 0755)    if err != nil {        log.Fatal(err)    }    // open and stat the file.    file, err := os.OpenFile(mmPath, os.O_RDWR, 0)    if err != nil {        log.Fatal(err)    }    defer file.Close()    stat, err := file.Stat()    if err != nil {        log.Fatal(err)    }    // mmap the file and print the contents.    // this should print only one byte of data.    data, err := unix.Mmap(int(file.Fd()), 0, int(stat.Size()), unix.PROT_READ|unix.PROT_WRITE, unix.MAP_SHARED)    if err != nil {        log.Fatal(err)    }}我嘗試尋找其他使用 的 Go 代碼mremap,但似乎找不到。我將不勝感激任何意見!
查看完整描述

1 回答

?
慕虎7371278

TA貢獻1802條經驗 獲得超4個贊

正如評論中提到的@kostix,mmap用于將常規文件映射到內存中。訪問緩沖區導致段錯誤的原因是底層文件本身不夠大。解決方案是在調用之前將文件截斷為所需的長度mremap:


if err := file.Truncate(2*4096); err != nil {

  log.Fatal(err)

}

data, err = mremap(data, 2*4096)


查看完整回答
反對 回復 2022-07-11
  • 1 回答
  • 0 關注
  • 126 瀏覽
慕課專欄
更多

添加回答

舉報

0/150
提交
取消
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號