Beispiel #1
0
ssize_t fatfs_write(file_t * file, struct uio * uio, size_t count)
{
    void * buf;
    struct fatfs_inode * in = get_inode_of_vnode(file->vnode);
    size_t count_out;
    int err;

    if (!S_ISREG(file->vnode->vn_mode))
        return -EOPNOTSUPP;

    err = f_lseek(&in->fp, file->seek_pos);
    if (err)
        return -EIO;

    err = uio_get_kaddr(uio, &buf);
    if (err)
        return err;

    err = f_write(&in->fp, buf, count, &count_out);
    if (err)
        return fresult2errno(err);

    file->seek_pos = f_tell(&in->fp);

    return count_out;
}
Beispiel #2
0
/**
 * Override read() function.
 */
static ssize_t procfs_read(file_t * file, struct uio * uio, size_t bcount)
{
    const struct procfs_info * spec = PROCFS_GET_FILESPEC(file);
    struct procfs_stream * stream;
    void * vbuf;
    ssize_t bytes;
    int err;

    if (!spec || spec->ftype > PROCFS_LAST || !file->stream)
        return -EIO;

    err = uio_get_kaddr(uio, &vbuf);
    if (err)
        return err;

    stream = (struct procfs_stream *)file->stream;
    bytes = stream->bytes;
    if (bytes > 0 && file->seek_pos <= bytes) {
        const ssize_t count = min(bcount, bytes - file->seek_pos);

        if (count <= bytes) {
            ssize_t sz;

            sz = strlcpy((char *)vbuf, stream->buf + file->seek_pos, count);
            sz++;
            bytes = (sz >= count) ? count : sz;
            file->seek_pos += bytes;
        }
    }

    return bytes;
}
Beispiel #3
0
ssize_t dev_write(file_t * file, struct uio * uio, size_t bcount)
{
    vnode_t * const vnode = file->vnode;
    const off_t offset = file->seek_pos;
    const int oflags = file->oflags;
    struct dev_info * devnfo = (struct dev_info *)vnode->vn_specinfo;
    uint8_t * buf;
    size_t buf_offset;
    off_t block_offset;
    ssize_t bytes_wr;
    int err;

    if (!devnfo->write)
        return -EOPNOTSUPP;

    err = uio_get_kaddr(uio, (void **)(&buf));
    if (err)
        return err;

    if ((devnfo->flags & DEV_FLAGS_MB_WRITE) &&
            ((bcount / devnfo->block_size) > 1)) {
        return devnfo->write(devnfo, offset, buf, bcount, oflags);
    }

    buf_offset = 0;
    block_offset = 0;
    do {
        int tries = RW_MAX_TRIES;
        size_t to_write = (bcount > devnfo->block_size) ?
            devnfo->block_size : bcount;
        ssize_t ret;

        while (1) {
            ret = devnfo->write(devnfo, offset + block_offset,
                                &buf[buf_offset], to_write, oflags);
            if (ret < 0 && --tries <= 0) {
                bytes_wr = (buf_offset > 0) ? buf_offset : ret;
                goto out;
            } else {
                break;
            }
        }

        buf_offset += ret;
        block_offset++;
        bcount -= ret;
    } while (bcount > 0);

    bytes_wr = buf_offset;
out:
    file->seek_pos += bytes_wr;
    return bytes_wr;
}
Beispiel #4
0
/**
 * Override write() function.
 */
static ssize_t procfs_write(file_t * file, struct uio * uio, size_t bcount)
{
    const struct procfs_info * spec = PROCFS_GET_FILESPEC(file);
    procfs_writefn_t * fn;
    void * vbuf;
    int err;

    if (!spec)
        return -EIO;

    if (spec->ftype > PROCFS_LAST)
        return -ENOLINK;

    fn = procfs_write_funcs[spec->ftype];
    if (!fn)
        return -ENOTSUP;

    err = uio_get_kaddr(uio, &vbuf);
    if (err)
        return err;

    return fn(spec, (struct procfs_stream *)(file->stream),
              vbuf, bcount);
}