提交 d93ac51c 编写于 作者: L Linus Torvalds

Merge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/sage/ceph-client

* 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/sage/ceph-client:
  ceph: remove bad auth_x kmem_cache
  ceph: fix lockless caps check
  ceph: clear dir complete, invalidate dentry on replayed rename
  ceph: fix direct io truncate offset
  ceph: discard incoming messages with bad seq #
  ceph: fix seq counting for skipped messages
  ceph: add missing #includes
  ceph: fix leaked spinlock during mds reconnect
  ceph: print more useful version info on module load
  ceph: fix snap realm splits
  ceph: clear dir complete on d_move
...@@ -509,7 +509,7 @@ static void writepages_finish(struct ceph_osd_request *req, ...@@ -509,7 +509,7 @@ static void writepages_finish(struct ceph_osd_request *req,
u64 bytes = 0; u64 bytes = 0;
struct ceph_client *client = ceph_inode_to_client(inode); struct ceph_client *client = ceph_inode_to_client(inode);
long writeback_stat; long writeback_stat;
unsigned issued = __ceph_caps_issued(ci, NULL); unsigned issued = ceph_caps_issued(ci);
/* parse reply */ /* parse reply */
replyhead = msg->front.iov_base; replyhead = msg->front.iov_base;
......
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
#include <linux/module.h> #include <linux/module.h>
#include <linux/slab.h> #include <linux/slab.h>
#include <linux/err.h> #include <linux/err.h>
#include <linux/slab.h>
#include "types.h" #include "types.h"
#include "auth_none.h" #include "auth_none.h"
......
#ifndef _FS_CEPH_AUTH_NONE_H #ifndef _FS_CEPH_AUTH_NONE_H
#define _FS_CEPH_AUTH_NONE_H #define _FS_CEPH_AUTH_NONE_H
#include <linux/slab.h>
#include "auth.h" #include "auth.h"
/* /*
......
...@@ -12,8 +12,6 @@ ...@@ -12,8 +12,6 @@
#include "auth.h" #include "auth.h"
#include "decode.h" #include "decode.h"
struct kmem_cache *ceph_x_ticketbuf_cachep;
#define TEMP_TICKET_BUF_LEN 256 #define TEMP_TICKET_BUF_LEN 256
static void ceph_x_validate_tickets(struct ceph_auth_client *ac, int *pneed); static void ceph_x_validate_tickets(struct ceph_auth_client *ac, int *pneed);
...@@ -131,13 +129,12 @@ static int ceph_x_proc_ticket_reply(struct ceph_auth_client *ac, ...@@ -131,13 +129,12 @@ static int ceph_x_proc_ticket_reply(struct ceph_auth_client *ac,
char *ticket_buf; char *ticket_buf;
u8 struct_v; u8 struct_v;
dbuf = kmem_cache_alloc(ceph_x_ticketbuf_cachep, GFP_NOFS | GFP_ATOMIC); dbuf = kmalloc(TEMP_TICKET_BUF_LEN, GFP_NOFS);
if (!dbuf) if (!dbuf)
return -ENOMEM; return -ENOMEM;
ret = -ENOMEM; ret = -ENOMEM;
ticket_buf = kmem_cache_alloc(ceph_x_ticketbuf_cachep, ticket_buf = kmalloc(TEMP_TICKET_BUF_LEN, GFP_NOFS);
GFP_NOFS | GFP_ATOMIC);
if (!ticket_buf) if (!ticket_buf)
goto out_dbuf; goto out_dbuf;
...@@ -251,9 +248,9 @@ static int ceph_x_proc_ticket_reply(struct ceph_auth_client *ac, ...@@ -251,9 +248,9 @@ static int ceph_x_proc_ticket_reply(struct ceph_auth_client *ac,
ret = 0; ret = 0;
out: out:
kmem_cache_free(ceph_x_ticketbuf_cachep, ticket_buf); kfree(ticket_buf);
out_dbuf: out_dbuf:
kmem_cache_free(ceph_x_ticketbuf_cachep, dbuf); kfree(dbuf);
return ret; return ret;
bad: bad:
...@@ -605,8 +602,6 @@ static void ceph_x_destroy(struct ceph_auth_client *ac) ...@@ -605,8 +602,6 @@ static void ceph_x_destroy(struct ceph_auth_client *ac)
remove_ticket_handler(ac, th); remove_ticket_handler(ac, th);
} }
kmem_cache_destroy(ceph_x_ticketbuf_cachep);
kfree(ac->private); kfree(ac->private);
ac->private = NULL; ac->private = NULL;
} }
...@@ -641,26 +636,20 @@ int ceph_x_init(struct ceph_auth_client *ac) ...@@ -641,26 +636,20 @@ int ceph_x_init(struct ceph_auth_client *ac)
int ret; int ret;
dout("ceph_x_init %p\n", ac); dout("ceph_x_init %p\n", ac);
ret = -ENOMEM;
xi = kzalloc(sizeof(*xi), GFP_NOFS); xi = kzalloc(sizeof(*xi), GFP_NOFS);
if (!xi) if (!xi)
return -ENOMEM; goto out;
ret = -ENOMEM;
ceph_x_ticketbuf_cachep = kmem_cache_create("ceph_x_ticketbuf",
TEMP_TICKET_BUF_LEN, 8,
(SLAB_RECLAIM_ACCOUNT|SLAB_MEM_SPREAD),
NULL);
if (!ceph_x_ticketbuf_cachep)
goto done_nomem;
ret = -EINVAL; ret = -EINVAL;
if (!ac->secret) { if (!ac->secret) {
pr_err("no secret set (for auth_x protocol)\n"); pr_err("no secret set (for auth_x protocol)\n");
goto done_nomem; goto out_nomem;
} }
ret = ceph_crypto_key_unarmor(&xi->secret, ac->secret); ret = ceph_crypto_key_unarmor(&xi->secret, ac->secret);
if (ret) if (ret)
goto done_nomem; goto out_nomem;
xi->starting = true; xi->starting = true;
xi->ticket_handlers = RB_ROOT; xi->ticket_handlers = RB_ROOT;
...@@ -670,10 +659,9 @@ int ceph_x_init(struct ceph_auth_client *ac) ...@@ -670,10 +659,9 @@ int ceph_x_init(struct ceph_auth_client *ac)
ac->ops = &ceph_x_ops; ac->ops = &ceph_x_ops;
return 0; return 0;
done_nomem: out_nomem:
kfree(xi); kfree(xi);
if (ceph_x_ticketbuf_cachep) out:
kmem_cache_destroy(ceph_x_ticketbuf_cachep);
return ret; return ret;
} }
......
...@@ -1861,8 +1861,8 @@ static void kick_flushing_capsnaps(struct ceph_mds_client *mdsc, ...@@ -1861,8 +1861,8 @@ static void kick_flushing_capsnaps(struct ceph_mds_client *mdsc,
} else { } else {
pr_err("%p auth cap %p not mds%d ???\n", inode, pr_err("%p auth cap %p not mds%d ???\n", inode,
cap, session->s_mds); cap, session->s_mds);
spin_unlock(&inode->i_lock);
} }
spin_unlock(&inode->i_lock);
} }
} }
......
...@@ -880,7 +880,16 @@ static int ceph_rename(struct inode *old_dir, struct dentry *old_dentry, ...@@ -880,7 +880,16 @@ static int ceph_rename(struct inode *old_dir, struct dentry *old_dentry,
* do_request, above). If there is no trace, we need * do_request, above). If there is no trace, we need
* to do it here. * to do it here.
*/ */
/* d_move screws up d_subdirs order */
ceph_i_clear(new_dir, CEPH_I_COMPLETE);
d_move(old_dentry, new_dentry); d_move(old_dentry, new_dentry);
/* ensure target dentry is invalidated, despite
rehashing bug in vfs_rename_dir */
new_dentry->d_time = jiffies;
ceph_dentry(new_dentry)->lease_shared_gen = 0;
} }
ceph_mdsc_put_request(req); ceph_mdsc_put_request(req);
return err; return err;
......
...@@ -665,7 +665,8 @@ static ssize_t ceph_sync_write(struct file *file, const char __user *data, ...@@ -665,7 +665,8 @@ static ssize_t ceph_sync_write(struct file *file, const char __user *data,
* throw out any page cache pages in this range. this * throw out any page cache pages in this range. this
* may block. * may block.
*/ */
truncate_inode_pages_range(inode->i_mapping, pos, pos+len); truncate_inode_pages_range(inode->i_mapping, pos,
(pos+len) | (PAGE_CACHE_SIZE-1));
} else { } else {
pages = alloc_page_vector(num_pages); pages = alloc_page_vector(num_pages);
if (IS_ERR(pages)) { if (IS_ERR(pages)) {
......
...@@ -997,6 +997,10 @@ int ceph_fill_trace(struct super_block *sb, struct ceph_mds_request *req, ...@@ -997,6 +997,10 @@ int ceph_fill_trace(struct super_block *sb, struct ceph_mds_request *req,
dn, dn->d_name.len, dn->d_name.name); dn, dn->d_name.len, dn->d_name.name);
dout("fill_trace doing d_move %p -> %p\n", dout("fill_trace doing d_move %p -> %p\n",
req->r_old_dentry, dn); req->r_old_dentry, dn);
/* d_move screws up d_subdirs order */
ceph_i_clear(dir, CEPH_I_COMPLETE);
d_move(req->r_old_dentry, dn); d_move(req->r_old_dentry, dn);
dout(" src %p '%.*s' dst %p '%.*s'\n", dout(" src %p '%.*s' dst %p '%.*s'\n",
req->r_old_dentry, req->r_old_dentry,
......
...@@ -1334,6 +1334,7 @@ static int read_partial_message(struct ceph_connection *con) ...@@ -1334,6 +1334,7 @@ static int read_partial_message(struct ceph_connection *con)
unsigned front_len, middle_len, data_len, data_off; unsigned front_len, middle_len, data_len, data_off;
int datacrc = con->msgr->nocrc; int datacrc = con->msgr->nocrc;
int skip; int skip;
u64 seq;
dout("read_partial_message con %p msg %p\n", con, m); dout("read_partial_message con %p msg %p\n", con, m);
...@@ -1368,6 +1369,25 @@ static int read_partial_message(struct ceph_connection *con) ...@@ -1368,6 +1369,25 @@ static int read_partial_message(struct ceph_connection *con)
return -EIO; return -EIO;
data_off = le16_to_cpu(con->in_hdr.data_off); data_off = le16_to_cpu(con->in_hdr.data_off);
/* verify seq# */
seq = le64_to_cpu(con->in_hdr.seq);
if ((s64)seq - (s64)con->in_seq < 1) {
pr_info("skipping %s%lld %s seq %lld, expected %lld\n",
ENTITY_NAME(con->peer_name),
pr_addr(&con->peer_addr.in_addr),
seq, con->in_seq + 1);
con->in_base_pos = -front_len - middle_len - data_len -
sizeof(m->footer);
con->in_tag = CEPH_MSGR_TAG_READY;
con->in_seq++;
return 0;
} else if ((s64)seq - (s64)con->in_seq > 1) {
pr_err("read_partial_message bad seq %lld expected %lld\n",
seq, con->in_seq + 1);
con->error_msg = "bad message sequence # for incoming message";
return -EBADMSG;
}
/* allocate message? */ /* allocate message? */
if (!con->in_msg) { if (!con->in_msg) {
dout("got hdr type %d front %d data %d\n", con->in_hdr.type, dout("got hdr type %d front %d data %d\n", con->in_hdr.type,
...@@ -1379,6 +1399,7 @@ static int read_partial_message(struct ceph_connection *con) ...@@ -1379,6 +1399,7 @@ static int read_partial_message(struct ceph_connection *con)
con->in_base_pos = -front_len - middle_len - data_len - con->in_base_pos = -front_len - middle_len - data_len -
sizeof(m->footer); sizeof(m->footer);
con->in_tag = CEPH_MSGR_TAG_READY; con->in_tag = CEPH_MSGR_TAG_READY;
con->in_seq++;
return 0; return 0;
} }
if (IS_ERR(con->in_msg)) { if (IS_ERR(con->in_msg)) {
...@@ -2030,6 +2051,7 @@ void ceph_con_revoke_message(struct ceph_connection *con, struct ceph_msg *msg) ...@@ -2030,6 +2051,7 @@ void ceph_con_revoke_message(struct ceph_connection *con, struct ceph_msg *msg)
ceph_msg_put(con->in_msg); ceph_msg_put(con->in_msg);
con->in_msg = NULL; con->in_msg = NULL;
con->in_tag = CEPH_MSGR_TAG_READY; con->in_tag = CEPH_MSGR_TAG_READY;
con->in_seq++;
} else { } else {
dout("con_revoke_pages %p msg %p pages %p no-op\n", dout("con_revoke_pages %p msg %p pages %p no-op\n",
con, con->in_msg, msg); con, con->in_msg, msg);
......
...@@ -869,16 +869,20 @@ void ceph_handle_snap(struct ceph_mds_client *mdsc, ...@@ -869,16 +869,20 @@ void ceph_handle_snap(struct ceph_mds_client *mdsc,
continue; continue;
ci = ceph_inode(inode); ci = ceph_inode(inode);
spin_lock(&inode->i_lock); spin_lock(&inode->i_lock);
if (!ci->i_snap_realm) if (list_empty(&ci->i_snap_realm_item)) {
goto split_skip_inode; struct ceph_snap_realm *oldrealm =
ceph_put_snap_realm(mdsc, ci->i_snap_realm); ci->i_snap_realm;
spin_lock(&realm->inodes_with_caps_lock);
list_add(&ci->i_snap_realm_item, dout(" moving %p to split realm %llx %p\n",
&realm->inodes_with_caps); inode, realm->ino, realm);
ci->i_snap_realm = realm; spin_lock(&realm->inodes_with_caps_lock);
spin_unlock(&realm->inodes_with_caps_lock); list_add(&ci->i_snap_realm_item,
ceph_get_snap_realm(mdsc, realm); &realm->inodes_with_caps);
split_skip_inode: ci->i_snap_realm = realm;
spin_unlock(&realm->inodes_with_caps_lock);
ceph_get_snap_realm(mdsc, realm);
ceph_put_snap_realm(mdsc, oldrealm);
}
spin_unlock(&inode->i_lock); spin_unlock(&inode->i_lock);
iput(inode); iput(inode);
} }
......
...@@ -996,9 +996,10 @@ static int __init init_ceph(void) ...@@ -996,9 +996,10 @@ static int __init init_ceph(void)
if (ret) if (ret)
goto out_icache; goto out_icache;
pr_info("loaded %d.%d.%d (mon/mds/osd proto %d/%d/%d)\n", pr_info("loaded (mon/mds/osd proto %d/%d/%d, osdmap %d/%d %d/%d)\n",
CEPH_VERSION_MAJOR, CEPH_VERSION_MINOR, CEPH_VERSION_PATCH, CEPH_MONC_PROTOCOL, CEPH_MDSC_PROTOCOL, CEPH_OSDC_PROTOCOL,
CEPH_MONC_PROTOCOL, CEPH_MDSC_PROTOCOL, CEPH_OSDC_PROTOCOL); CEPH_OSDMAP_VERSION, CEPH_OSDMAP_VERSION_EXT,
CEPH_OSDMAP_INC_VERSION, CEPH_OSDMAP_INC_VERSION_EXT);
return 0; return 0;
out_icache: out_icache:
......
...@@ -10,6 +10,7 @@ ...@@ -10,6 +10,7 @@
#include <linux/fs.h> #include <linux/fs.h>
#include <linux/mempool.h> #include <linux/mempool.h>
#include <linux/pagemap.h> #include <linux/pagemap.h>
#include <linux/slab.h>
#include <linux/wait.h> #include <linux/wait.h>
#include <linux/writeback.h> #include <linux/writeback.h>
#include <linux/slab.h> #include <linux/slab.h>
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册