def append_pool(msg):
    pool_id = msg['pool_id'].replace(' ', '')
    prefix = msg['prefix']
    with dbw() as conn:
        with conn.cursor() as crsr:
            bulk = []
            network = ip_network(prefix)
            size = network.num_addresses
            if size >= 65536:
                chunk = 65536
            else:
                chunk = size

            i = 1
            for ip in network:
                bulk.append('(uuid(), "%s", 0x%s)' % (
                    pool_id,
                    ip.packed.hex(),
                ))
                if i == chunk:
                    try:
                        crsr.execute('INSERT INTO calabiyau_ippool' +
                                     ' (id, pool_id, framedipaddress)' +
                                     ' VALUES' + ' %s' % ", ".join(bulk))
                        crsr.commit()
                    except SQLIntegrityError as e:
                        log.warning(e)
                    i = 1
                    bulk = []
                i += 1
Exemple #2
0
def post_processing(queue):
    while True:
        pkt = queue.get(queue)
        with MBClient('subscriber') as mb:
            mb.send(
                'radius_accounting', {
                    'attributes': encode_packet(pkt),
                    'datetime': str(datetime.utcnow())
                })
        with db() as dbro:
            with dbro.cursor() as crsr:
                client = pkt.get('NAS-IP-Address')[0]
                user = get_user(crsr, client, pkt.source[0],
                                pkt.get('User-Name')[0])
                if user:
                    status = pkt.get('Acct-Status-Type', [''])[0].lower()
                    if not user['static_ip4'] and user['pool_id']:
                        with dbw() as dbwr:
                            update_ip(dbwr, status, user, pkt)

                duplicate_to = g.app.config.get('radius',
                                                'duplicate',
                                                fallback=None)
                if duplicate_to:
                    with dbro.cursor() as crsr:
                        client = pkt.get('NAS-IP-Address')[0]
                        user = get_user(crsr, client, pkt.source[0],
                                        pkt.get('User-Name')[0])
                        if user:
                            pkt['Class'] = user['package'].encode('utf-8')
                            duplicates = duplicate_to.split(',')
                            for duplicate_to in duplicates:
                                duplicate_to = duplicate_to.strip()
                                duplicate(pkt.raw_packet, duplicate_to, 1813)
Exemple #3
0
def acct(msg):
    fr = parse_fr(msg.get('fr', ()))
    status = fr.get('Acct-Status-Type', 'start').lower()
    dt = utc(parse_datetime(msg.get('datetime', None)))
    diff = (now() - dt).total_seconds()

    if diff > 60:
        log.error('Processing radius accounting message older' +
                  ' than 60 seconds. Age(%s)' % diff)

    if not require_attributes('accounting', fr, [
            'User-Name', 'NAS-IP-Address', 'Acct-Status-Type',
            'Acct-Session-Id', 'Acct-Unique-Session-Id', 'Acct-Input-Octets64',
            'Acct-Output-Octets64'
    ]):
        return False

    with db() as conn:
        with dbw() as connw:
            user = get_user(conn, fr['NAS-IP-Address'], fr['User-Name'])
            if not user:
                log.debug("user '%s' not found" % (fr['User-Name'], ))
                return False

            input_octets, output_octets = do_acct(connw, fr, dt, user, status)
            usage(connw, fr, user, input_octets, output_octets, status)

            if not user['static_ip4'] and user['pool_id']:
                update_ip(connw, user, fr)

    return True
Exemple #4
0
def acct(msg):
    try:
        pkt = msg['attributes']
    except KeyError:
        return
    try:
        pkt = decode_packet(pkt)
    except Exception:
        return
    try:
        nas_session_id = pkt.get('Acct-Session-Id', [None])[0]
        unique_session_id = pkt.get('Acct-Unique-Session-Id')[0]
        status = pkt.get('Acct-Status-Type', [''])[0].lower()
        username = pkt.get('User-Name', [None])[0]
        client = pkt.get('Client-IP-Address')[0]
        nas = pkt.get('NAS-IP-Address', ['0.0.0.0'])[0]
    except IndexError:
        return True

    dt = utc(parse_datetime(msg.get('datetime', None)))
    diff = (now()-dt).total_seconds()

    if diff > 60:
        log.error('Processing radius accounting message older' +
                  ' than 60 seconds. Age(%s)' % diff)

    with db() as conn:
        with dbw() as connw:
            with conn.cursor() as crsr:
                user = get_user(crsr,
                                client,
                                nas,
                                username)
                crsr.commit()
                if not user:
                    log.debug("user '%s' not found"
                              % username)
                    return False

                input_octets, output_octets = do_acct(connw,
                                                      pkt,
                                                      client,
                                                      nas,
                                                      nas_session_id,
                                                      unique_session_id,
                                                      dt,
                                                      user,
                                                      status)
                usage(connw,
                      pkt,
                      client,
                      nas,
                      nas_session_id,
                      unique_session_id,
                      user,
                      input_octets,
                      output_octets,
                      status)

    return True
def purge_sessions():
    with dbw() as conn:
        with conn.cursor() as crsr:
            while True:
                log.info('Purging old stop sessions')
                crsr.execute("DELETE FROM calabiyau_session WHERE" +
                             " processed < (NOW() - INTERVAL 24 HOUR)" +
                             " AND accttype = 'stop'")
                crsr.commit()
                time.sleep(60)
def delete_pool(msg):
    pool_id = msg['pool_id']
    prefix = msg['prefix']
    with dbw() as conn:
        with conn.cursor() as crsr:
            network = ip_network(prefix)
            size = network.num_addresses
            start = network[0].packed
            end = network[size - 1].packed
            crsr.execute(
                'DELETE FROM calabiyau_ippool' +
                ' WHERE pool_id = "%s"' % pool_id +
                ' AND framedipaddress BETWEEN %s AND %s', (
                    start,
                    end,
                ))
            crsr.commit()
Exemple #7
0
def delete_pool(msg):
    log = MPLogger(__name__)

    pool_id = msg['pool_id']
    prefix = msg['prefix']
    with dbw() as conn:
        with conn.cursor() as crsr:
            for ip in ip_network(prefix):
                try:
                    crsr.execute(
                        'DELETE FROM calabiyau_ippool' +
                        ' WHERE pool_id = %s' + ' and framedipaddress = %s', (
                            pool_id,
                            str(ip),
                        ))
                except SQLIntegrityError as e:
                    log.warning(e)
            crsr.commit()
Exemple #8
0
def append_pool(msg):
    log = MPLogger(__name__)

    pool_id = msg['pool_id']
    prefix = msg['prefix']
    with dbw() as conn:
        with conn.cursor() as crsr:
            for ip in ip_network(prefix):
                try:
                    crsr.execute(
                        'INSERT INTO calabiyau_ippool' +
                        ' (id, pool_id, framedipaddress)' + ' VALUES' +
                        ' (uuid(), %s, %s)', (
                            pool_id,
                            str(ip),
                        ))
                except SQLIntegrityError as e:
                    log.warning(e)
            crsr.commit()
Exemple #9
0
    def auth(self, pkt, queue, debug):
        with db() as dbro:
            with dbro.cursor() as crsr:
                client = pkt.get('NAS-IP-Address')[0]
                user = get_user(crsr, client, pkt.source[0],
                                pkt.get('User-Name')[0])
                if user:
                    if not user['enabled']:
                        log.warning('Subscriber account disabled (%s)' %
                                    user['username'])
                        dbro.commit()
                        return
                else:
                    log.warning('User not found (%s)' %
                                pkt.get('User-Name')[0])
                    dbro.commit()
                    return

                if ('User-Password' in pkt):
                    if pkt['User-Password'][0] != user['password']:
                        # Check for Legacy MD5 hashed passwords.
                        hashed = md5(pkt['User-Password'][0].encode(
                            'utf-8')).hexdigest()
                        if str(hashed) != user['password']:
                            dbro.commit()
                            log.warning('Password mismatch (%s)' %
                                        user['username'])
                            return
                elif ('CHAP-Password' in pkt
                      and not validate_chap_password(pkt, user['password'])):
                    dbro.commit()
                    log.warning('Password mismatch (%s)' % user['username'])
                    return
                elif ('User-Password' not in pkt
                      and 'CHAP-Password' not in pkt):
                    dbro.commit()
                    log.warning('No password supplied (%s)' % user['username'])
                    return

                ctx = ctx_values[usage(crsr, user)]
                attributes = get_attributes(crsr, user, ctx)
                if ctx == 'deactivate-login' and not attributes:
                    return

                if (user['static_ip4'] or not user['simultaneous']):
                    if has_session(crsr, user):
                        log.warning('Subscriber duplicate session (%s)' %
                                    user['username'])
                        dbro.commit()
                        return
                    elif user['static_ip4']:
                        attributes['Framed-IP-Address'] = user['static_ip4']
                elif user['pool_id']:
                    with dbw() as dbwr:
                        ip = get_ip(dbwr, user)
                    if ip:
                        attributes['Framed-IP-Address'] = ip
                    else:
                        pool_name = get_pool_name(crsr, user)
                        log.critical("IP Pool Empty user '%s' pool '%s'" % (
                            user['username'],
                            pool_name,
                        ))
                        dbro.commit()
                        return

                dbro.commit()
        return (RAD_ACCESSACCEPT, attributes)