def set_value(self, values): if not self['mechanism'] in self.plain_mechs: if values: self.xml.text = bytes(base64.b64encode(values)).decode('utf-8') else: self.xml.text = '=' else: self.xml.text = bytes(values).decode('utf-8')
def response(self, prefix=b""): nc = bytes("%08x" % self.nonce_count) a1 = bytes(self.hash(self.A1()).hexdigest().lower()) a2 = bytes(self.hash(self.A2(prefix)).hexdigest().lower()) s = self.nonce + b":" + nc + b":" + self.cnonce + b":" + self.qop + b":" + a2 return bytes(self.hash(a1 + b":" + s).hexdigest().lower())
def response(self, prefix=b''): nc = bytes('%08x' % self.nonce_count) a1 = bytes(self.hash(self.A1()).hexdigest().lower()) a2 = bytes(self.hash(self.A2(prefix)).hexdigest().lower()) s = self.nonce + b':' + nc + b':' + self.cnonce + \ b':' + self.qop + b':' + a2 return bytes(self.hash(a1 + b':' + s).hexdigest().lower())
def saslname(self, value): escaped = b"" for char in bytes(value): if char == b",": escaped += b"=2C" elif char == b"=": escaped += b"=3D" else: if isinstance(char, int): char = chr(char) escaped += bytes(char) return escaped
def saslname(self, value): escaped = b'' for char in bytes(value): if char == b',': escaped += b'=2C' elif char == b'=': escaped += b'=3D' else: if isinstance(char, int): char = chr(char) escaped += bytes(char) return escaped
def choose(mech_list, credentials, security_settings, limit=None, min_mech=None): available_mechs = set(MECHANISMS.keys()) if limit is None: limit = set(mech_list) if not isinstance(limit, set): limit = set(limit) if not isinstance(mech_list, set): mech_list = set(mech_list) mech_list = mech_list.intersection(limit) available_mechs = available_mechs.intersection(mech_list) best_score = MECH_SEC_SCORES.get(min_mech, -1) best_mech = None for name in available_mechs: if name in MECH_SEC_SCORES: if MECH_SEC_SCORES[name] > best_score: best_score = MECH_SEC_SCORES[name] best_mech = name if best_mech is None: raise SASLNoAppropriateMechanism() mech_class = MECHANISMS[best_mech] try: creds = credentials(mech_class.required_credentials, mech_class.optional_credentials) for req in mech_class.required_credentials: if req not in creds: raise SASLCancelled('Missing credential: %s' % req) for opt in mech_class.optional_credentials: if opt not in creds: creds[opt] = b'' for cred in creds: if cred in ('username', 'password', 'authzid'): creds[cred] = bytes(saslprep(creds[cred])) else: creds[cred] = bytes(creds[cred]) security_opts = security_settings(mech_class.security) return mech_class(best_mech, creds, security_opts) except SASLCancelled as e: log.info('SASL: %s: %s', best_mech, e.message) mech_list.remove(best_mech) return choose(mech_list, credentials, security_settings, limit=limit, min_mech=min_mech)
def process_1(self, challenge): self.step = 1 data = {} self.cnonce = bytes(('%s' % random.random())[2:]) gs2_cbind_flag = b'n' if self.credentials['channel_binding']: if self.use_channel_binding: gs2_cbind_flag = b'p=tls-unique' else: gs2_cbind_flag = b'y' authzid = b'' if self.credentials['authzid']: authzid = b'a=' + self.saslname(self.credentials['authzid']) self.gs2_header = gs2_cbind_flag + b',' + authzid + b',' nonce = b'r=' + self.cnonce username = b'n=' + self.saslname(self.credentials['username']) self.client_first_message_bare = username + b',' + nonce self.client_first_message = self.gs2_header + \ self.client_first_message_bare return self.client_first_message
def process_1(self, challenge): self.step = 1 data = {} self.cnonce = bytes(("%s" % random.random())[2:]) gs2_cbind_flag = b"n" if self.credentials["channel_binding"]: if self.use_channel_binding: gs2_cbind_flag = b"p=tls-unique" else: gs2_cbind_flag = b"y" authzid = b"" if self.credentials["authzid"]: authzid = b"a=" + self.saslname(self.credentials["authzid"]) self.gs2_header = gs2_cbind_flag + b"," + authzid + b"," nonce = b"r=" + self.cnonce username = b"n=" + self.saslname(self.credentials["username"]) self.client_first_message_bare = username + b"," + nonce self.client_first_message = self.gs2_header + self.client_first_message_bare return self.client_first_message
def set_binval(self, value): self.del_binval() parent = self.parent() if value: xml = ET.Element('{%s}BINVAL' % self.namespace) xml.text = bytes(base64.b64encode(value)).decode('utf-8') parent.append(xml)
def Hi(self, text, salt, iterations): text = bytes(text) ui1 = self.HMAC(text, salt + b"\0\0\0\01") ui = ui1 for i in range(iterations - 1): ui1 = self.HMAC(text, ui1) ui = XOR(ui, ui1) return ui
def Hi(self, text, salt, iterations): text = bytes(text) ui1 = self.HMAC(text, salt + b'\0\0\0\01') ui = ui1 for i in range(iterations - 1): ui1 = self.HMAC(text, ui1) ui = XOR(ui, ui1) return ui
def respond(self): data = { 'username': quote(self.credentials['username']), 'authzid': quote(self.credentials['authzid']), 'realm': quote(self.credentials['realm']), 'nonce': quote(self.nonce), 'cnonce': quote(self.cnonce), 'nc': bytes('%08x' % self.nonce_count), 'qop': self.qop, 'digest-uri': quote(self.digest_uri()), 'response': self.response(b'AUTHENTICATE'), 'maxbuf': self.maxbuf } resp = b'' for key, value in data.items(): if value and value != b'""': resp += b',' + bytes(key) + b'=' + bytes(value) return resp[1:]
def parse(self, challenge=b''): data = {} var_name = b'' var_value = b'' # States: var, new_var, end, quote, escaped_quote state = 'var' for char in challenge: if sys.version_info >= (3, 0): char = bytes([char]) if state == 'var': if char.isspace(): continue if char == b'=': state = 'value' else: var_name += char elif state == 'value': if char == b'"': state = 'quote' elif char == b',': if var_name: data[var_name.decode('utf-8')] = var_value var_name = b'' var_value = b'' state = 'var' else: var_value += char elif state == 'escaped': var_value += char elif state == 'quote': if char == b'\\': state = 'escaped' elif char == b'"': state = 'end' else: var_value += char else: if char == b',': if var_name: data[var_name.decode('utf-8')] = var_value var_name = b'' var_value = b'' state = 'var' else: var_value += char if var_name: data[var_name.decode('utf-8')] = var_value var_name = b'' var_value = b'' state = 'var' return data
def respond(self): data = { "username": quote(self.credentials["username"]), "authzid": quote(self.credentials["authzid"]), "realm": quote(self.credentials["realm"]), "nonce": quote(self.nonce), "cnonce": quote(self.cnonce), "nc": bytes("%08x" % self.nonce_count), "qop": self.qop, "digest-uri": quote(self.digest_uri()), "response": self.response(b"AUTHENTICATE"), "maxbuf": self.maxbuf, "charset": "utf-8", } resp = b"" for key, value in data.items(): if value and value != b'""': resp += b"," + bytes(key) + b"=" + bytes(value) return resp[1:]
def parse(self, challenge=b""): data = {} var_name = b"" var_value = b"" # States: var, new_var, end, quote, escaped_quote state = "var" for char in challenge: if sys.version_info >= (3, 0): char = bytes([char]) if state == "var": if char.isspace(): continue if char == b"=": state = "value" else: var_name += char elif state == "value": if char == b'"': state = "quote" elif char == b",": if var_name: data[var_name.decode("utf-8")] = var_value var_name = b"" var_value = b"" state = "var" else: var_value += char elif state == "escaped": var_value += char elif state == "quote": if char == b"\\": state = "escaped" elif char == b'"': state = "end" else: var_value += char else: if char == b",": if var_name: data[var_name.decode("utf-8")] = var_value var_name = b"" var_value = b"" state = "var" else: var_value += char if var_name: data[var_name.decode("utf-8")] = var_value var_name = b"" var_value = b"" state = "var" return data
def process(self, challenge=b''): if not challenge: return None username = self.credentials['username'] password = self.credentials['password'] mac = hmac.HMAC(key=password, digestmod=self.hash) mac.update(challenge) return username + b' ' + bytes(mac.hexdigest())
def process(self, challenge=b""): if not challenge: return None username = self.credentials["username"] password = self.credentials["password"] mac = hmac.HMAC(key=password, digestmod=self.hash) mac.update(challenge) return username + b" " + bytes(mac.hexdigest())
def A1(self): username = self.credentials["username"] password = self.credentials["password"] authzid = self.credentials["authzid"] realm = self.credentials["realm"] a1 = self.hash() a1.update(username + b":" + realm + b":" + password) a1 = a1.digest() a1 += b":" + self.nonce + b":" + self.cnonce if authzid: a1 += b":" + authzid return bytes(a1)
def A1(self): username = self.credentials['username'] password = self.credentials['password'] authzid = self.credentials['authzid'] realm = self.credentials['realm'] a1 = self.hash() a1.update(username + b':' + realm + b':' + password) a1 = a1.digest() a1 += b':' + self.nonce + b':' + self.cnonce if authzid: a1 += b':' + authzid return bytes(a1)
def process(self, challenge=b""): if challenge: values = {} for kv in challenge.split(b"&"): key, value = kv.split(b"=") values[key] = value resp_data = { b"method": values[b"method"], b"v": b"1.0", b"call_id": b"1.0", b"nonce": values[b"nonce"], b"access_token": self.credentials["access_token"], b"api_key": self.credentials["api_key"], } resp = "&".join(["%s=%s" % (k, v) for k, v in resp_data.items()]) return bytes(resp) return b""
def process(self, challenge=b''): if challenge: values = {} for kv in challenge.split(b'&'): key, value = kv.split(b'=') values[key] = value resp_data = { b'method': values[b'method'], b'v': b'1.0', b'call_id': b'1.0', b'nonce': values[b'nonce'], b'access_token': self.credentials['access_token'], b'api_key': self.credentials['api_key'] } resp = '&'.join(['%s=%s' % (k, v) for k, v in resp_data.items()]) return bytes(resp) return b''
def process(self, challenge=b""): if not challenge: if self.cnonce and self.nonce and self.nonce_count and self.qop: self.nonce_count += 1 return self.respond() return None data = self.parse(challenge) if "rspauth" in data: if data["rspauth"] != self.response(): raise SASLMutualAuthFailed() else: self.nonce_count = 1 self.cnonce = bytes("%s" % random.random())[2:] self.qops = data.get("qop", [b"auth"]) self.qop = b"auth" if "nonce" in data: self.nonce = data["nonce"] if "realm" in data and not self.credentials["realm"]: self.credentials["realm"] = data["realm"] return self.respond()
def process(self, challenge=b''): if not challenge: if self.cnonce and self.nonce and self.nonce_count and self.qop: self.nonce_count += 1 return self.respond() return None data = self.parse(challenge) if 'rspauth' in data: if data['rspauth'] != self.response(): raise SASLMutualAuthFailed() else: self.nonce_count = 1 self.cnonce = bytes('%s' % random.random())[2:] self.qops = data.get('qop', [b'auth']) self.qop = b'auth' if 'nonce' in data: self.nonce = data['nonce'] if 'realm' in data and not self.credentials['realm']: self.credentials['realm'] = data['realm'] return self.respond()
def A2(self, prefix=b""): a2 = prefix + b":" + self.digest_uri() if self.qop in (b"auth-int", b"auth-conf"): a2 += b":00000000000000000000000000000000" return bytes(a2)
def get_value(self): return base64.b64decode(bytes(self.xml.text))
def to_b64(data): return bytes(base64.b64encode(bytes(data))).decode('utf-8')
def from_b64(data): return bytes(base64.b64decode(bytes(data)))
def get_value(self): if not self['mechanism'] in self.plain_mechs: return base64.b64decode(bytes(self.xml.text)) else: return self.xml.text
def get_data(self): return base64.b64decode(bytes(self.xml.text))
def A2(self, prefix=b''): a2 = prefix + b':' + self.digest_uri() if self.qop in (b'auth-int', b'auth-conf'): a2 += b':00000000000000000000000000000000' return bytes(a2)
def get_binval(self): parent = self.parent() xml = parent.find('{%s}BINVAL' % self.namespace) if xml is not None: return base64.b64decode(bytes(xml.text)) return b''
def set_value(self, value): if value: self.xml.text = b64encode(bytes(value)) else: self.xml.text = ''
def set_value(self, values): if values: self.xml.text = bytes(base64.b64encode(values)).decode('utf-8') else: self.xml.text = '='
def get_value(self): if self.xml.text: return b64decode(bytes(self.xml.text)) return ''
def set_data(self, value): self.xml.text = bytes(base64.b64encode(value)).decode('utf-8')
def set_value(self, value): self.xml.text = '' if value: self.xml.text = b64encode(bytes(value))