Пример #1
0
def create_subscriber_info(payload_: asn1.SkrAbonentInfo):
    oid = payload_['id']
    if oid == asn1.sorm_report_abonent_person:
        item, rest = ber_decode(payload_['data'], asn1.SkrAbonentPerson())
        return PersonInfo.create(item)
    if oid == asn1.sorm_report_abonent_organization:
        item, rest = ber_decode(payload_['data'],
                                asn1.SkrAbonentOrganization())
        return OrganizationInfo.create(item)
    raise exceptions.GeneralFault(
        f'unable to create subscriber info by the "{str(oid)}" OID')
Пример #2
0
 def create(payload_):
     item, rest = ber_decode(payload_, asn1.SkrReportedVoipIdentifier())
     ip_bytes = tools.get_optional_bytes(item['ip-address'])
     return ReportedVoipIdentifier(
         network.IPAddress(ip_bytes) if ip_bytes is not None else None,
         tools.get_optional_str(item['originator-name']),
         tools.get_optional_str(item['calling-number']))
Пример #3
0
def encode_decode(lm):
    """Simulate transmission over the network"""
    raw = ber_encode(lm)
    response, raw = ber_decode(raw, asn1Spec=rfc4511.LDAPMessage())
    if raw:
        raise Exception('Unexpected leftover bits')
    return response
Пример #4
0
 def read_sent(self):
     """Read the first sent message in the queue"""
     lm, raw = ber_decode(self._incoming_queue.popleft(),
                          asn1Spec=rfc4511.LDAPMessage())
     if raw:
         raise Exception('unexpected leftover bits')
     return lm
Пример #5
0
 def create(payload_):
     item, rest = ber_decode(payload_, asn1.SkrReportedCdmaIdentifier())
     return ReportedCdmaIdentifier(str(item['directory-number']),
                                   str(item['imsi']),
                                   tools.get_optional_str(item['esn']),
                                   tools.get_optional_str(item['min']),
                                   tools.get_optional_str(item['icc']))
Пример #6
0
 def handle(self, ctrl_value):
     real_ctrl_value, raw = ber_decode(ctrl_value,
                                       asn1Spec=RealSearchControlValue())
     if raw:
         raise LDAPError(
             'Unexpected leftover bits in response control value')
     cookie = get_string_component(real_ctrl_value, 'cookie')
     return cookie
Пример #7
0
def create_typed_message(raw_message_):
    payload_id = str(raw_message_['id'])
    descriptor = message_descriptors.get(payload_id, None)
    if descriptor is None:
        raise exceptions.GeneralFault(
            'unable to recognize message with id: "{payload_id}"')
    payload, rest = ber_decode(raw_message_['data'],
                               descriptor.descriptor_reference())
    return descriptor.creator(raw_message_, payload)
Пример #8
0
 def data_received(self, data):
     self._buffer += data
     try:
         message, self._buffer = ber_decode(self._buffer)
     except SubstrateUnderrunError:
         pass
     else:
         message_id = int(message[0])
         self._pending_messages[message_id].set_result(message[1])
         del self._pending_messages[message_id]
Пример #9
0
 def create(raw_message_, message_payload_, report_payload_):
     sequence_of, rest = ber_decode(bytes(report_payload_),
                                    asn1.SkrReportServiceData())
     records = tools.sequence_of_to_list(sequence_of, Service.create)
     return ServiceReport(
         raw_message_['version'], raw_message_['message-id'],
         raw_message_['message-time'],
         tools.get_optional_str(raw_message_['operator-name']),
         raw_message_['id'], int(message_payload_['request-id']),
         int(message_payload_['task-id']),
         int(message_payload_['total-blocks-number']),
         int(message_payload_['block-number']), records)
Пример #10
0
def parse_ed_pubkey(public_key):
    try:
        public_key, _ = ber_decode(public_key, asn1Spec=EdPublicKey())
    except Exception:
        raise ParseError("Not a BER encoded Edwards curve public key")

    if not public_key["key_info"]["key_type"] == univ.ObjectIdentifier("1.3.101.112"):
        raise ParseError("Not a BER encoded Edwards curve public key")

    public_key = bytes(public_key["public_key"].asOctets())

    return public_key
Пример #11
0
 def recv_messages(self, want_message_id):
     while self._outgoing_queue:
         raw = self._outgoing_queue.popleft()
         lm, raw = ber_decode(raw, asn1Spec=rfc4511.LDAPMessage())
         if raw:
             raise Exception('Unexpected leftover bits')
         have_message_id = lm.getComponentByName('messageID')
         if have_message_id != want_message_id:
             raise Exception(
                 'Unexpected message ID in mock queue (have={0} want={1})'.
                 format(have_message_id, want_message_id))
         yield lm
     raise Exception('No messages in mock queue')
Пример #12
0
 def create(payload_):
     item, rest = ber_decode(payload_,
                             asn1.SkrReportedDataNetworkIdentifier())
     return ReportedDataNetworkIdentifier(
         tools.get_optional_value(item['user-equipment'],
                                  network.DataNetworkEquipment.create),
         tools.get_optional_str(item['login']),
         tools.get_optional_ip_address(item['ip-address']),
         tools.get_optional_str(item['e-mail']),
         tools.get_optional_str(item['pin']),
         tools.get_optional_str(item['phone-number']),
         tools.get_optional_str(item['user-domain']),
         tools.get_optional_str(item['reserved']),
         tools.get_optional_value(item['ip-mask'], network.IPMask.create))
Пример #13
0
    async def run(self):
        """Handle the client's requests forever"""

        self.log.debug('Started new client')
        buffer = b''
        while True:
            try:
                data = await self.reader.read(self.RECV_BUFFER)
                if not data:
                    self.log.info('Client has exited')
                    return
                buffer += data
                while len(buffer) > 0:
                    _request, buffer = ber_decode(
                        buffer, asn1Spec=rfc4511.LDAPMessage())
                    req = Request(_request)

                    self.log.info(
                        f'Received message_id={req.id} operation={req.operation}'
                    )

                    if req.operation == 'unbindRequest':
                        self.authenticated_name = None
                        self.log.info('Client has unbound')
                        return
                    elif req.operation == 'abandonRequest':
                        # As of right now I can't fathom a way to actually get abandon to work with asyncio
                        #
                        # Unfortunately RFC4511 specifies that interrupting result entries is the one thing we MUST
                        # do, but it also says clients MUST NOT care if the abandon worked, so ... ?
                        self.log.warning('Received abandon request - ignoring')
                    else:
                        await self._respond_to_request(req)
            except SubstrateUnderrunError:
                continue
            except (PyAsn1Error, DisconnectionProtocolError) as e:
                self.log.exception('Caught fatal disconnect error', e)
                xr = ldap_result(rfc4511.ExtendedResponse,
                                 'protocolError',
                                 message=str(e))
                xr.setComponentByName('responseName',
                                      constants.OID_NOTICE_OF_DISCONNECTION)
                op = protocol_op('extendedResp', xr)
                lm = pack(0, op)
                await self.send(lm)
                return
Пример #14
0
def parse_ec_pubkey(public_key):
    try:
        public_key, _ = ber_decode(public_key, asn1Spec=EcPublicKey())
    except Exception:
        raise ParseError("Not a BER encoded named elliptic curve public key")

    if not public_key["key_info"]["key_type"] == univ.ObjectIdentifier(
            "1.2.840.10045.2.1"):
        raise ParseError("Not a BER encoded named elliptic curve public key")
    curve_identifier = public_key["key_info"]["curve_name"]
    curve_name = get_curve_name_by_identifier(curve_identifier)

    if curve_name is None:
        raise NotSupported(
            "Unsupported named elliptic curve: {}".format(curve_identifier))

    try:
        public_key = bytes(public_key["public_key"].asOctets())
    except:
        raise ParseError("Not a BER encoded named elliptic curve public key")

    return curve_name, public_key
Пример #15
0
    def wait_for_message(self):
        def append_data(data_):
            self.undecoded_data = self.undecoded_data + data_

        raw_message = None
        while True:
            if self.stop_message_dispatching_event.is_set():
                return
            self.receive_data(append_data)
            try:
                raw_message, rest = ber_decode(self.undecoded_data,
                                               asn1.SkrMessage())
                self.undecoded_data = rest
                break
            except asn1_error.SubstrateUnderrunError:
                continue

        message = base.create_typed_message(raw_message)
        self.lg.diagnostic(
            f'The {message.__class__.__name__} message has been received ' +
            f'on the channel {self.get_full_name()} ...')
        self.lg.debug(f'The message body: {message}')
        return message
Пример #16
0
    def recv_messages(self, want_message_id):
        """Iterate all messages with ``want_message_id`` being sent by the server.

        :param int want_message_id: The desired message ID.
        :return: An iterator over :class:`.rfc4511.LDAPMessage`.
        """
        flush_queue = True
        raw = b''
        while True:
            if flush_queue:
                if want_message_id in self._message_queues:
                    q = self._message_queues[want_message_id]
                    while True:
                        if len(q) == 0:
                            break
                        obj = q.popleft()
                        if len(q) == 0:
                            del self._message_queues[want_message_id]
                        yield obj
            else:
                flush_queue = True
            if want_message_id in self.abandoned_mids:
                raise StopIteration()
            try:
                newraw = self._sock.recv(LDAPSocket.RECV_BUFFER)
                if self._has_sasl_client():
                    newraw = self._sasl_client.unwrap(newraw)
                raw += newraw
                while len(raw) > 0:
                    response, raw = ber_decode(raw, asn1Spec=LDAPMessage())
                    have_message_id = response.getComponentByName('messageID')
                    if want_message_id == have_message_id:
                        yield response
                    elif have_message_id == 0:
                        msg = 'Received unsolicited message (default message - should never be seen)'
                        try:
                            mid, xr, ctrls = unpack('extendedResp', response)
                            res_code = xr.getComponentByName('resultCode')
                            xr_oid = six.text_type(
                                xr.getComponentByName('responseName'))
                            if xr_oid == LDAPSocket.OID_DISCONNECTION_NOTICE:
                                mtype = 'Notice of Disconnection'
                            else:
                                mtype = 'Unhandled ({0})'.format(xr_oid)
                            diag = xr.getComponentByName('diagnosticMessage')
                            msg = 'Got unsolicited message: {0}: {1}: {2}'.format(
                                mtype, res_code, diag)
                            if res_code == ResultCode('protocolError'):
                                msg += (
                                    ' (This may indicate an incompatability between laurelin-ldap and your server '
                                    'distribution)')
                            elif res_code == ResultCode(
                                    'strongerAuthRequired'):
                                # this is a direct quote from RFC 4511 sec 4.4.1
                                msg += (
                                    ' (The server has detected that an established security association between the'
                                    'client and server has unexpectedly failed or been compromised)'
                                )
                        except UnexpectedResponseType:
                            msg = 'Unhandled unsolicited message from server'
                        finally:
                            raise LDAPUnsolicitedMessage(response, msg)
                    else:
                        if have_message_id not in self._message_queues:
                            self._message_queues[have_message_id] = deque()
                        self._message_queues[have_message_id].append(response)
            except SubstrateUnderrunError:
                flush_queue = False
                continue
Пример #17
0
 def create(payload_):
     item, rest = ber_decode(payload_, asn1.SkrReportedPstnIdentifier())
     return ReportedPstnIdentifier(
         str(item['directory-number']),
         tools.get_optional_str(item['internal-number']))
Пример #18
0
    def recv_messages(self, want_message_id):
        """Iterate all messages with ``want_message_id`` being sent by the server.

        :param int want_message_id: The desired message ID.
        :return: An iterator over :class:`.rfc4511.LDAPMessage`.
        """
        flush_queue = True
        raw = b''
        while True:
            if flush_queue:
                if want_message_id in self._message_queues:
                    q = self._message_queues[want_message_id]
                    while True:
                        if len(q) == 0:
                            break
                        obj = q.popleft()
                        if len(q) == 0:
                            del self._message_queues[want_message_id]
                        yield obj
            else:
                flush_queue = True
            if want_message_id in self.abandoned_mids:
                return
            try:
                newraw = self._sock.recv(LDAPSocket.RECV_BUFFER)
                if self._has_sasl_client():
                    newraw = self._sasl_client.unwrap(newraw)
                raw += newraw
                while len(raw) > 0:
                    response, raw = ber_decode(raw, asn1Spec=LDAPMessage())
                    have_message_id = response.getComponentByName('messageID')
                    if want_message_id == have_message_id:
                        yield response
                    elif have_message_id == 0:
                        msg = 'Received unsolicited message (default message - should never be seen)'
                        try:
                            mid, xr, ctrls = unpack('extendedResp', response)
                            res_code = xr.getComponentByName('resultCode')
                            xr_oid = six.text_type(xr.getComponentByName('responseName'))
                            if xr_oid == LDAPSocket.OID_DISCONNECTION_NOTICE:
                                mtype = 'Notice of Disconnection'
                            else:
                                mtype = 'Unhandled ({0})'.format(xr_oid)
                            diag = xr.getComponentByName('diagnosticMessage')
                            msg = 'Got unsolicited message: {0}: {1}: {2}'.format(mtype, res_code, diag)
                            if res_code == ResultCode('protocolError'):
                                msg += (' (This may indicate an incompatability between laurelin-ldap and your server '
                                        'distribution)')
                            elif res_code == ResultCode('strongerAuthRequired'):
                                # this is a direct quote from RFC 4511 sec 4.4.1
                                msg += (' (The server has detected that an established security association between the'
                                        ' client and server has unexpectedly failed or been compromised)')
                        except UnexpectedResponseType:
                            msg = 'Unhandled unsolicited message from server'
                        finally:
                            raise LDAPUnsolicitedMessage(response, msg)
                    else:
                        if have_message_id not in self._message_queues:
                            self._message_queues[have_message_id] = deque()
                        self._message_queues[have_message_id].append(response)
            except SubstrateUnderrunError:
                flush_queue = False
                continue
Пример #19
0
 def handle(self, ctrl_value):
     real_ctrl_value, raw = ber_decode(ctrl_value, asn1Spec=RealSearchControlValue())
     if raw:
         raise LDAPError('Unexpected leftover bits in response control value')
     cookie = get_string_component(real_ctrl_value, 'cookie')
     return cookie