瀏覽代碼

ceph: fix authenticator buffer size calculation

The buffer size was incorrectly calculated for the ceph_x_encrypt()
encapsulated ticket blob.  Use a helper (with correct arithmetic) and
BUG out if we were wrong.

Signed-off-by: Sage Weil <sage@newdream.net>
Sage Weil 15 年之前
父節點
當前提交
807c86e2ce
共有 1 個文件被更改,包括 13 次插入6 次删除
  1. 13 6
      fs/ceph/auth_x.c

+ 13 - 6
fs/ceph/auth_x.c

@@ -28,6 +28,12 @@ static int ceph_x_is_authenticated(struct ceph_auth_client *ac)
 	return (ac->want_keys & xi->have_keys) == ac->want_keys;
 	return (ac->want_keys & xi->have_keys) == ac->want_keys;
 }
 }
 
 
+static int ceph_x_encrypt_buflen(int ilen)
+{
+	return sizeof(struct ceph_x_encrypt_header) + ilen + 16 +
+		sizeof(u32);
+}
+
 static int ceph_x_encrypt(struct ceph_crypto_key *secret,
 static int ceph_x_encrypt(struct ceph_crypto_key *secret,
 			  void *ibuf, int ilen, void *obuf, size_t olen)
 			  void *ibuf, int ilen, void *obuf, size_t olen)
 {
 {
@@ -242,7 +248,7 @@ static int ceph_x_build_authorizer(struct ceph_auth_client *ac,
 				   struct ceph_x_ticket_handler *th,
 				   struct ceph_x_ticket_handler *th,
 				   struct ceph_x_authorizer *au)
 				   struct ceph_x_authorizer *au)
 {
 {
-	int len;
+	int maxlen;
 	struct ceph_x_authorize_a *msg_a;
 	struct ceph_x_authorize_a *msg_a;
 	struct ceph_x_authorize_b msg_b;
 	struct ceph_x_authorize_b msg_b;
 	void *p, *end;
 	void *p, *end;
@@ -253,15 +259,15 @@ static int ceph_x_build_authorizer(struct ceph_auth_client *ac,
 	dout("build_authorizer for %s %p\n",
 	dout("build_authorizer for %s %p\n",
 	     ceph_entity_type_name(th->service), au);
 	     ceph_entity_type_name(th->service), au);
 
 
-	len = sizeof(*msg_a) + sizeof(msg_b) + sizeof(u32) +
-		ticket_blob_len + 16;
-	dout("  need len %d\n", len);
-	if (au->buf && au->buf->alloc_len < len) {
+	maxlen = sizeof(*msg_a) + sizeof(msg_b) +
+		ceph_x_encrypt_buflen(ticket_blob_len);
+	dout("  need len %d\n", maxlen);
+	if (au->buf && au->buf->alloc_len < maxlen) {
 		ceph_buffer_put(au->buf);
 		ceph_buffer_put(au->buf);
 		au->buf = NULL;
 		au->buf = NULL;
 	}
 	}
 	if (!au->buf) {
 	if (!au->buf) {
-		au->buf = ceph_buffer_new(len, GFP_NOFS);
+		au->buf = ceph_buffer_new(maxlen, GFP_NOFS);
 		if (!au->buf)
 		if (!au->buf)
 			return -ENOMEM;
 			return -ENOMEM;
 	}
 	}
@@ -296,6 +302,7 @@ static int ceph_x_build_authorizer(struct ceph_auth_client *ac,
 	au->buf->vec.iov_len = p - au->buf->vec.iov_base;
 	au->buf->vec.iov_len = p - au->buf->vec.iov_base;
 	dout(" built authorizer nonce %llx len %d\n", au->nonce,
 	dout(" built authorizer nonce %llx len %d\n", au->nonce,
 	     (int)au->buf->vec.iov_len);
 	     (int)au->buf->vec.iov_len);
+	BUG_ON(au->buf->vec.iov_len > maxlen);
 	return 0;
 	return 0;
 
 
 out_buf:
 out_buf: