示例#1
0
static int filldir64(void * __buf, const char * name, int namlen, loff_t offset,
		     u64 ino, unsigned int d_type)
{
	struct linux_dirent64 * dirent, d;
	struct getdents_callback64 * buf = (struct getdents_callback64 *) __buf;
	int reclen = ROUND_UP64(NAME_OFFSET(dirent) + namlen + 1);
	int err;

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	dirent = buf->previous;
	if (dirent) {
		d.d_off = offset;
		err = copy_to_user(&dirent->d_off, &d.d_off, sizeof(d.d_off));
		BUG_ON(err);
	}
	dirent = buf->current_dir;
	buf->previous = dirent;
	memset(&d, 0, NAME_OFFSET(&d));
	d.d_ino = ino;
	d.d_reclen = reclen;
	d.d_type = d_type;
	err = copy_to_user(dirent, &d, NAME_OFFSET(&d));
	BUG_ON(err);
	err = copy_to_user(dirent->d_name, name, namlen);
	BUG_ON(err);
	err = put_user(0, dirent->d_name + namlen);
	BUG_ON(err);
	dirent = (void *)dirent + reclen;
	buf->current_dir = dirent;
	buf->count -= reclen;
	return 0;
}
示例#2
0
文件: readdir.c 项目: xricson/knoppix
static int filldir(void * __buf, const char * name, int namlen, loff_t offset,
		   ino_t ino, unsigned int d_type)
{
	struct linux_dirent __user * dirent;
	struct getdents_callback * buf = (struct getdents_callback *) __buf;
	int reclen = ROUND_UP(NAME_OFFSET(dirent) + namlen + 1);

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	dirent = buf->previous;
	if (dirent) {
		if (__put_user(offset, &dirent->d_off))
			goto efault;
	}
	dirent = buf->current_dir;
	if (__put_user(ino, &dirent->d_ino))
		goto efault;
	if (__put_user(reclen, &dirent->d_reclen))
		goto efault;
	if (copy_to_user(dirent->d_name, name, namlen))
		goto efault;
	if (__put_user(0, dirent->d_name + namlen))
		goto efault;
	buf->previous = dirent;
	((char *) dirent) += reclen;
	buf->current_dir = dirent;
	buf->count -= reclen;
	return 0;
efault:
	buf->error = -EFAULT;
	return -EFAULT;
}
示例#3
0
static int sunos_filldir(void * __buf, const char * name, int namlen,
			 loff_t offset, ino_t ino, unsigned int d_type)
{
	struct sunos_dirent * dirent;
	struct sunos_dirent_callback * buf = (struct sunos_dirent_callback *) __buf;
	int reclen = ROUND_UP(NAME_OFFSET(dirent) + namlen + 1);

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	dirent = buf->previous;
	if (dirent)
		put_user(offset, &dirent->d_off);
	dirent = buf->curr;
	buf->previous = dirent;
	put_user(ino, &dirent->d_ino);
	put_user(namlen, &dirent->d_namlen);
	put_user(reclen, &dirent->d_reclen);
	copy_to_user(dirent->d_name, name, namlen);
	put_user(0, dirent->d_name + namlen);
	((char *) dirent) += reclen;
	buf->curr = dirent;
	buf->count -= reclen;
	return 0;
}
示例#4
0
static int
filldir32 (void *__buf, const char *name, int namlen, loff_t offset, ino_t ino,
	   unsigned int d_type)
{
	struct linux32_dirent __user * dirent;
	struct getdents32_callback * buf = (struct getdents32_callback *) __buf;
	int reclen = ROUND_UP(NAME_OFFSET(dirent) + namlen + 1, 4);
	u32 d_ino;

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	d_ino = ino;
	if (sizeof(d_ino) < sizeof(ino) && d_ino != ino)
		return -EOVERFLOW;
	dirent = buf->previous;
	if (dirent)
		put_user(offset, &dirent->d_off);
	dirent = buf->current_dir;
	buf->previous = dirent;
	put_user(d_ino, &dirent->d_ino);
	put_user(reclen, &dirent->d_reclen);
	copy_to_user(dirent->d_name, name, namlen);
	put_user(0, dirent->d_name + namlen);
	dirent = ((void __user *)dirent) + reclen;
	buf->current_dir = dirent;
	buf->count -= reclen;
	return 0;
}
示例#5
0
static int sunos_filldirentry(void * __buf, const char * name, int namlen,
			      loff_t offset, ino_t ino, unsigned int d_type)
{
	struct sunos_direntry __user *dirent;
	struct sunos_direntry_callback * buf =
		(struct sunos_direntry_callback *) __buf;
	int reclen = ROUND_UP(NAME_OFFSET(dirent) + namlen + 1);
	u32 d_ino;

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	d_ino = ino;
	if (sizeof(d_ino) < sizeof(ino) && d_ino != ino)
		return -EOVERFLOW;
	dirent = buf->previous;
	dirent = buf->curr;
	buf->previous = dirent;
	put_user(d_ino, &dirent->d_ino);
	put_user(namlen, &dirent->d_namlen);
	put_user(reclen, &dirent->d_reclen);
	if (copy_to_user(dirent->d_name, name, namlen))
		return -EFAULT;
	put_user(0, dirent->d_name + namlen);
	dirent = (void __user *) dirent + reclen;
	buf->curr = dirent;
	buf->count -= reclen;
	return 0;
}
示例#6
0
文件: fs.c 项目: 7L/pi_plus
static int filldir(void * __buf, const char * name, int namlen, loff_t offset,
		u64 ino, unsigned d_type)
{
	struct hpux_dirent __user * dirent;
	struct getdents_callback * buf = (struct getdents_callback *) __buf;
	ino_t d_ino;
	int reclen = ALIGN(NAME_OFFSET(dirent) + namlen + 1, sizeof(long));

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	d_ino = ino;
	if (sizeof(d_ino) < sizeof(ino) && d_ino != ino) {
		buf->error = -EOVERFLOW;
		return -EOVERFLOW;
	}
	dirent = buf->previous;
	if (dirent)
		if (put_user(offset, &dirent->d_off))
			goto Efault;
	dirent = buf->current_dir;
	if (put_user(d_ino, &dirent->d_ino) ||
	    put_user(reclen, &dirent->d_reclen) ||
	    put_user(namlen, &dirent->d_namlen) ||
	    copy_to_user(dirent->d_name, name, namlen) ||
	    put_user(0, dirent->d_name + namlen))
		goto Efault;
	buf->previous = dirent;
	buf->current_dir = (void __user *)dirent + reclen;
	buf->count -= reclen;
	return 0;
Efault:
	buf->error = -EFAULT;
	return -EFAULT;
}
示例#7
0
static int filldir(void * __buf, const char * name, int namlen, loff_t offset,
		   u64 ino, unsigned int d_type)
{
	struct linux_dirent __user * dirent;
	struct getdents_callback * buf = (struct getdents_callback *) __buf;
	unsigned long d_ino;
	int reclen = ALIGN(NAME_OFFSET(dirent) + namlen + 2, sizeof(long));
	int ret;

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	d_ino = ino;
	if (sizeof(d_ino) < sizeof(ino) && d_ino != ino) {
		buf->error = -EOVERFLOW;
		return -EOVERFLOW;
	}
	dirent = buf->previous;
	if (dirent) {
		if (__put_user(offset, &dirent->d_off))
			goto efault;
	}
	dirent = buf->current_dir;

	scribe_data_non_det();
	ret = __put_user(d_ino, &dirent->d_ino);
	scribe_data_pop_flags();
	if (ret)
		goto efault;

	if (__put_user(reclen, &dirent->d_reclen))
		goto efault;
	if (copy_to_user(dirent->d_name, name, namlen))
		goto efault;
	if (__put_user(0, dirent->d_name + namlen))
		goto efault;
	if (__put_user(d_type, (char __user *) dirent + reclen - 1))
		goto efault;
	buf->previous = dirent;
	dirent = (void __user *)dirent + reclen;
	buf->current_dir = dirent;
	buf->count -= reclen;
	return 0;
efault:
	buf->error = -EFAULT;
	return -EFAULT;
}
示例#8
0
/*
 * Stupid Pico/Pilot/Pine!!!  They are assuming that the returned st_size
 * field from a stat() syscall for a directory is the actual size of the 
 * directory.  But Cygwin returns zero and they don't check for that.
 *
 * The unfortunate result is that a diretory stat() is _very_ expensive...
 */
static void get_dir_size(char *name, struct linux_stat *ls)
{
  DIR *dir;
  struct dirent *d;
  int size = 0;
    char file[MAX_PATH];
    change_path_to_relative(file, (char*)name);
  my_print("[ender]get dir size %s \n", file);
  dir = opendir(file);
  if (NULL == dir) return;
  
  while (NULL != (d = readdir(dir))) {
    size += ROUND_UP(NAME_OFFSET(d) + strlen(d->d_name)+1);
  } 
  
  ls->st_size = size;
}
示例#9
0
static int filldir64(void * __buf, const char * name, int namlen, loff_t offset,
                     u64 ino, unsigned int d_type)
{
    struct linux_dirent64 __user *dirent;
    struct getdents_callback64 * buf = (struct getdents_callback64 *) __buf;
    int reclen = ALIGN(NAME_OFFSET(dirent) + namlen + 1, sizeof(u64));

    buf->error = -EINVAL;	/* only used if we fail.. */
    if (reclen > buf->count)
        return -EINVAL;

    if (!gr_acl_handle_filldir(buf->file, name, namlen, ino))
        return 0;

    dirent = buf->previous;
    if (dirent) {
        if (__put_user(offset, &dirent->d_off))
            goto efault;
    }
    dirent = buf->current_dir;
    if (__put_user(ino, &dirent->d_ino))
        goto efault;
    if (__put_user(0, &dirent->d_off))
        goto efault;
    if (__put_user(reclen, &dirent->d_reclen))
        goto efault;
    if (__put_user(d_type, &dirent->d_type))
        goto efault;
    if (copy_to_user(dirent->d_name, name, namlen))
        goto efault;
    if (__put_user(0, dirent->d_name + namlen))
        goto efault;
    buf->previous = dirent;
    dirent = (void __user *)dirent + reclen;
    buf->current_dir = dirent;
    buf->count -= reclen;
    return 0;
efault:
    buf->error = -EFAULT;
    return -EFAULT;
}
示例#10
0
static int filldir(void * __buf, const char * name, int namlen, off_t offset, ino_t ino)
{
	struct linux_dirent * dirent;
	struct getdents_callback * buf = (struct getdents_callback *) __buf;
	int reclen = ROUND_UP(NAME_OFFSET(dirent) + namlen + 1);

	buf->error = -EINVAL;	/* only used if we fail.. */
	if (reclen > buf->count)
		return -EINVAL;
	dirent = buf->previous;
	if (dirent)
		put_user(offset, &dirent->d_off);
	dirent = buf->current_dir;
	buf->previous = dirent;
	put_user(ino, &dirent->d_ino);
	put_user(reclen, &dirent->d_reclen);
	memcpy_tofs(dirent->d_name, name, namlen);
	put_user(0, dirent->d_name + namlen);
	((char *) dirent) += reclen;
	buf->current_dir = dirent;
	buf->count -= reclen;
	return 0;
}
示例#11
0
static int osf_filldir(void * __buf, const char * name, int namlen, off_t offset, ino_t ino)
{
	struct osf_dirent * dirent;
	struct osf_dirent_callback * buf = (struct osf_dirent_callback *) __buf;
	int reclen = ROUND_UP(NAME_OFFSET(dirent) + namlen + 1);

	buf->error = -EINVAL;		/* only used if we fail */
	if (reclen > buf->count)
		return -EINVAL;
	if (buf->basep) {
		put_user(offset, buf->basep);
		buf->basep = NULL;
	}
	dirent = buf->dirent;
	put_user(ino, &dirent->d_ino);
	put_user(namlen, &dirent->d_namlen);
	put_user(reclen, &dirent->d_reclen);
	memcpy_tofs(dirent->d_name, name, namlen);
	put_fs_byte(0, dirent->d_name + namlen);
	((char *) dirent) += reclen;
	buf->dirent = dirent;
	buf->count -= reclen;
	return 0;
}
示例#12
0
static int ext2_readdir (struct inode * inode, struct file * filp,
			 struct dirent * dirent, int count)
{
	unsigned long offset, blk;
	int i, num, stored, dlen;
	struct buffer_head * bh, * tmp, * bha[16];
	struct ext2_dir_entry * de;
	struct super_block * sb;
	int err, version;

	if (!inode || !S_ISDIR(inode->i_mode))
		return -EBADF;
	sb = inode->i_sb;

	stored = 0;
	bh = NULL;
	offset = filp->f_pos & (sb->s_blocksize - 1);

	while (count > 0 && !stored && filp->f_pos < inode->i_size) {
		blk = (filp->f_pos) >> EXT2_BLOCK_SIZE_BITS(sb);
		bh = ext2_bread (inode, blk, 0, &err);
		if (!bh) {
			filp->f_pos += sb->s_blocksize - offset;
			continue;
		}

		/*
		 * Do the readahead
		 */
		if (!offset) {
			for (i = 16 >> (EXT2_BLOCK_SIZE_BITS(sb) - 9), num = 0;
			     i > 0; i--) {
				tmp = ext2_getblk (inode, ++blk, 0, &err);
				if (tmp && !tmp->b_uptodate && !tmp->b_lock)
					bha[num++] = tmp;
				else
					brelse (tmp);
			}
			if (num) {
				ll_rw_block (READA, num, bha);
				for (i = 0; i < num; i++)
					brelse (bha[i]);
			}
		}
		
revalidate:
		/* If the dir block has changed since the last call to
		 * readdir(2), then we might be pointing to an invalid
		 * dirent right now.  Scan from the start of the block
		 * to make sure. */
		if (filp->f_version != inode->i_version) {
			for (i = 0; i < sb->s_blocksize && i < offset; ) {
				de = (struct ext2_dir_entry *) 
					(bh->b_data + i);
				/* It's too expensive to do a full
				 * dirent test each time round this
				 * loop, but we do have to test at
				 * least that it is non-zero.  A
				 * failure will be detected in the
				 * dirent test below. */
				if (de->rec_len < EXT2_DIR_REC_LEN(1))
					break;
				i += de->rec_len;
			}
			offset = i;
			filp->f_pos = (filp->f_pos & ~(sb->s_blocksize - 1))
				| offset;
			filp->f_version = inode->i_version;
		}
		
		while (count > 0 && filp->f_pos < inode->i_size 
		       && offset < sb->s_blocksize) {
			de = (struct ext2_dir_entry *) (bh->b_data + offset);
			if (!ext2_check_dir_entry ("ext2_readdir", inode, de,
						   bh, offset)) {
				/* On error, skip the f_pos to the
                                   next block. */
				filp->f_pos = (filp->f_pos & (sb->s_blocksize - 1))
					      + sb->s_blocksize;
				brelse (bh);
				return stored;
			}
			if (de->inode) {
				dlen = ROUND_UP(NAME_OFFSET(dirent) 
						+ de->name_len + 1);
				/* Old libc libraries always use a
                                   count of 1. */
				if (count == 1 && !stored)
					count = dlen;
				if (count < dlen) {
					count = 0;
					break;
				}

				/* We might block in the next section
				 * if the data destination is
				 * currently swapped out.  So, use a
				 * version stamp to detect whether or
				 * not the directory has been modified
				 * during the copy operation. */
				version = inode->i_version;
				i = de->name_len;
				memcpy_tofs (dirent->d_name, de->name, i);
				put_fs_long (de->inode, &dirent->d_ino);
				put_fs_byte (0, dirent->d_name + i);
				put_fs_word (i, &dirent->d_reclen);
				put_fs_long (dlen, &dirent->d_off);
				if (version != inode->i_version)
					goto revalidate;
				dcache_add(inode, de->name, de->name_len,
						 de->inode);

				stored += dlen;
				count -= dlen;
				((char *) dirent) += dlen;
			}
			offset += de->rec_len;
			filp->f_pos += de->rec_len;
		}
		offset = 0;
		brelse (bh);
	}
	if (!IS_RDONLY(inode)) {
		inode->i_atime = CURRENT_TIME;
		inode->i_dirt = 1;
	}
	return stored;
}
示例#13
0
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <stddef.h>

#include "panic.h"
#include "settings.h"

static struct name_to_offset {
	const char *name;
	int offset;
} name_to_offset[] = {
#define NAME_OFFSET(name, field) { name, offsetof(struct settings, field) },
	NAME_OFFSET("control-type", control_type)
	NAME_OFFSET("pad-keysyms-0", pad_keysyms[0])
	NAME_OFFSET("pad-keysyms-1", pad_keysyms[1])
	NAME_OFFSET("pad-keysyms-2", pad_keysyms[2])
	NAME_OFFSET("pad-keysyms-3", pad_keysyms[3])
	NAME_OFFSET("pad-keysyms-4", pad_keysyms[4])
	NAME_OFFSET("pad-keysyms-5", pad_keysyms[5])
	NAME_OFFSET("pad-keysyms-6", pad_keysyms[6])
	NAME_OFFSET("pad-keysyms-7", pad_keysyms[7])
	NAME_OFFSET("pad-sticks-0", pad_sticks[0])
	NAME_OFFSET("pad-sticks-1", pad_sticks[1])
	NAME_OFFSET("pad-sticks-2", pad_sticks[2])
	NAME_OFFSET("pad-sticks-3", pad_sticks[3])
	NAME_OFFSET("pad-sticks-4", pad_sticks[4])
	NAME_OFFSET("pad-sticks-5", pad_sticks[5])
	NAME_OFFSET("pad-sticks-6", pad_sticks[6])
	NAME_OFFSET("pad-sticks-7", pad_sticks[7])