# source config info
. $OBDDIR/demos/config.sh
-[ ! -d $MNTOBD ] && mkdir $MNTOBD
-[ ! -d $MNTSNAP ] && mkdir $MNTSNAP
-[ ! -d $MNTSNAP2 ] && mkdir $MNTSNAP2
-
-
# temp file
if [ "$TMPFILE" -a -f $TMPFILE ]; then
echo "$TMPFILE exists; I'm unwilling to overwrite it. Remove [N/y]?" 1>&2
quit
EOF
+[ ! -d "$MNTOBD" ] && mkdir $MNTOBD
plog mount -t obdfs -odevice=/dev/obd0 none $MNTOBD
# one where changes are made, while $MNTSNAP will contain the original
# files at the point when the snapshot was taken.
+[ ! -d "$MNTOBD" ] && mkdir $MNTOBD
+[ ! -d "$MNTSNAP" ] && mkdir $MNTSNAP
plog mount -t obdfs -odevice=/dev/obd1 none $MNTOBD
plog mount -t obdfs -oro,device=/dev/obd2 none $MNTSNAP
*/
-#define OBD_PSDEV_MAJOR 186
-#define MAX_OBD_DEVICES 8
-#define MAX_MULTI 16
+#define OBD_PSDEV_MAJOR 186
+#define MAX_OBD_DEVICES 8
+#define MAX_MULTI 16
extern struct obd_device obd_dev[MAX_OBD_DEVICES];
struct obd_ops {
- int (*o_iocontrol)(int cmd, struct obd_conn *, int len, void *karg, void *uarg);
- int (*o_get_info)(struct obd_conn *, obd_count keylen, void *key, obd_count *vallen, void **val);
- int (*o_set_info)(struct obd_conn *, obd_count keylen, void *key, obd_count vallen, void *val);
- int (*o_attach)(struct obd_device *, obd_count len, void *);
- int (*o_detach)(struct obd_device *);
+ int (*o_iocontrol)(int cmd, struct obd_conn *, int len, void *karg,
+ void *uarg);
+ int (*o_get_info)(struct obd_conn *, obd_count keylen, void *key,
+ obd_count *vallen, void **val);
+ int (*o_set_info)(struct obd_conn *, obd_count keylen, void *key,
+ obd_count vallen, void *val);
+ int (*o_attach)(struct obd_device *dev, obd_count len, void *data);
+ int (*o_detach)(struct obd_device *dev);
int (*o_setup) (struct obd_device *dev, obd_count len, void *data);
int (*o_cleanup)(struct obd_device *dev);
int (*o_connect)(struct obd_conn *conn);
- int (*o_disconnect)(struct obd_conn *);
- int (*o_statfs)(struct obd_conn *, struct statfs *statfs);
+ int (*o_disconnect)(struct obd_conn *conn);
+ int (*o_statfs)(struct obd_conn *conn, struct statfs *statfs);
int (*o_preallocate)(struct obd_conn *, obd_count *req, obd_id *ids);
- int (*o_create)(struct obd_conn *, struct obdo *oa);
- int (*o_destroy)(struct obd_conn *, struct obdo *oa);
- int (*o_setattr)(struct obd_conn *, struct obdo *oa);
- int (*o_getattr)(struct obd_conn *, struct obdo *oa);
- int (*o_read)(struct obd_conn *, struct obdo *oa, char *buf, obd_size *count, obd_off offset);
- int (*o_write)(struct obd_conn *, struct obdo *oa, char *buf, obd_size *count, obd_off offset);
- int (*o_brw)(int rw, struct obd_conn * conn, struct obdo *oa, char *buf, obd_size count, obd_off offset, obd_flag flags);
- int (*o_punch)(struct obd_conn *, struct obdo *tgt, obd_size count, obd_off offset);
- int (*o_sync)(struct obd_conn *, struct obdo *tgt, obd_size count, obd_off offset);
- int (*o_migrate)(struct obd_conn *, struct obdo *dst, struct obdo *src, obd_size count, obd_off offset);
- int (*o_copy)(struct obd_conn *dstconn, struct obdo *dst, struct obd_conn *srconn, struct obdo *src, obd_size count, obd_off offset);
- int (*o_iterate)(struct obd_conn *, int (*)(obd_id, void *), obd_id start, void *);
-
+ int (*o_create)(struct obd_conn *conn, struct obdo *oa);
+ int (*o_destroy)(struct obd_conn *conn, struct obdo *oa);
+ int (*o_setattr)(struct obd_conn *conn, struct obdo *oa);
+ int (*o_getattr)(struct obd_conn *conn, struct obdo *oa);
+ int (*o_read)(struct obd_conn *conn, struct obdo *oa, char *buf,
+ obd_size *count, obd_off offset);
+ int (*o_write)(struct obd_conn *conn, struct obdo *oa, char *buf,
+ obd_size *count, obd_off offset);
+ int (*o_brw)(int rw, struct obd_conn *conn, struct obdo *oa,
+ char *buf, obd_size count, obd_off offset, obd_flag flags);
+ int (*o_punch)(struct obd_conn *conn, struct obdo *tgt, obd_size count,
+ obd_off offset);
+ int (*o_sync)(struct obd_conn *conn, struct obdo *tgt, obd_size count,
+ obd_off offset);
+ int (*o_migrate)(struct obd_conn *conn, struct obdo *dst,
+ struct obdo *src, obd_size count, obd_off offset);
+ int (*o_copy)(struct obd_conn *dstconn, struct obdo *dst,
+ struct obd_conn *srconn, struct obdo *src,
+ obd_size count, obd_off offset);
+ int (*o_iterate)(struct obd_conn *conn, int (*)(obd_id, obd_gr, void *),
+ obd_id *startid, obd_gr group, void *data);
};
#define OBT(dev) dev->obd_type->typ_ops
struct oic_prealloc_s {
uint32_t cli_id;
uint32_t alloc; /* user sets it to the number of inodes
- * requesting to be preallocated. kernel
- * sets it to the actual number * of
- * succesfully preallocated inodes */
+ * requesting to be preallocated. kernel
+ * sets it to the actual number of
+ * succesfully preallocated inodes */
obd_id ids[32]; /* actual inode numbers */
};
#define CMD(cmd) (( cmd == READ ) ? "read" : "write")
#define IDEBUG(inode) { \
- printk("]]%s line %d[[ ino %ld, blocks %ld, size %Ld, atm %ld, ctim %ld, mtm %ld, mode %o, uid %d, gid %d\n", \
+ printk("]]%s line %d[[ ino %ld, blocks %ld, size %Ld, atm %ld, ctm %ld, mtm %ld, mode %o, uid %d, gid %d\n", \
__FUNCTION__ , __LINE__, \
inode->i_ino, inode->i_blocks, inode->i_size,\
inode->i_atime, inode->i_ctime, inode->i_mtime,\
char *oi_inline;
};
-#define WB_NEXT(req) ((struct obdfs_wreq *) ((req)->wb_list.next))
-/* XXX page list should go on each inode instead of supberblock */
+#define OBD_INFO(inode) ((struct obdfs_inode_info *)(&(inode)->u.generic_ip))
+
+/* this was used when the list was in the superblock
#define OBD_LIST(inode) (((struct obdfs_sb_info *)(&(inode)->i_sb->u.generic_sbp))->osi_list)
+*/
+#define OBD_LIST(inode) (OBD_INFO(inode)->oi_list)
+#define WB_NEXT(req) ((struct obdfs_wreq *) ((req)->wb_list.next))
#define WREQ(entry) (list_entry(entry, struct obdfs_wreq, wb_list))
void obdfs_sysctl_init(void);
OBP(obddev, disconnect)(&conn);
return 0;
- /* XXX sync needs to be done */
case OBD_IOC_SYNC: {
struct oic_range_s *range = karg;
return -ENODEV;
err = copy_from_user(range, (const void *)arg, sizeof(*range));
- if (err) {
+
+ if ( err ) {
+ EXIT;
+ return err;
+ }
+
+ if ( !OBT(obddev) || !OBP(obddev, sync) ) {
+ err = -EOPNOTSUPP;
EXIT;
return err;
}
+ /* XXX sync needs to be tested/verified */
+ err = OBP(obddev, sync)(&conn, &range->obdo, range->count,
+ range->offset);
+
+ if ( err ) {
+ EXIT;
+ return err;
+ }
+
return put_user(err, (int *) arg);
}
case OBD_IOC_CREATE: {
}
}
- obd_sysctl_clean();
obd_cleanup_obdo_cache();
+ obd_sysctl_clean();
obd_init_magic = 0;
EXIT;
}
return 0;
}
- obdo_cachep = kmem_cache_create("obdo_cache",
- sizeof(struct obdo),
- 0, SLAB_HWCACHE_ALIGN,
- NULL, NULL);
+ obdo_cachep = kmem_cache_create("obdo_cache", sizeof(struct obdo),
+ 0, SLAB_HWCACHE_ALIGN, NULL, NULL);
if (obdo_cachep == NULL) {
EXIT;
return -ENOMEM;
} /* obd_client */
-
/* a connection defines a context in which preallocation can be managed. */
int gen_connect (struct obd_conn *conn)
{
}
INIT_LIST_HEAD(&cli->cli_prealloc_inodes);
- /* this should probably spinlocked? */
+ /* XXX this should probably spinlocked? */
cli->cli_id = ++conn->oc_dev->obd_gen_last_id;
cli->cli_prealloc_quota = 0;
cli->cli_obd = conn->oc_dev;
}
dst->o_size = src->o_size;
dst->o_blocks = src->o_blocks;
+ dst->o_valid |= (OBD_MD_FLSIZE | OBD_MD_FLBLOCKS);
UnlockPage(page);
__free_page(page);
}
/*
- * ext2_delete_entry deletes a directory entry by merging it with the
+ * obdfs_delete_entry deletes a directory entry by merging it with the
* previous entry
*/
static int obdfs_delete_entry (struct ext2_dir_entry_2 * dir,
struct obdo *obdo;
struct inode *inode;
struct obdfs_inode_info *oinfo;
+ ino_t ino;
int err;
+ ENTRY;
obdo = obdo_alloc();
if (!obdo) {
EXIT;
}
err = IOPS(dir, create)(IID(dir), obdo);
- if ( err )
+ ino = (ino_t)obdo->o_id;
+ obdo_free(obdo);
+
+ if ( err ) {
+ EXIT;
return ERR_PTR(err);
+ }
+
+ inode = iget(dir->i_sb, ino);
- inode = iget(dir->i_sb, (unsigned long)obdo->o_id);
if (!inode) {
- obdo_free(obdo);
EXIT;
return ERR_PTR(-EIO);
}
if (!list_empty(&inode->i_dentry)) {
- CDEBUG(D_INODE, "New inode (%ld) has aliases!\n",
- inode->i_ino);
+ CDEBUG(D_INODE, "New inode (%ld) has aliases!\n", inode->i_ino);
iput(inode);
EXIT;
return ERR_PTR(-EIO);
}
- obdo_free(obdo);
-
- oinfo = inode->u.generic_ip;
+ oinfo = OBD_INFO(inode);
INIT_LIST_HEAD(&oinfo->oi_list);
EXIT;
return inode;
int err = -EIO;
ENTRY;
-
inode = obdfs_new_inode(dir);
if ( IS_ERR(inode) ) {
EXIT;
ENTRY;
inode = obdfs_new_inode(dir);
- oinfo = inode->u.generic_ip;
+ oinfo = OBD_INFO(inode);
if ( IS_ERR(inode) ) {
EXIT;
return PTR_ERR(inode);
struct inode *inode = dentry->d_inode;
int rc;
- ENTRY;
+ ENTRY;
PDEBUG(page, "READ");
rc = obdfs_brw(READ, inode, page, 0);
if (!rc) {
* ext2 also does the same thing - discard write even if error?
*/
put_page(page);
- list_del(&wreq->wb_list);
+ list_del(&wreq->wb_list);
kmem_cache_free(obdfs_wreq_cachep, wreq);
EXIT;
wreq->wb_page = page;
wreq->wb_inode = inode;
+ CDEBUG(D_INODE, "getting page %p\n", wreq->wb_page);
get_page(wreq->wb_page);
+ CDEBUG(D_INODE, "adding wreq %p to inode %p\n", wreq, inode);
+ { struct obdfs_inode_info *oinfo = OBD_INFO(inode);
+ CDEBUG(D_INODE, "generic is %p\n", inode->u.generic_ip);
+ CDEBUG(D_INODE, "oinfo is %p\n", oinfo);
+ }
+ CDEBUG(D_INODE, "wreq_list %p\n", &wreq->wb_list);
+ return -EIO;
+ CDEBUG(D_INODE, "inode_list: next %p, prev %p\n", OBD_LIST(inode).next,
+ OBD_LIST(inode).prev);
+ CDEBUG(D_INODE, "inode_list_addr: %p\n", &OBD_LIST(inode));
+
list_add(&wreq->wb_list, &OBD_LIST(inode));
/* For testing purposes, we write out the page here.
* In the future, a flush daemon will write out the page.
*/
+ printk(KERN_INFO "finding page in cache for write\n");
wreq = obdfs_find_in_page_cache(inode, page);
if (!wreq) {
CDEBUG(D_INODE, "XXXX Can't find page after adding it!!!\n");
+ EXIT;
return -EINVAL;
- } else
- return obdfs_remove_from_page_cache(wreq);
+ }
- return 0;
+ EXIT;
+ return obdfs_remove_from_page_cache(wreq);
}
{
int rc;
- ENTRY;
+ ENTRY;
PDEBUG(page, "WRITEPAGE");
if ( sync ) {
rc = obdfs_brw(WRITE, inode, page, 1);
int obdfs_write_one_page(struct file *file, struct page *page, unsigned long offset, unsigned long bytes, const char * buf)
{
long status;
- struct inode *inode = file->f_dentry->d_inode;
+ struct inode *inode = file->f_dentry->d_inode;
ENTRY;
if ( !Page_Uptodate(page) ) {
struct page * page;
int rc;
- ENTRY;
+ ENTRY;
offset = offset & PAGE_CACHE_MASK;
CDEBUG(D_INODE, "\n");
inline int obdfs_has_inline(struct inode *inode)
{
- struct obdfs_inode_info *oinfo = inode->u.generic_ip;
+ struct obdfs_inode_info *oinfo = OBD_INFO(inode);
return (oinfo->oi_flags & OBD_FL_INLINEDATA);
}
void inline obdfs_from_inode(struct obdo *oa, struct inode *inode)
{
- struct obdfs_inode_info *oinfo = inode->u.generic_ip;
-
obdo_from_inode(oa, inode);
if (obdfs_has_inline(inode)) {
+ struct obdfs_inode_info *oinfo = OBD_INFO(inode);
+
memcpy(oa->o_inline, oinfo->oi_inline, OBD_INLINESZ);
oa->o_flags |= OBD_FL_INLINEDATA;
}
void inline obdfs_to_inode(struct inode *inode, struct obdo *oa)
{
- struct obdfs_inode_info *oinfo = inode->u.generic_ip;
-
obdo_to_inode(inode, oa);
if (obdo_has_inline(oa)) {
+ struct obdfs_inode_info *oinfo = OBD_INFO(inode);
+
memcpy(oinfo->oi_inline, oa->o_inline, OBD_INLINESZ);
oinfo->oi_flags |= OBD_FL_INLINEDATA;
}
struct obdo *oa;
int err;
+ ENTRY;
oa = obdo_alloc();
oa->o_valid = OBD_MD_FLALL;
obdfs_from_inode(oa, inode);
if (err) {
printk("obdfs_write_inode: obd_setattr fails (%d)\n", err);
+ EXIT;
return;
}
- return;
+ EXIT;
}
static void obdfs_delete_inode(struct inode *inode)
{
ENTRY;
- obdfs_sysctl_clean();
obdfs_cleanup_wreqcache();
+ obdfs_sysctl_clean();
unregister_filesystem(&obdfs_fs_type);
}