From bee7be2f8211f4f26822a45b78265d3e78a70d2f Mon Sep 17 00:00:00 2001 From: Sage Weil Date: Thu, 4 Feb 2010 09:31:30 -0800 Subject: [PATCH] cephx: add struct_v throughout. some cleanup. --- src/auth/Auth.h | 20 +++++++- src/auth/KeyRing.cc | 30 +++++------ src/auth/KeyRing.h | 9 ++-- src/auth/cephx/CephxKeyServer.cc | 5 +- src/auth/cephx/CephxKeyServer.h | 18 ++++++- src/auth/cephx/CephxProtocol.cc | 62 ++++++++++++++++------- src/auth/cephx/CephxProtocol.h | 60 ++++++++++++++++++---- src/auth/none/AuthNoneAuthorizeHandler.cc | 2 + src/auth/none/AuthNoneProtocol.h | 2 + src/mon/AuthMonitor.cc | 2 + src/mon/MonClient.cc | 2 + src/mon/Monitor.cc | 6 ++- 12 files changed, 163 insertions(+), 55 deletions(-) diff --git a/src/auth/Auth.h b/src/auth/Auth.h index 60b9455241ea1..5946e0e46899e 100644 --- a/src/auth/Auth.h +++ b/src/auth/Auth.h @@ -109,10 +109,14 @@ struct EntityAuth { map caps; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(key, bl); ::encode(caps, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(key, bl); ::decode(caps, bl); } @@ -130,12 +134,16 @@ struct AuthCapsInfo { AuthCapsInfo() : allow_all(false) {} void encode(bufferlist& bl) const { - uint32_t a = (uint32_t)allow_all; + __u8 struct_v = 1; + ::encode(struct_v, bl); + __u8 a = (__u8)allow_all; ::encode(a, bl); ::encode(caps, bl); } void decode(bufferlist::iterator& bl) { - uint32_t a; + __u8 struct_v; + ::decode(struct_v, bl); + __u8 a; ::decode(a, bl); allow_all = (bool)a; ::decode(caps, bl); @@ -212,10 +220,14 @@ struct ExpiringCryptoKey { utime_t expiration; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(key, bl); ::encode(expiration, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(key, bl); ::decode(expiration, bl); } @@ -229,10 +241,14 @@ struct RotatingSecrets { RotatingSecrets() : max_ver(0) {} void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(secrets, bl); ::encode(max_ver, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(secrets, bl); ::decode(max_ver, bl); } diff --git a/src/auth/KeyRing.cc b/src/auth/KeyRing.cc index 3c6632699bb23..6bf21551d3ad1 100644 --- a/src/auth/KeyRing.cc +++ b/src/auth/KeyRing.cc @@ -138,30 +138,26 @@ bool KeyRing::need_rotating_secrets() return false; } -bool KeyRing::get_service_secret(uint32_t service_id, uint64_t secret_id, CryptoKey& secret) -{ - Mutex::Locker l(lock); - /* we ignore the service id, there's only one service id that we're handling */ +void KeyRing::dump_rotating() { - map::iterator iter = rotating_secrets.secrets.begin(); - dout(0) << "dumping rotating secrets: this=" << dendl; - - for (; iter != rotating_secrets.secrets.end(); ++iter) { - ExpiringCryptoKey& key = iter->second; - - dout(0) << "id: " << iter->first << dendl; - dout(0) << "key.expiration: " << key.expiration << dendl; - bufferptr& bp = key.key.get_secret(); - bufferlist bl; - bl.append(bp); - hexdump(" key", bl.c_str(), bl.length()); - } + dout(0) << "dump_rotating:" << dendl; + for (map::iterator iter = rotating_secrets.secrets.begin(); + iter != rotating_secrets.secrets.end(); + ++iter) + dout(0) << " id " << iter->first << " " << iter->second.key + << " expires " << iter->second.expiration << dendl; } +bool KeyRing::get_service_secret(uint32_t service_id, uint64_t secret_id, CryptoKey& secret) +{ + Mutex::Locker l(lock); + + /* we ignore the service id, there's only one service id that we're handling */ map::iterator iter = rotating_secrets.secrets.find(secret_id); if (iter == rotating_secrets.secrets.end()) { dout(0) << "could not find secret_id=" << secret_id << dendl; + dump_rotating(); return false; } diff --git a/src/auth/KeyRing.h b/src/auth/KeyRing.h index e81a8d61e142c..a95a18ecd09b9 100644 --- a/src/auth/KeyRing.h +++ b/src/auth/KeyRing.h @@ -69,18 +69,19 @@ public: void import(KeyRing& other); // weirdness + void dump_rotating(); void set_rotating(RotatingSecrets& secrets); bool need_rotating_secrets(); bool get_service_secret(uint32_t service_id, uint64_t secret_id, CryptoKey& secret); void encode(bufferlist& bl) const { - __u8 v = 1; - ::encode(v, bl); + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(keys, bl); } void decode(bufferlist::iterator& bl) { - __u8 v; - ::decode(v, bl); + __u8 struct_v; + ::decode(struct_v, bl); ::decode(keys, bl); } }; diff --git a/src/auth/cephx/CephxKeyServer.cc b/src/auth/cephx/CephxKeyServer.cc index 88603780452d3..5c6ea16f5a64b 100644 --- a/src/auth/cephx/CephxKeyServer.cc +++ b/src/auth/cephx/CephxKeyServer.cc @@ -286,9 +286,8 @@ bool KeyServer::updated_rotating(bufferlist& rotating_bl, version_t& rotating_ve if (data.rotating_ver <= rotating_ver) return false; - - ::encode(data.rotating_ver, rotating_bl); - ::encode(data.rotating_secrets, rotating_bl); + + data.encode_rotating(rotating_bl); rotating_ver = data.rotating_ver; diff --git a/src/auth/cephx/CephxKeyServer.h b/src/auth/cephx/CephxKeyServer.h index 1c237f71dfda4..54528c4c88860 100644 --- a/src/auth/cephx/CephxKeyServer.h +++ b/src/auth/cephx/CephxKeyServer.h @@ -35,6 +35,8 @@ struct KeyServerData { KeyServerData() : version(0), rotating_ver(0) {} void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(version, bl); ::encode(rotating_ver, bl); ::encode(next_rotating_time, bl); @@ -42,6 +44,8 @@ struct KeyServerData { ::encode(rotating_secrets, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(version, bl); ::decode(rotating_ver, bl); ::decode(next_rotating_time, bl); @@ -49,8 +53,16 @@ struct KeyServerData { ::decode(rotating_secrets, bl); } + void encode_rotating(bufferlist& bl) { + __u8 struct_v = 1; + ::encode(struct_v, bl); + ::encode(rotating_ver, bl); + ::encode(rotating_secrets, bl); + } void decode_rotating(bufferlist& rotating_bl) { bufferlist::iterator iter = rotating_bl.begin(); + __u8 struct_v; + ::decode(struct_v, iter); ::decode(rotating_ver, iter); ::decode(rotating_secrets, iter); } @@ -100,7 +112,9 @@ struct KeyServerData { EntityAuth auth; void encode(bufferlist& bl) const { - __u32 _op = (__u32)op; + __u8 struct_v = 1; + ::encode(struct_v, bl); + __u32 _op = (__u32)op; ::encode(_op, bl); if (op == AUTH_INC_SET_ROTATING) { ::encode(rotating_bl, bl); @@ -110,6 +124,8 @@ struct KeyServerData { } } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); __u32 _op; ::decode(_op, bl); op = (IncrementalOp)_op; diff --git a/src/auth/cephx/CephxProtocol.cc b/src/auth/cephx/CephxProtocol.cc index 4b659b4c55da2..088ed7fe3bc20 100644 --- a/src/auth/cephx/CephxProtocol.cc +++ b/src/auth/cephx/CephxProtocol.cc @@ -34,18 +34,18 @@ int cephx_calc_client_server_challenge(CryptoKey& secret, __u64 server_challenge * Authentication */ -bool cephx_build_service_ticket(CephXSessionAuthInfo& info, bufferlist& reply) +bool cephx_build_service_ticket_blob(CephXSessionAuthInfo& info, CephXTicketBlob& blob) { CephXServiceTicketInfo ticket_info; ticket_info.session_key = info.session_key; ticket_info.ticket = info.ticket; ticket_info.ticket.caps = info.ticket.caps; - ::encode(info.secret_id, reply); + dout(10) << "build_service_ticket encoded info.secret_id=" << info.secret_id << " ticket_info.ticket.name=" << ticket_info.ticket.name.to_str() << dendl; - if (encode_encrypt(ticket_info, info.service_secret, reply) < 0) + blob.secret_id = info.secret_id; + if (encode_encrypt_enc_bl(ticket_info, info.service_secret, blob.blob) < 0) return false; - return true; } @@ -64,6 +64,9 @@ bool cephx_build_service_ticket_reply( CryptoKey& ticket_enc_key, bufferlist& reply) { + __u8 service_ticket_reply_v = 1; + ::encode(service_ticket_reply_v, reply); + uint32_t num = ticket_info_vec.size(); ::encode(num, reply); dout(10) << "build_service_ticket_reply encoding " << num @@ -75,6 +78,9 @@ bool cephx_build_service_ticket_reply( CephXSessionAuthInfo& info = *ticket_iter; ::encode(info.service_id, reply); + __u8 service_ticket_v = 1; + ::encode(service_ticket_v, reply); + CephXServiceTicket msg_a; msg_a.session_key = info.session_key; msg_a.validity = info.validity; @@ -83,8 +89,10 @@ bool cephx_build_service_ticket_reply( bufferlist service_ticket_bl; - if (!cephx_build_service_ticket(info, service_ticket_bl)) + CephXTicketBlob blob; + if (!cephx_build_service_ticket_blob(info, blob)) return false; + ::encode(blob, service_ticket_bl); ::encode((__u8)should_encrypt_ticket, reply); @@ -105,15 +113,18 @@ bool cephx_build_service_ticket_reply( * this ServiceTicket with the result. */ bool CephXTicketHandler::verify_service_ticket_reply(CryptoKey& secret, - bufferlist::iterator& indata) + bufferlist::iterator& indata) { - CephXServiceTicket msg_a; + __u8 service_ticket_v; + ::decode(service_ticket_v, indata); + CephXServiceTicket msg_a; if (decode_decrypt(msg_a, secret, indata) < 0) { dout(0) << "verify_service_ticket_reply failed decode_decrypt with secret " << secret << dendl; return false; } - __u8 ticket_enc; + + __u8 ticket_enc; ::decode(ticket_enc, indata); if (ticket_enc) { dout(10) << "getting encrypted ticket" << dendl; @@ -209,6 +220,9 @@ void CephXTicketManager::set_have_need_key(uint32_t service_id, uint32_t& have, bool CephXTicketManager::verify_service_ticket_reply(CryptoKey& secret, bufferlist::iterator& indata) { + __u8 service_ticket_reply_v; + ::decode(service_ticket_reply_v, indata); + uint32_t num; ::decode(num, indata); dout(10) << "verify_service_ticket_reply got " << num << " keys" << dendl; @@ -242,8 +256,12 @@ CephXAuthorizer *CephXTicketHandler::build_authorizer(uint64_t global_id) a->session_key = session_key; a->nonce = ((__u64)rand() << 32) + rand(); + __u8 authorizer_v = 1; + ::encode(authorizer_v, a->bl); + ::encode(global_id, a->bl); ::encode(service_id, a->bl); + ::encode(ticket, a->bl); CephXAuthorize msg; @@ -322,41 +340,51 @@ bool cephx_decode_ticket(KeyStore& keys, uint32_t service_id, CephXTicketBlob& t bool cephx_verify_authorizer(KeyStore& keys, bufferlist::iterator& indata, CephXServiceTicketInfo& ticket_info, bufferlist& reply_bl) { + __u8 authorizer_v; + ::decode(authorizer_v, indata); + uint32_t service_id; - uint64_t secret_id; uint64_t global_id; CryptoKey service_secret; ::decode(global_id, indata); ::decode(service_id, indata); - ::decode(secret_id, indata); - dout(10) << "verify_authorizer decrypted service_id=" << service_id << " secret_id=" << secret_id << dendl; - if (secret_id == (uint64_t)-1) { + // ticket blob + CephXTicketBlob ticket; + ::decode(ticket, indata); + dout(10) << "verify_authorizer decrypted service_id=" << service_id + << " secret_id=" << ticket.secret_id << dendl; + + if (ticket.secret_id == (uint64_t)-1) { EntityName name; name.entity_type = service_id; if (!keys.get_secret(name, service_secret)) { - dout(0) << "verify_authorizer could not get general service secret for service_id=" << service_id << " secret_id=" << secret_id << dendl; + dout(0) << "verify_authorizer could not get general service secret for service_id=" << service_id + << " secret_id=" << ticket.secret_id << dendl; return false; } } else { - if (!keys.get_service_secret(service_id, secret_id, service_secret)) { - dout(0) << "verify_authorizer could not get service secret for service_id=" << service_id << " secret_id=" << secret_id << dendl; + if (!keys.get_service_secret(service_id, ticket.secret_id, service_secret)) { + dout(0) << "verify_authorizer could not get service secret for service_id=" << service_id + << " secret_id=" << ticket.secret_id << dendl; return false; } } - if (decode_decrypt(ticket_info, service_secret, indata) < 0) { + if (decode_decrypt_enc_bl(ticket_info, service_secret, ticket.blob) < 0) { dout(0) << "verify_authorizer could not decrypt ticket info" << dendl; return false; } if (ticket_info.ticket.global_id != global_id) { - dout(0) << "verify_authorizer global_id mismatch: declared id=" << global_id << " ticket_id=" << ticket_info.ticket.global_id << dendl; + dout(0) << "verify_authorizer global_id mismatch: declared id=" << global_id + << " ticket_id=" << ticket_info.ticket.global_id << dendl; return false; } dout(10) << "verify_authorizer global_id=" << global_id << dendl; + // CephXAuthorize CephXAuthorize auth_msg; if (decode_decrypt(auth_msg, ticket_info.session_key, indata) < 0) { dout(0) << "verify_authorizercould not decrypt authorize request" << dendl; diff --git a/src/auth/cephx/CephxProtocol.h b/src/auth/cephx/CephxProtocol.h index 2a816a1455123..754d6d9968565 100644 --- a/src/auth/cephx/CephxProtocol.h +++ b/src/auth/cephx/CephxProtocol.h @@ -94,9 +94,13 @@ struct CephXServerChallenge { __u64 server_challenge; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(server_challenge, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(server_challenge, bl); } }; @@ -137,11 +141,15 @@ struct CephXTicketBlob { bufferlist blob; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(secret_id, bl); ::encode(blob, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(secret_id, bl); ::decode(blob, bl); } @@ -155,11 +163,15 @@ struct CephXAuthenticate { CephXTicketBlob old_ticket; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(client_challenge, bl); ::encode(key, bl); ::encode(old_ticket, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(client_challenge, bl); ::decode(key, bl); ::decode(old_ticket, bl); @@ -198,7 +210,7 @@ struct CephXSessionAuthInfo { }; -extern bool cephx_build_service_ticket(CephXSessionAuthInfo& ticket_info, bufferlist& reply); +extern bool cephx_build_service_ticket_blob(CephXSessionAuthInfo& ticket_info, CephXTicketBlob& blob); extern void cephx_build_service_ticket_request(uint32_t keys, bufferlist& request); @@ -213,9 +225,13 @@ struct CephXServiceTicketRequest { uint32_t keys; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(keys, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(keys, bl); } }; @@ -229,9 +245,13 @@ WRITE_CLASS_ENCODER(CephXServiceTicketRequest); struct CephXAuthorizeReply { __u64 nonce_plus_one; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(nonce_plus_one, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(nonce_plus_one, bl); } }; @@ -300,10 +320,14 @@ struct CephXServiceTicket { utime_t validity; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(session_key, bl); ::encode(validity, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(session_key, bl); ::decode(validity, bl); } @@ -316,10 +340,14 @@ struct CephXServiceTicketInfo { CryptoKey session_key; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(ticket, bl); ::encode(session_key, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(ticket, bl); ::decode(session_key, bl); } @@ -329,9 +357,13 @@ WRITE_CLASS_ENCODER(CephXServiceTicketInfo); struct CephXAuthorize { __u64 nonce; void encode(bufferlist& bl) const { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(nonce, bl); } void decode(bufferlist::iterator& bl) { + __u8 struct_v; + ::decode(struct_v, bl); ::decode(nonce, bl); } }; @@ -370,6 +402,8 @@ int decode_decrypt_enc_bl(T& t, CryptoKey key, bufferlist& bl_enc) { } bufferlist::iterator iter2 = bl.begin(); + __u8 struct_v; + ::decode(struct_v, iter2); ::decode(magic, iter2); if (magic != AUTH_ENC_MAGIC) { generic_dout(0) << "bad magic in decode_decrypt, " << magic << " != " << AUTH_ENC_MAGIC << dendl; @@ -381,26 +415,34 @@ int decode_decrypt_enc_bl(T& t, CryptoKey key, bufferlist& bl_enc) { return 0; } +template +int encode_encrypt_enc_bl(const T& t, CryptoKey& key, bufferlist& out) { + bufferlist bl; + __u8 struct_v = 1; + ::encode(struct_v, bl); + uint64_t magic = AUTH_ENC_MAGIC; + ::encode(magic, bl); + ::encode(t, bl); + + int ret = key.encrypt(bl, out); + if (ret < 0) + return ret; + return 0; +} + template int decode_decrypt(T& t, CryptoKey key, bufferlist::iterator& iter) { bufferlist bl_enc; ::decode(bl_enc, iter); - return decode_decrypt_enc_bl(t, key, bl_enc); } template int encode_encrypt(const T& t, CryptoKey& key, bufferlist& out) { - uint64_t magic = AUTH_ENC_MAGIC; - bufferlist bl; - ::encode(magic, bl); - ::encode(t, bl); - bufferlist bl_enc; - int ret = key.encrypt(bl, bl_enc); + int ret = encode_encrypt_enc_bl(t, key, bl_enc); if (ret < 0) return ret; - ::encode(bl_enc, out); return 0; } diff --git a/src/auth/none/AuthNoneAuthorizeHandler.cc b/src/auth/none/AuthNoneAuthorizeHandler.cc index c5e39af54a0ca..82afb15f63bb7 100644 --- a/src/auth/none/AuthNoneAuthorizeHandler.cc +++ b/src/auth/none/AuthNoneAuthorizeHandler.cc @@ -9,6 +9,8 @@ bool AuthNoneAuthorizeHandler::verify_authorizer(bufferlist& authorizer_data, bu bufferlist::iterator iter = authorizer_data.begin(); try { + __u8 struct_v = 1; + ::decode(struct_v, iter); ::decode(entity_name, iter); ::decode(global_id, iter); } catch (buffer::error *err) { diff --git a/src/auth/none/AuthNoneProtocol.h b/src/auth/none/AuthNoneProtocol.h index 0f70a6efbd17b..d5339ccaffa18 100644 --- a/src/auth/none/AuthNoneProtocol.h +++ b/src/auth/none/AuthNoneProtocol.h @@ -20,6 +20,8 @@ struct AuthNoneAuthorizer : public AuthAuthorizer { AuthNoneAuthorizer() : AuthAuthorizer(CEPH_AUTH_NONE) { } bool build_authorizer(uint64_t global_id) { + __u8 struct_v = 1; + ::encode(struct_v, bl); ::encode(*g_conf.entity_name, bl); ::encode(global_id, bl); return 0; diff --git a/src/mon/AuthMonitor.cc b/src/mon/AuthMonitor.cc index f4052a9a34d4f..88a59c478bcf1 100644 --- a/src/mon/AuthMonitor.cc +++ b/src/mon/AuthMonitor.cc @@ -377,6 +377,8 @@ bool AuthMonitor::prep_auth(MAuth *m, bool paxos_writable) set<__u32> supported; try { + __u8 struct_v = 1; + ::decode(struct_v, indata); ::decode(supported, indata); ::decode(entity_name, indata); ::decode(s->global_id, indata); diff --git a/src/mon/MonClient.cc b/src/mon/MonClient.cc index b2cf400c33ff0..fc2c751384394 100644 --- a/src/mon/MonClient.cc +++ b/src/mon/MonClient.cc @@ -375,6 +375,8 @@ void MonClient::_reopen_session() MAuth *m = new MAuth; m->protocol = 0; + __u8 struct_v = 1; + ::encode(struct_v, m->auth_payload); ::encode(auth_supported, m->auth_payload); ::encode(entity_name, m->auth_payload); ::encode(global_id, m->auth_payload); diff --git a/src/mon/Monitor.cc b/src/mon/Monitor.cc index 39e6bb9e3ba3c..06b805d25120a 100644 --- a/src/mon/Monitor.cc +++ b/src/mon/Monitor.cc @@ -992,10 +992,12 @@ bool Monitor::ms_get_authorizer(int dest_type, AuthAuthorizer **authorizer, bool } - bufferlist ticket_data; - ret = cephx_build_service_ticket(info, ticket_data); + CephXTicketBlob blob; + ret = cephx_build_service_ticket_blob(info, blob); if (ret < 0) return false; + bufferlist ticket_data; + ::encode(blob, ticket_data); dout(0) << "built service ticket" << dendl; bufferlist::iterator iter = ticket_data.begin(); -- 2.39.5