Authentifizierung auf Host- und Userbasis

Sockets, TCP/IP, (XML-)RPC und ähnliche Themen gehören in dieses Forum
joerg
User
Beiträge: 188
Registriert: Samstag 17. August 2002, 17:48
Wohnort: Berlin
Kontaktdaten:

Authentifizierung auf Host- und Userbasis

Beitragvon joerg » Sonntag 15. Dezember 2002, 14:31

Hallo,
für eine Serveranwendung brauche ich einen Check, von welchen IPs zugegriffen werden darf und eine Benutzer/Passwort-Authentifizierung. Folgenden Code dazu habe ich mir ausgedacht, ein kleines Testprogramm ist dabei.

Code: Alles auswählen

#!/usr/bin/env python

import shelve, time, warnings
try:
    import crypt
except:
    crypt = None

try:
    # Options.py may not be present...
    from Options import userAuthFailSleep
except:
    userAuthFailSleep = 3.0 # prevent dictionary attacks

# just for convenience
ALLOW = 1
DENY = 0

class HostAuth:
    """IPv4 address matching with allow/deny rules from database"""
    def __init__(self, hostFile='.hosts'):
        self.db = shelve.open(hostFile)
    def check(self, ip):
        """check IP against rules"""
        parts = ip.split('.')
        allowed = self.db.get('_DEFAULT_', DENY)
        for i in range(len(parts)):
            mask = '.'.join(parts[:i+1])
            if self.db.has_key(mask):
                allowed = self.db[mask]
        return allowed
    def addRule(self, ip, allowed):
        self.db[ip] = allowed
    def delRule(self, ip):
        del self.db[ip]
    def rules(self):
        dct = {}
        dct.update(self.db)
        return dct

class UserAuth:
    """User/password authentification with database containing
    (encrypted) passwords (UNIX-like)"""
    def __init__(self, userFile='.password'):
        self.db = shelve.open(userFile)
        if crypt:
            self.crypt = crypt.crypt
        else:
            self.crypt = lambda x,y: x
            warnings.warn('crypt module not found - using cleartext passwords!')
    def check(self, username, password):
        ans = self.db.has_key(username) and \
               self.db[username] == self.crypt(password, password[:2])
        if not ans:
            time.sleep(userAuthFailSleep)
        return ans
    def addUser(self, username, password):
        self.db[username] = self.crypt(password, password[:2])
    def delUser(self, username):
        del self.db[username]
    def users(self):
        return self.db.keys()


if __name__ == '__main__':
    ha = HostAuth('.hosts.test')
    ha.addRule('_DEFAULT_', DENY)
    ha.addRule('127.0.0', ALLOW)
    ha.addRule('192.168.42', ALLOW)
    ha.addRule('192.168.42.6', DENY)
    # should give 1, 1, 0
    print ha.check('127.0.0.1'), ha.check('192.168.42.3'), ha.check('192.168.42.6')
    #print ha.rules()

    ua = UserAuth('.password.test')
    ua.addUser('admin', 'istrator')
    ua.addUser('test', 'piZZa')
    # should give 0, 1 after 3 seconds delay
    print ua.check('test', 'SuPPe'), ua.check('admin', 'istrator')
    #print ua.users()

Ich hoffe, der Code ist relativ selbsterklärend, er sollte überall laufen. Die Passort-Datenbank und die Datenbank der IP-Regeln sind shelves. Der Paßwort-Mechanismus ist an UNIX angelehnt. Bei den IP-Regeln kann man einfach einzelne IPs oder Bereiche sperren oder freigeben.

Da ich kein Sicherheitsfachmann bin, wollte ich mal weitere Meinungen einholen, ob da große potentielle Lücken drin sind. Wo kann man den Code noch sicherer gestalten?

Und gibt es unter Nicht-UNIX-Plattformen einen Ersatz für crypt.crypt()?

Danke!
Jörg
RicmanX
User
Beiträge: 69
Registriert: Donnerstag 29. August 2002, 17:10
Wohnort: Erfurt
Kontaktdaten:

Beitragvon RicmanX » Sonntag 15. Dezember 2002, 15:09

Die beste Sicherung, ist immer eine nicht reversible (umkehrbare).

Am besten du nimmst das Modul md5 und speicherst die PWs so. Beim einloggen wandelst du die PWs genauso um, und überprüfst auf Gleichheit.
joerg
User
Beiträge: 188
Registriert: Samstag 17. August 2002, 17:48
Wohnort: Berlin
Kontaktdaten:

Beitragvon joerg » Sonntag 15. Dezember 2002, 15:57

RicmanX hat geschrieben:Die beste Sicherung, ist immer eine nicht reversible (umkehrbare).

Genau so wollte ich es machen. crypt ist IMO genau eine solche Einbahnstraßenverschlüsselung. Aber ich werde mir md5 mal ansehen, wenn das Modul plattformübergreifend verfügbar ist, wäre mir schon weiter geholfen.
Danke!
Jörg
joerg
User
Beiträge: 188
Registriert: Samstag 17. August 2002, 17:48
Wohnort: Berlin
Kontaktdaten:

Beitragvon joerg » Sonntag 15. Dezember 2002, 18:28

Bei der Doku zu md5 habe ich gelesen, daß sha als noch sicherer angesehen wird. Also habe ich das crypt erstmal durch sha ersetzt.
Sind denn md5 und sha bei python auf verschiedenen Plattformen standardmäßig dabei?

Jörg

Wer ist online?

Mitglieder in diesem Forum: 0 Mitglieder