class MmapScanner::Mmap

Public Class Methods

new(p1, p2 = v2, p3 = v3) click to toggle source
static VALUE mmap_initialize(int argc, VALUE *argv, VALUE obj)
{
    mmap_data_t *data;
    VALUE file, voffset, vlength;
    off_t offset = 0;
    size_t length = 0;
    int fd;
    struct stat st;
    void *ptr;

    Data_Get_Struct(obj, mmap_data_t, data);
    if (data->ptr)
        rb_raise(rb_eRuntimeError, "already mapped");
    rb_scan_args(argc, argv, "12", &file, &voffset, &vlength);
    if (TYPE(file) != T_FILE)
        rb_raise(rb_eTypeError, "File object required");
    if (voffset != Qnil && NUM2LL(voffset) < 0)
        rb_raise(rb_eRangeError, "offset out of range: %lld", NUM2LL(voffset));
    if (vlength != Qnil && NUM2LL(vlength) < 0)
        rb_raise(rb_eRangeError, "length out of range: %lld", NUM2LL(vlength));
    fd = FIX2INT(rb_funcall(file, rb_intern("fileno"), 0));
    if (fstat(fd, &st) < 0)
        rb_sys_fail("fstat");
    offset = voffset == Qnil ? 0 : NUM2SIZET(voffset);
    length = vlength == Qnil ? st.st_size : NUM2SIZET(vlength);
    if (offset + length > st.st_size)
        length = st.st_size - offset;
    if ((ptr = mmap(NULL, length, PROT_READ, MAP_SHARED, fd, offset)) == MAP_FAILED)
        rb_sys_fail("mmap");

    data->ptr = ptr;
    data->size = length;
    return Qnil;
}

Public Instance Methods

size() click to toggle source
static VALUE mmap_size(VALUE obj)
{
    mmap_data_t *data;
    Data_Get_Struct(obj, mmap_data_t, data);
    return SIZET2NUM(data->size);
}
unmap() click to toggle source
static VALUE mmap_unmap(VALUE obj)
{
    mmap_data_t *data;
    Data_Get_Struct(obj, mmap_data_t, data);
    if (data->ptr == NULL)
        rb_raise(rb_eRuntimeError, "already unmapped");
    if (munmap(data->ptr, data->size) < 0)
        rb_sys_fail("munmap");
    data->ptr = NULL;
    return Qnil;
}