Replace (unmaintained py2-only) yubiserve with "yubikeyedup", a rewrite.
Note, while it is broadly compatible with the most common use of yubiserve it has its limits: it supports only sqlite3 (using the same schema as before) not other databases, and it only supports HTTP internally, if you require HTTPS then you will need to use a proxy (e.g. relayd or nginx). It no longer uses a configuration file, only command line arguments.
This commit is contained in:
parent
950bbfcaf8
commit
8fe8557fa6
|
@ -1,11 +1,11 @@
|
|||
# $OpenBSD: Makefile,v 1.1238 2021/03/23 08:26:23 sebastia Exp $
|
||||
# $OpenBSD: Makefile,v 1.1239 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
COMMENT = exceptions to pkg_add rules
|
||||
CATEGORIES = devel databases
|
||||
DISTFILES =
|
||||
|
||||
# API.rev
|
||||
PKGNAME = quirks-3.626
|
||||
PKGNAME = quirks-3.627
|
||||
PKG_ARCH = *
|
||||
MAINTAINER = Marc Espie <espie@openbsd.org>
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#! /usr/bin/perl
|
||||
|
||||
# ex:ts=8 sw=4:
|
||||
# $OpenBSD: Quirks.pm,v 1.1252 2021/03/23 08:26:23 sebastia Exp $
|
||||
# $OpenBSD: Quirks.pm,v 1.1253 2021/03/29 12:08:39 sthen Exp $
|
||||
#
|
||||
# Copyright (c) 2009 Marc Espie <espie@openbsd.org>
|
||||
#
|
||||
|
@ -619,6 +619,7 @@ my $stem_extensions = {
|
|||
'py-axolotl' => 'py3-axolotl',
|
||||
'py-protobuf' => 'py3-protobuf',
|
||||
'py-http_ece' => 'py3-http_ece',
|
||||
'yubiserve' => 'yubikeyedup',
|
||||
};
|
||||
|
||||
my $obsolete_reason = {
|
||||
|
|
|
@ -1,54 +1,34 @@
|
|||
# $OpenBSD: Makefile,v 1.22 2021/03/14 11:47:04 sthen Exp $
|
||||
# $OpenBSD: Makefile,v 1.23 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
COMMENT= standalone Yubikey and OATH/HOTP validation server
|
||||
DISTNAME= yubico-yubiserve-3.1
|
||||
REVISION= 14
|
||||
EXTRACT_SUFX= .zip
|
||||
UNZIP= unzip -a
|
||||
PKGNAME= ${DISTNAME:S/yubico-//}
|
||||
COMMENT= standalone Yubikey validation server
|
||||
|
||||
GH_ACCOUNT= scumjr
|
||||
GH_PROJECT= yubikeyedup
|
||||
GH_COMMIT= d5044d3fdc10cc59a5213efd53e0f80b2a1096f9
|
||||
DISTNAME= yubikeyedup-0.20201226
|
||||
|
||||
CATEGORIES= security www
|
||||
|
||||
HOMEPAGE= https://code.google.com/p/yubico-yubiserve/
|
||||
|
||||
MAINTAINER= Stuart Henderson <stu.ports@spacehopper.org>
|
||||
|
||||
# GPLv3
|
||||
PERMIT_PACKAGE= Yes
|
||||
|
||||
MASTER_SITES= ${MASTER_SITE_GOOGLECODE:=yubico-yubiserve/}
|
||||
|
||||
MODULES= lang/python
|
||||
MODPY_VERSION = ${MODPY_DEFAULT_VERSION_2}
|
||||
BUILD_DEPENDS= databases/sqlite3
|
||||
RUN_DEPENDS= security/py-cryptodome${MODPY_FLAVOR} \
|
||||
security/py-openssl${MODPY_FLAVOR}
|
||||
MODPY_SETUPTOOLS= Yes
|
||||
|
||||
RUN_DEPENDS= security/py-cryptodome${MODPY_FLAVOR}
|
||||
|
||||
NO_BUILD= Yes
|
||||
NO_TEST= Yes
|
||||
|
||||
PKG_ARCH= *
|
||||
WRKDIST= ${WRKDIR}/yubico-yubiserve
|
||||
|
||||
MODPY_ADJ_FILES= yubiserve.py dbconf.py
|
||||
|
||||
pre-patch:
|
||||
perl -pi -e 's,\? ,\t,g' ${WRKSRC}/dbconf.py
|
||||
echo >> ${WRKSRC}/yubiserve.py
|
||||
mv ${WRKSRC}/src ${WRKSRC}/yubikeyedup
|
||||
mv ${WRKSRC}/tools ${WRKSRC}/yubikeyedup/tools
|
||||
touch ${WRKSRC}/yubikeyedup/{,tools}/__init__.py
|
||||
|
||||
do-configure:
|
||||
@cd ${WRKSRC}; ${SUBST_CMD} -m 555 -c yubiserve.py yubiserve \
|
||||
dbconf.py yubiserve-dbconf
|
||||
cd ${WRKSRC}; sqlite3 yubikeys.sqlite3 < src/dump.sqlite
|
||||
|
||||
do-install:
|
||||
${INSTALL_DATA_DIR} ${PREFIX}/share/doc/yubiserve \
|
||||
${PREFIX}/share/examples/yubiserve
|
||||
cd ${WRKSRC}; ${INSTALL_DATA} LICENSE README \
|
||||
src/* ${PREFIX}/share/doc/yubiserve; \
|
||||
${INSTALL_DATA} yubiserve.cfg yubikeys.sqlite3 \
|
||||
${PREFIX}/share/examples/yubiserve; \
|
||||
${INSTALL_SCRIPT} yubiserve-dbconf ${PREFIX}/bin/yubiserve-dbconf; \
|
||||
${INSTALL_SCRIPT} yubiserve ${PREFIX}/sbin/yubiserve
|
||||
post-install:
|
||||
${INSTALL_DATA_DIR} ${PREFIX}/share/doc/yubikeyedup
|
||||
${INSTALL_DATA} ${WRKSRC}/{LICENSE,README.rst} \
|
||||
${PREFIX}/share/doc/yubikeyedup
|
||||
|
||||
.include <bsd.port.mk>
|
||||
|
|
|
@ -1,2 +1,2 @@
|
|||
SHA256 (yubico-yubiserve-3.1.zip) = pE79hfnIvKbwWkvBuJrYChiQwl8Wbg3T+WNj5NrB1wY=
|
||||
SIZE (yubico-yubiserve-3.1.zip) = 52856
|
||||
SHA256 (yubikeyedup-0.20201226-d5044d3f.tar.gz) = 90Q4oHSOt8RoxKFYJgqlyg4B8vILNJef5hq5UWAUrFI=
|
||||
SIZE (yubikeyedup-0.20201226-d5044d3f.tar.gz) = 25412
|
||||
|
|
|
@ -1,24 +0,0 @@
|
|||
$OpenBSD: patch-README,v 1.1.1.1 2012/07/18 08:25:07 sthen Exp $
|
||||
|
||||
sqlite3 support and doc fix from upstream
|
||||
http://code.google.com/p/yubico-yubiserve/source/list r39, r45
|
||||
|
||||
--- README.orig Wed Jul 18 01:16:24 2012
|
||||
+++ README Wed Jul 18 01:16:13 2012
|
||||
@@ -23,6 +23,7 @@ Under Debian, you can run:
|
||||
apt-get install python python-crypto python-openssl
|
||||
If you want to add the sqlite support, you should run:
|
||||
apt-get install python-sqlite
|
||||
+sqlite3 is also supported, which is included with python in RHEL6.
|
||||
Or, if you want to add the mysql support, you should run:
|
||||
apt-get install python-mysqldb
|
||||
If you chosen the mysql support, you must create a database and create the
|
||||
@@ -115,7 +116,7 @@ t=2010-11-20T23:54:35
|
||||
h=
|
||||
|
||||
As you can see, the 'h' parameter is not set, and this is because we didn't use
|
||||
-the signature through API Key. To use it, just add the 'key=<api key id>'
|
||||
+the signature through API Key. To use it, just add the 'id=<api key id>'
|
||||
parameter we had when we added the API Key.
|
||||
ex.: http://192.168.0.1:8000/wsapi/2.0/verify?otp=vvnjbbkvjbcnhiretjvjfebbrdgrjjchdhtbderrdbhj&id=1
|
||||
This time the response will be like:
|
|
@ -1,273 +0,0 @@
|
|||
$OpenBSD: patch-dbconf_py,v 1.1.1.1 2012/07/18 08:25:07 sthen Exp $
|
||||
|
||||
sqlite3 support from http://code.google.com/p/yubico-yubiserve/source/list r39
|
||||
|
||||
--- dbconf.py.orig Wed Jul 18 01:16:24 2012
|
||||
+++ dbconf.py Wed Jul 18 01:04:51 2012
|
||||
@@ -1,4 +1,4 @@
|
||||
-#!/usr/bin/python
|
||||
+#!${MODPY_BIN}
|
||||
import time, random, re, os
|
||||
from sys import argv
|
||||
try:
|
||||
@@ -6,12 +6,16 @@ try:
|
||||
except ImportError:
|
||||
pass
|
||||
try:
|
||||
+ import sqlite3
|
||||
+except ImportError:
|
||||
+ pass
|
||||
+try:
|
||||
import sqlite
|
||||
except ImportError:
|
||||
pass
|
||||
|
||||
def parseConfigFile(): # Originally I wrote this function to parse PHP configuration files!
|
||||
- config = open(os.path.dirname(os.path.realpath(__file__)) + '/yubiserve.cfg', 'r').read().splitlines()
|
||||
+ config = open('${SYSCONFDIR}/yubiserve/yubiserve.cfg', 'r').read().splitlines()
|
||||
keys = {}
|
||||
for line in config:
|
||||
match = re.search('(.*?)=(.*);', line)
|
||||
@@ -54,14 +58,15 @@ if config['yubiDB'] == 'mysql' and (config['yubiMySQLH
|
||||
print "Cannot continue without any MySQL configuration.\nPlease read README.\n\n"
|
||||
quit()
|
||||
try:
|
||||
- if config['yubiDB'] == 'sqlite':
|
||||
- con = sqlite.connect(os.path.dirname(os.path.realpath(__file__)) + '/yubikeys.sqlite')
|
||||
+ if config['yubiDB'] == 'sqlite3':
|
||||
+ con = sqlite3.connect('/var/db/yubiserve/yubikeys.sqlite3')
|
||||
+ elif config['yubiDB'] == 'sqlite':
|
||||
+ con = sqlite.connect('/var/db/yubiserve/yubikeys.sqlite')
|
||||
elif config['yubiDB'] == 'mysql':
|
||||
con = MySQLdb.connect(host=config['yubiMySQLHost'], user=config['yubiMySQLUser'], passwd=config['yubiMySQLPass'], db=config['yubiMySQLName'])
|
||||
except:
|
||||
print "There's a problem with the database!\n"
|
||||
cur = con.cursor()
|
||||
-
|
||||
if (len(argv)<2):
|
||||
print ' == YubiServe Key Management Tool 2.0 ==\n'
|
||||
print ' -ya <nickname> <publicid> <secretid> <aeskey>\tAdd a new Yubikey'
|
||||
@@ -84,13 +89,15 @@ else:
|
||||
if argv[1][0:2] == '-y': # Yubico Yubikey
|
||||
if (argv[1][2] == 'd') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print 'Key not found.'
|
||||
else:
|
||||
- cur.execute("SELECT * FROM yubikeys WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
- if (cur.rowcount == 1):
|
||||
- cur.execute("UPDATE yubikeys SET active = '1' WHERE nickname = '" + nickname + "'")
|
||||
+ cur.execute("SELECT count(nickname) FROM yubikeys WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if rowcount[0]:
|
||||
+ cur.execute("UPDATE yubikeys SET active = '0' WHERE nickname = '" + nickname + "'")
|
||||
print "Key '" + nickname + "' disabled."
|
||||
con.commit()
|
||||
else:
|
||||
@@ -98,12 +105,14 @@ else:
|
||||
|
||||
elif (argv[1][2] == 'e') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print 'Key not found.'
|
||||
else:
|
||||
- cur.execute("SELECT * FROM yubikeys WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
- if (cur.rowcount == 1):
|
||||
+ cur.execute("SELECT count(nickname) FROM yubikeys WHERE nickname = '" + nickname + "' AND active = '0'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if rowcount[0]:
|
||||
cur.execute("UPDATE yubikeys SET active = '1' WHERE nickname = '" + nickname + "'")
|
||||
print "Key '" + nickname + "' enabled."
|
||||
con.commit()
|
||||
@@ -111,8 +120,9 @@ else:
|
||||
print 'Key is already enabled.'
|
||||
elif (argv[1][2] == 'k') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print 'Key not found.'
|
||||
else:
|
||||
cur.execute("DELETE FROM yubikeys WHERE nickname = '" + nickname + "'")
|
||||
@@ -121,8 +131,9 @@ else:
|
||||
elif (argv[1][2] == 'a') and (len(argv)>4):
|
||||
nickname = re.escape(argv[2])
|
||||
if ((len(argv[2])<=16) and (len(argv[3]) <= 16) and (len(argv[4]) <= 12) and (len(argv[5])<=32)):
|
||||
- cur.execute("SELECT * FROM yubikeys WHERE nickname = '" + argv[2] + "' OR publicname = '" + argv[3] + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM yubikeys WHERE nickname = '" + argv[2] + "' OR publicname = '" + argv[3] + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
cur.execute("INSERT INTO yubikeys VALUES ('" + argv[2] + "', '" + argv[3] + "', '" + time.strftime("%Y-%m-%dT%H:%M:%SZ", time.gmtime()) + "', '" + argv[4] + "', '" + argv[5] + "', 1, 1, 1)")
|
||||
con.commit()
|
||||
print "Key '" + argv[2] + "' added to database."
|
||||
@@ -133,13 +144,14 @@ else:
|
||||
print 'Secretid must be 12 characters max, aeskey must be 32 characters max.\n'
|
||||
quit()
|
||||
elif (argv[1][2] == 'l'):
|
||||
- cur.execute('SELECT nickname, publicname, active FROM yubikeys')
|
||||
- if cur.rowcount != 0:
|
||||
- print " " + str(cur.rowcount) + " keys into database:"
|
||||
+ cur.execute('SELECT count(nickname) FROM yubikeys')
|
||||
+ rowcount = cur.fetchone();
|
||||
+ print " %s keys into database:" % (rowcount[0])
|
||||
+ if rowcount[0]:
|
||||
+ cur.execute('SELECT nickname, publicname, active FROM yubikeys')
|
||||
print '[Nickname]\t\t>> [PublicID]'
|
||||
- for i in range(0, cur.rowcount):
|
||||
- (nickname, publicname, active) = cur.fetchone()
|
||||
- print ' ' + nickname + ' ' * (23-len(nickname)) + ">> " + publicname + ' ' * (21-len(publicname)) + ">> " + active
|
||||
+ for (nickname, publicname, active) in cur:
|
||||
+ print '%-23s >> %-21s >> %s ' % (nickname, publicname, active)
|
||||
print ''
|
||||
else:
|
||||
print 'No keys in database\n'
|
||||
@@ -148,12 +160,14 @@ else:
|
||||
elif argv[1][0:2] == '-h':
|
||||
if (argv[1][2] == 'd') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print 'Key not found.'
|
||||
else:
|
||||
- cur.execute("SELECT * FROM oathtokens WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
- if (cur.rowcount == 1):
|
||||
+ cur.execute("SELECT count(nickname) FROM oathtokens WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if rowcount[0]:
|
||||
cur.execute("UPDATE oathtokens SET active = '1' WHERE nickname = '" + nickname + "'")
|
||||
print "Key '" + nickname + "' disabled."
|
||||
con.commit()
|
||||
@@ -162,12 +176,14 @@ else:
|
||||
|
||||
elif (argv[1][2] == 'e') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print 'Key not found.'
|
||||
else:
|
||||
- cur.execute("SELECT * FROM oathtokens WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
- if (cur.rowcount == 1):
|
||||
+ cur.execute("SELECT count(nickname) FROM oathtokens WHERE nickname = '" + nickname + "' AND active = '1'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if rowcount[0]:
|
||||
cur.execute("UPDATE oathtokens SET active = '1' WHERE nickname = '" + nickname + "'")
|
||||
print "Key '" + nickname + "' enabled."
|
||||
con.commit()
|
||||
@@ -175,8 +191,9 @@ else:
|
||||
print 'Key is already enabled.'
|
||||
elif (argv[1][2] == 'k') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print 'Key not found.'
|
||||
else:
|
||||
cur.execute("DELETE FROM oathtokens WHERE nickname = '" + nickname + "'")
|
||||
@@ -185,8 +202,9 @@ else:
|
||||
elif (argv[1][2] == 'a') and (len(argv)>3):
|
||||
nickname = re.escape(argv[2])
|
||||
if (len(argv[2])<=16) and (len(argv[3]) <= 16) and (len(argv[4]) <= 40):
|
||||
- cur.execute("SELECT * FROM oathtokens WHERE nickname = '" + argv[2] + "' OR publicname = '" + argv[3] + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM oathtokens WHERE nickname = '" + argv[2] + "' OR publicname = '" + argv[3] + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
cur.execute("INSERT INTO oathtokens VALUES ('" + nickname + "', '" + argv[3] + "', '" + time.strftime("%Y-%m-%dT%H:%M:%SZ", time.gmtime()) + "', '" + argv[4] + "', 1, 1)")
|
||||
con.commit()
|
||||
print "Key '" + argv[2] + "' added to database."
|
||||
@@ -197,14 +215,14 @@ else:
|
||||
print 'Secret key must be 40 characters max.\n'
|
||||
quit()
|
||||
elif (argv[1][2] == 'l'):
|
||||
- cur.execute('SELECT nickname, publicname FROM oathtokens')
|
||||
- if cur.rowcount != 0:
|
||||
- print " " + str(cur.rowcount) + " keys into database:"
|
||||
+ cur.execute('SELECT count(nickname) FROM oathtokens')
|
||||
+ rowcount = cur.fetchone();
|
||||
+ print " %s keys into database:" % (rowcount[0])
|
||||
+ if rowcount[0]:
|
||||
+ cur.execute('SELECT nickname, publicname FROM oathtokens')
|
||||
print '[Nickname]\t\t>> [PublicID]'
|
||||
- for i in range(0, cur.rowcount):
|
||||
- (nickname, publicname) = cur.fetchone()
|
||||
- print ' ' + nickname + ' ' * (23-len(nickname)) + ">> " + publicname
|
||||
- print ''
|
||||
+ for (nickname, publicname) in cur:
|
||||
+ print '%-23s >> %-21s >> %s ' % (nickname, publicname)
|
||||
else:
|
||||
print 'No keys in database\n'
|
||||
else:
|
||||
@@ -212,13 +230,15 @@ else:
|
||||
elif argv[1][0:2] == '-a':
|
||||
if (argv[1][2] == 'a') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM apikeys WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount != 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM apikeys WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if rowcount[0]:
|
||||
print 'API Key for this nickname is already present. Remove it or choose another one.\n'
|
||||
quit()
|
||||
cur.execute('SELECT id FROM apikeys ORDER BY id DESC LIMIT 1')
|
||||
- if (cur.rowcount != 0):
|
||||
- id = cur.fetchone()[0] + 1
|
||||
+ lastid = cur.fetchone()
|
||||
+ if lastid:
|
||||
+ id = lastid[0] + 1
|
||||
else:
|
||||
id = 1
|
||||
api_key = randomChars(20)
|
||||
@@ -228,22 +248,23 @@ else:
|
||||
print "Your API Key ID is: " + str(id) + "\n"
|
||||
elif (argv[1][2] == 'k') and (len(argv)>2):
|
||||
nickname = re.escape(argv[2])
|
||||
- cur.execute("SELECT * FROM apikeys WHERE nickname = '" + nickname + "'")
|
||||
- if (cur.rowcount == 0):
|
||||
+ cur.execute("SELECT count(nickname) FROM apikeys WHERE nickname = '" + nickname + "'")
|
||||
+ rowcount = cur.fetchone();
|
||||
+ if not rowcount[0]:
|
||||
print "API Key for this nickname Doesn't exists!\n"
|
||||
quit()
|
||||
cur.execute("DELETE FROM apikeys WHERE nickname = '" + nickname + "'")
|
||||
con.commit()
|
||||
print "API Key for '" + nickname + "' has been deleted.\n"
|
||||
elif (argv[1][2] == 'l'):
|
||||
- cur.execute('SELECT nickname FROM apikeys')
|
||||
- if cur.rowcount != 0:
|
||||
- print ' ' + str(cur.rowcount) + ' keys into database:'
|
||||
+ cur.execute('SELECT count(nickname) FROM apikeys')
|
||||
+ rowcount = cur.fetchone();
|
||||
+ print " %s keys into database:" % (rowcount[0])
|
||||
+ if rowcount[0]:
|
||||
+ cur.execute('SELECT nickname FROM apikeys')
|
||||
print '[Nickname]'
|
||||
- for i in range(0, cur.rowcount):
|
||||
- nickname = cur.fetchone()[0]
|
||||
- print ' ' + nickname
|
||||
- print ''
|
||||
+ for (nickname) in cur:
|
||||
+ print '%-23s' % (nickname)
|
||||
else:
|
||||
print 'No keys in database\n'
|
||||
-
|
||||
\ No newline at end of file
|
||||
+
|
34
security/yubiserve/patches/patch-setup_py
Normal file
34
security/yubiserve/patches/patch-setup_py
Normal file
|
@ -0,0 +1,34 @@
|
|||
$OpenBSD: patch-setup_py,v 1.1 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
https://github.com/scumjr/yubikeyedup/pull/5
|
||||
|
||||
Index: setup.py
|
||||
--- setup.py.orig
|
||||
+++ setup.py
|
||||
@@ -0,0 +1,26 @@
|
||||
+#!/usr/bin/env python3
|
||||
+
|
||||
+from setuptools import setup, find_packages
|
||||
+
|
||||
+setup(
|
||||
+ name='yubikeyedup',
|
||||
+ version='0.1',
|
||||
+ author="Alessio Periloso, scumjr, jaroug",
|
||||
+ author_email="mail@periloso.it",
|
||||
+ license="GPL v3",
|
||||
+ description="Yet Another YubiKey OTP Validation Server",
|
||||
+ long_description=open('README.rst').read(),
|
||||
+
|
||||
+ packages=find_packages(),
|
||||
+ include_package_data=True,
|
||||
+ classifiers=[
|
||||
+ ],
|
||||
+
|
||||
+ entry_points = {
|
||||
+ 'console_scripts': [
|
||||
+ 'yubikeyedup=yubikeyedup.yubiserve:main',
|
||||
+ 'yubikeyedup-dbcreate=yubikeyedup.tools.dbcreate:main',
|
||||
+ 'yubikeyedup-dbconf=yubikeyedup.tools.dbconf:main',
|
||||
+ ],
|
||||
+ },
|
||||
+)
|
21
security/yubiserve/patches/patch-yubikeyedup_tools_dbconf_py
Normal file
21
security/yubiserve/patches/patch-yubikeyedup_tools_dbconf_py
Normal file
|
@ -0,0 +1,21 @@
|
|||
$OpenBSD: patch-yubikeyedup_tools_dbconf_py,v 1.1 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
Index: yubikeyedup/tools/dbconf.py
|
||||
--- yubikeyedup/tools/dbconf.py.orig
|
||||
+++ yubikeyedup/tools/dbconf.py
|
||||
@@ -251,7 +251,7 @@ class API(DBConf):
|
||||
return keys
|
||||
|
||||
|
||||
-if __name__ == '__main__':
|
||||
+def main():
|
||||
options = {
|
||||
'-ya': (4, Yubikey, 'add'),
|
||||
'-yk': (1, Yubikey, 'delete'),
|
||||
@@ -290,3 +290,6 @@ if __name__ == '__main__':
|
||||
function = getattr(klass, fname)
|
||||
db = klass(filename)
|
||||
function(db, *args)
|
||||
+
|
||||
+if __name__ == '__main__':
|
||||
+ main()
|
|
@ -0,0 +1,19 @@
|
|||
$OpenBSD: patch-yubikeyedup_tools_dbcreate_py,v 1.1 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
Index: yubikeyedup/tools/dbcreate.py
|
||||
--- yubikeyedup/tools/dbcreate.py.orig
|
||||
+++ yubikeyedup/tools/dbcreate.py
|
||||
@@ -42,9 +42,12 @@ def create_db(filename):
|
||||
conn.commit()
|
||||
conn.close()
|
||||
|
||||
-if __name__ == '__main__':
|
||||
+def main():
|
||||
if len(sys.argv) != 2:
|
||||
print('Usage: %s <db.sqlite3>' % sys.argv[0])
|
||||
sys.exit(0)
|
||||
|
||||
create_db(sys.argv[1])
|
||||
+
|
||||
+if __name__ == '__main__':
|
||||
+ main()
|
18
security/yubiserve/patches/patch-yubikeyedup_validate_py
Normal file
18
security/yubiserve/patches/patch-yubikeyedup_validate_py
Normal file
|
@ -0,0 +1,18 @@
|
|||
$OpenBSD: patch-yubikeyedup_validate_py,v 1.1 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
Index: yubikeyedup/validate.py
|
||||
--- yubikeyedup/validate.py.orig
|
||||
+++ yubikeyedup/validate.py
|
||||
@@ -1,9 +1,9 @@
|
||||
import re
|
||||
|
||||
-from Cryptodome.Cipher import AES
|
||||
+from Crypto.Cipher import AES
|
||||
|
||||
-from sql import *
|
||||
-import yubistatus
|
||||
+from yubikeyedup.sql import *
|
||||
+from yubikeyedup import yubistatus
|
||||
|
||||
|
||||
class Validate:
|
43
security/yubiserve/patches/patch-yubikeyedup_yubiserve_py
Normal file
43
security/yubiserve/patches/patch-yubikeyedup_yubiserve_py
Normal file
|
@ -0,0 +1,43 @@
|
|||
$OpenBSD: patch-yubikeyedup_yubiserve_py,v 1.1 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
Index: yubikeyedup/yubiserve.py
|
||||
--- yubikeyedup/yubiserve.py.orig
|
||||
+++ yubikeyedup/yubiserve.py
|
||||
@@ -16,10 +16,10 @@ import time
|
||||
import urllib.request, urllib.parse, urllib.error
|
||||
import urllib.parse
|
||||
|
||||
-import yubistatus
|
||||
-import validate
|
||||
-import html
|
||||
-from sql import *
|
||||
+from yubikeyedup import yubistatus
|
||||
+from yubikeyedup import validate
|
||||
+from yubikeyedup import html
|
||||
+from yubikeyedup.sql import *
|
||||
|
||||
|
||||
class YubiServeHandler:
|
||||
@@ -134,12 +134,13 @@ def stop_signal_handler(signum, frame):
|
||||
sys.exit(0)
|
||||
|
||||
|
||||
-if __name__ == '__main__':
|
||||
+def main():
|
||||
parser = optparse.OptionParser('Usage: %prog [options]')
|
||||
parser.add_option('-d', '--db', default='./yubikeys.sqlite3', dest='db')
|
||||
parser.add_option('-a', '--address', default='0.0.0.0', dest='host')
|
||||
parser.add_option('-p', '--port', default='8000', dest='port')
|
||||
(options, args) = parser.parse_args()
|
||||
+ global sqlite_db
|
||||
sqlite_db = options.db
|
||||
|
||||
yubiserveHTTP = ThreadingHTTPServer((options.host, int(options.port)), YubiHTTPServer)
|
||||
@@ -151,3 +152,7 @@ if __name__ == '__main__':
|
||||
http_thread.start()
|
||||
|
||||
signal.pause()
|
||||
+
|
||||
+
|
||||
+if __name__ == '__main__':
|
||||
+ main()
|
|
@ -1,17 +0,0 @@
|
|||
$OpenBSD: patch-yubiserve_cfg,v 1.1.1.1 2012/07/18 08:25:07 sthen Exp $
|
||||
--- yubiserve.cfg.orig Thu Mar 24 11:25:52 2011
|
||||
+++ yubiserve.cfg Thu Jun 7 02:48:38 2012
|
||||
@@ -1,9 +1,10 @@
|
||||
yubiservePORT = 8000;
|
||||
yubiserveSSLPORT = 8001;
|
||||
yubiserveHOST = '0.0.0.0';
|
||||
-yubiDB = 'sqlite';
|
||||
+yubiDB = 'sqlite3';
|
||||
#yubiDB = 'mysql';
|
||||
#yubiMySQLHost = 'localhost';
|
||||
#yubiMySQLUser = 'yubiserve';
|
||||
#yubiMySQLPass = 'yubipass';
|
||||
-#yubiMySQLName = 'yubikeys';
|
||||
\ No newline at end of file
|
||||
+#yubiMySQLName = 'yubikeys';
|
||||
+yubiserveDebugLevel = 0;
|
|
@ -1,197 +0,0 @@
|
|||
$OpenBSD: patch-yubiserve_py,v 1.9 2019/03/25 01:29:42 sthen Exp $
|
||||
|
||||
sqlite3 support from
|
||||
http://code.google.com/p/yubico-yubiserve/source/list r39
|
||||
|
||||
remove bogus timestamp checking code; that isn't what the timestamps are for,
|
||||
and they wrap after between 0 and 24-and-a-bit days uptime causing failures.
|
||||
|
||||
Index: yubiserve.py
|
||||
--- yubiserve.py.orig
|
||||
+++ yubiserve.py
|
||||
@@ -1,4 +1,4 @@
|
||||
-#!/usr/bin/python
|
||||
+#!${MODPY_BIN}
|
||||
import re, os, time, socket
|
||||
import urlparse, SocketServer, urllib, BaseHTTPServer
|
||||
from Crypto.Cipher import AES
|
||||
@@ -10,12 +10,16 @@ try:
|
||||
except ImportError:
|
||||
pass
|
||||
try:
|
||||
+ import sqlite3
|
||||
+except ImportError:
|
||||
+ pass
|
||||
+try:
|
||||
import sqlite
|
||||
except ImportError:
|
||||
pass
|
||||
|
||||
def parseConfigFile(): # Originally I wrote this function to parse PHP configuration files!
|
||||
- config = open(os.path.dirname(os.path.realpath(__file__)) + '/yubiserve.cfg', 'r').read().splitlines()
|
||||
+ config = open('${SYSCONFDIR}/yubiserve/yubiserve.cfg', 'r').read().splitlines()
|
||||
keys = {}
|
||||
for line in config:
|
||||
match = re.search('(.*?)=(.*);', line)
|
||||
@@ -45,7 +49,7 @@ class OATHValidation():
|
||||
def validateOATH(self, OATH, publicID):
|
||||
cur = self.con.cursor()
|
||||
cur.execute("SELECT counter, secret FROM oathtokens WHERE publicname = '" + publicID + "' AND active = '1'")
|
||||
- if (cur.rowcount != 1):
|
||||
+ if not cur:
|
||||
validationResult = self.status['BAD_OTP']
|
||||
return validationResult
|
||||
(actualcounter, key) = cur.fetchone()
|
||||
@@ -99,6 +103,7 @@ class OTPValidation():
|
||||
def getResponse(self):
|
||||
return self.validationResponse
|
||||
def validateOTP(self, OTP):
|
||||
+ global config
|
||||
self.OTP = re.escape(OTP)
|
||||
self.validationResult = 0
|
||||
if (len(OTP) <= 32) or (len(OTP) > 48):
|
||||
@@ -109,15 +114,21 @@ class OTPValidation():
|
||||
if match.group(1) and match.group(2):
|
||||
self.userid = match.group(1)
|
||||
self.token = self.modhex2hex(match.group(2))
|
||||
+ # pdb.set_trace()
|
||||
cur = self.con.cursor()
|
||||
cur.execute('SELECT aeskey, internalname FROM yubikeys WHERE publicname = "' + self.userid + '" AND active = "1"')
|
||||
- if (cur.rowcount != 1):
|
||||
+ if not cur:
|
||||
+ if config['yubiserveDebugLevel'] > 0:
|
||||
+ print "Yubikey rejected because it is not found in the database, using the query: 'SELECT aeskey, internalname FROM yubikeys WHERE publicname = \"%s\" AND active = \"1\"'" % (self.userid)
|
||||
self.validationResult = self.status['BAD_OTP']
|
||||
return self.validationResult
|
||||
(self.aeskey, self.internalname) = cur.fetchone()
|
||||
self.plaintext = self.aes128ecb_decrypt(self.aeskey, self.token)
|
||||
uid = self.plaintext[:12]
|
||||
if (self.internalname != uid):
|
||||
+ if config['yubiserveDebugLevel'] > 0:
|
||||
+ print "Yubikey rejected because the uid (6 byte secret) in the decrypted AES key (set with with ykpersonalise -ouid) does not match the secret key (internalname) in the database"
|
||||
+ print "Decrypted AES: %s\n Username from yubikey: %s shoould equal the database username: %s" % (self.plaintext, uid, self.internalname)
|
||||
self.validationResult = self.status['BAD_OTP']
|
||||
return self.validationResult
|
||||
if not (self.CRC() or self.isCRCValid()):
|
||||
@@ -126,16 +137,13 @@ class OTPValidation():
|
||||
self.internalcounter = self.hexdec(self.plaintext[14:16] + self.plaintext[12:14] + self.plaintext[22:24])
|
||||
self.timestamp = self.hexdec(self.plaintext[20:22] + self.plaintext[18:20] + self.plaintext[16:18])
|
||||
cur.execute('SELECT counter, time FROM yubikeys WHERE publicname = "' + self.userid + '" AND active = "1"')
|
||||
- if (cur.rowcount != 1):
|
||||
+ if not cur:
|
||||
self.validationResult = self.status['BAD_OTP']
|
||||
return self.validationResult
|
||||
(self.counter, self.time) = cur.fetchone()
|
||||
if (self.counter) >= (self.internalcounter):
|
||||
self.validationResult = self.status['REPLAYED_OTP']
|
||||
return self.validationResult
|
||||
- if (self.time >= self.timestamp) and ((self.counter >> 8) == (self.internalcounter >> 8)):
|
||||
- self.validationResult = self.status['DELAYED_OTP']
|
||||
- return self.validationResult
|
||||
except IndexError:
|
||||
self.validationResult = self.status['BAD_OTP']
|
||||
return self.validationResult
|
||||
@@ -147,11 +155,13 @@ class OTPValidation():
|
||||
class YubiServeHandler (BaseHTTPServer.BaseHTTPRequestHandler):
|
||||
__base = BaseHTTPServer.BaseHTTPRequestHandler
|
||||
__base_handle = __base.handle
|
||||
- server_version = 'Yubiserve/3.0'
|
||||
+ server_version = 'Yubiserve/3.1'
|
||||
global config
|
||||
#try:
|
||||
- if config['yubiDB'] == 'sqlite':
|
||||
- con = sqlite.connect(os.path.dirname(os.path.realpath(__file__)) + '/yubikeys.sqlite')
|
||||
+ if config['yubiDB'] == 'sqlite3':
|
||||
+ con = sqlite3.connect('/var/db/yubiserve/yubikeys.sqlite3', check_same_thread = False)
|
||||
+ elif config['yubiDB'] == 'sqlite':
|
||||
+ con = sqlite.connect('/var/db/yubiserve/yubikeys.sqlite', check_same_thread = False)
|
||||
elif config['yubiDB'] == 'mysql':
|
||||
con = MySQLdb.connect(host=config['yubiMySQLHost'], user=config['yubiMySQLUser'], passwd=config['yubiMySQLPass'], db=config['yubiMySQLName'])
|
||||
#except:
|
||||
@@ -190,7 +200,7 @@ class YubiServeHandler (BaseHTTPServer.BaseHTTPRequest
|
||||
if len(query) > 0:
|
||||
getData = self.getToDict(query)
|
||||
otpvalidation = OTPValidation(self.con)
|
||||
- validation = otpvalidation.validateOTP(getData['otp'])
|
||||
+ validation = otpvalidation.validateOTP(getData['otp'].lower())
|
||||
self.send_response(200)
|
||||
self.send_header('Content-type', 'text/plain')
|
||||
self.end_headers()
|
||||
@@ -200,16 +210,16 @@ class YubiServeHandler (BaseHTTPServer.BaseHTTPRequest
|
||||
orderedResult = 'nonce=' + getData['nonce'] + '&otp=' + getData['otp'] + '&sl=100&status=' + [k for k, v in otpvalidation.status.iteritems() if v == validation][0] + '&t=' + iso_time
|
||||
except KeyError:
|
||||
result = 't=' + iso_time + '\r\notp=' + getData['otp'] + '\r\nnonce=\r\nsl=100\r\nstatus=' + [k for k, v in otpvalidation.status.iteritems() if v == validation][0] + '\r\n'
|
||||
- orderedResult = 'nonce=&otp=' + getData['otp'] + 'sl=100&status=' + [k for k, v in otpvalidation.status.iteritems() if v == validation][0] + '&t=' + iso_time
|
||||
+ orderedResult = 'nonce=&otp=' + getData['otp'] + '&sl=100&status=' + [k for k, v in otpvalidation.status.iteritems() if v == validation][0] + '&t=' + iso_time
|
||||
otp_hmac = ''
|
||||
try:
|
||||
if (getData['id'] != None):
|
||||
apiID = re.escape(getData['id'])
|
||||
cur = self.con.cursor()
|
||||
cur.execute("SELECT secret from apikeys WHERE id = '" + apiID + "'")
|
||||
- if cur.rowcount != 0:
|
||||
+ if cur:
|
||||
api_key = cur.fetchone()[0]
|
||||
- otp_hmac = hmac.new(api_key, msg=orderedResult, digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
+ otp_hmac = hmac.new(str(api_key), msg=str(orderedResult), digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
else:
|
||||
result = 't=' + iso_time + '\r\notp=' + getData['otp'] + '\r\nstatus=NO_CLIENT\r\n'
|
||||
except KeyError:
|
||||
@@ -230,7 +240,7 @@ class YubiServeHandler (BaseHTTPServer.BaseHTTPRequest
|
||||
apiID = re.escape(getData['id'])
|
||||
cur = self.con.cursor()
|
||||
cur.execute("SELECT secret from apikeys WHERE id = '" + apiID + "'")
|
||||
- if cur.rowcount != 0:
|
||||
+ if cur:
|
||||
api_key = cur.fetchone()[0]
|
||||
otp_hmac = hmac.new(api_key, msg=orderedResult, digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
except KeyError:
|
||||
@@ -258,15 +268,16 @@ class YubiServeHandler (BaseHTTPServer.BaseHTTPRequest
|
||||
self.end_headers()
|
||||
iso_time = time.strftime("%Y-%m-%dT%H:%M:%S")
|
||||
result = 'otp=' + getData['otp'] + '\r\nstatus=' + [k for k, v in oathvalidation.status.iteritems() if v == validation][0] + '\r\nt=' + iso_time
|
||||
+ orderedResult = 'otp=' + getData['otp'] + '&status=' + [k for k, v in oathvalidation.status.iteritems() if v == validation][0] + '&t=' + iso_time
|
||||
otp_hmac = ''
|
||||
try:
|
||||
if (getData['id'] != None):
|
||||
apiID = re.escape(getData['id'])
|
||||
cur = self.con.cursor()
|
||||
cur.execute("SELECT secret from apikeys WHERE id = '" + apiID + "'")
|
||||
- if cur.rowcount != 0:
|
||||
+ if cur:
|
||||
api_key = cur.fetchone()[0]
|
||||
- otp_hmac = hmac.new(api_key, msg=result, digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
+ otp_hmac = hmac.new(str(api_key), msg=str(orderedResult), digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
else:
|
||||
result = 'otp=' + getData['otp'] + '\r\nstatus=NO_CLIENT\r\nt=' + iso_time
|
||||
except KeyError:
|
||||
@@ -285,7 +296,7 @@ class YubiServeHandler (BaseHTTPServer.BaseHTTPRequest
|
||||
apiID = re.escape(getData['id'])
|
||||
cur = self.con.cursor()
|
||||
cur.execute("SELECT secret from apikeys WHERE id = '" + apiID + "'")
|
||||
- if cur.rowcount != 0:
|
||||
+ if cur:
|
||||
api_key = cur.fetchone()[0]
|
||||
otp_hmac = hmac.new(api_key, msg=result, digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
except KeyError:
|
||||
@@ -305,7 +316,7 @@ class YubiServeHandler (BaseHTTPServer.BaseHTTPRequest
|
||||
apiID = re.escape(getData['id'])
|
||||
cur = self.con.cursor()
|
||||
cur.execute("SELECT secret from apikeys WHERE id = '" + apiID + "'")
|
||||
- if cur.rowcount != 0:
|
||||
+ if cur:
|
||||
api_key = cur.fetchone()[0]
|
||||
otp_hmac = hmac.new(api_key, msg=result, digestmod=hashlib.sha1).hexdigest().decode('hex').encode('base64').strip()
|
||||
except KeyError:
|
||||
@@ -322,9 +333,10 @@ class SecureHTTPServer(BaseHTTPServer.HTTPServer):
|
||||
def __init__(self, server_address, HandlerClass):
|
||||
BaseHTTPServer.HTTPServer.__init__(self, server_address, HandlerClass)
|
||||
ctx = SSL.Context(SSL.SSLv23_METHOD)
|
||||
- fpem = os.path.dirname(os.path.realpath(__file__)) + '/yubiserve.pem'
|
||||
+ fpem = '${SYSCONFDIR}/yubiserve/yubiserve.pem'
|
||||
ctx.use_privatekey_file (fpem)
|
||||
ctx.use_certificate_file(fpem)
|
||||
+ ctx.use_certificate_chain_file(fpem)
|
||||
self.socket = SSL.Connection(ctx, socket.socket(self.address_family, self.socket_type))
|
||||
self.server_bind()
|
||||
self.server_activate()
|
|
@ -1,6 +1,9 @@
|
|||
YubiServe is a lightweight Validation Server supporting both OATH/HOTP
|
||||
and Yubico Yubikey implementations, written in Python that uses an
|
||||
SQLite database or, optionally, a MySQL database. It has an integrated
|
||||
threaded webserver, with HTTPS/SSL support, compatible with the
|
||||
Yubico validation protocol 2.0 including HMAC SHA-1 signatures to
|
||||
provide for authentication of the server.
|
||||
yubikeyedup is a lightweight validation server for Yubikey OTP
|
||||
authentication written in Python. It provides the standard HTTP-based
|
||||
Validation Protocol 2.0 used by various servers including Yubico's
|
||||
official PHP-based server.
|
||||
|
||||
It is a complete rewrite of the earlier project "YubiServe" (seemingly
|
||||
abandoned and never ported to Python 3). It uses the same database schema
|
||||
and is broadly compatible, though does not support HTTPS internally (if
|
||||
wanted, this can be added by proxying from relayd, nginx or similar).
|
||||
|
|
|
@ -1,32 +1,42 @@
|
|||
@comment $OpenBSD: PLIST,v 1.1.1.1 2012/07/18 08:25:07 sthen Exp $
|
||||
@comment $OpenBSD: PLIST,v 1.2 2021/03/29 12:08:39 sthen Exp $
|
||||
@newgroup _yubiserve:700
|
||||
@newuser _yubiserve:700:_yubiserve:daemon:yubiserve user:/nonexistent:/sbin/nologin
|
||||
bin/yubiserve-dbconf
|
||||
sbin/yubiserve
|
||||
share/doc/yubiserve/
|
||||
share/doc/yubiserve/LICENSE
|
||||
share/doc/yubiserve/README
|
||||
share/doc/yubiserve/dump.mysql
|
||||
share/doc/yubiserve/dump.sqlite
|
||||
share/examples/yubiserve/
|
||||
share/examples/yubiserve/yubikeys.sqlite3
|
||||
@mode 770
|
||||
@owner _yubiserve
|
||||
@group _yubiserve
|
||||
@sample /var/db/yubiserve/
|
||||
@mode 640
|
||||
@sample /var/db/yubiserve/yubikeys.sqlite3
|
||||
@mode
|
||||
@owner
|
||||
@group
|
||||
share/examples/yubiserve/yubiserve.cfg
|
||||
@mode 750
|
||||
@owner root
|
||||
@group _yubiserve
|
||||
@sample ${SYSCONFDIR}/yubiserve/
|
||||
@mode 640
|
||||
@sample ${SYSCONFDIR}/yubiserve/yubiserve.cfg
|
||||
@mode
|
||||
@owner
|
||||
@group
|
||||
@rcscript ${RCDIR}/yubiserve
|
||||
@rcscript ${RCDIR}/yubikeyedup
|
||||
bin/yubikeyedup
|
||||
bin/yubikeyedup-dbconf
|
||||
bin/yubikeyedup-dbcreate
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup-0.1-py${MODPY_VERSION}.egg-info/
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup-0.1-py${MODPY_VERSION}.egg-info/PKG-INFO
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup-0.1-py${MODPY_VERSION}.egg-info/SOURCES.txt
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup-0.1-py${MODPY_VERSION}.egg-info/dependency_links.txt
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup-0.1-py${MODPY_VERSION}.egg-info/entry_points.txt
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup-0.1-py${MODPY_VERSION}.egg-info/top_level.txt
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/__init__.py
|
||||
${MODPY_COMMENT}lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}/
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}__init__.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}html.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}sql.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}validate.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}yubiserve.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/${MODPY_PYCACHE}yubistatus.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/html.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/sql.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/__init__.py
|
||||
${MODPY_COMMENT}lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/${MODPY_PYCACHE}/
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/${MODPY_PYCACHE}__init__.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/${MODPY_PYCACHE}dbconf.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/${MODPY_PYCACHE}dbcreate.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/${MODPY_PYCACHE}flash.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/${MODPY_PYCACHE}unittests.${MODPY_PYC_MAGIC_TAG}pyc
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/dbconf.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/dbcreate.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/flash.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/tools/unittests.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/validate.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/yubiserve.py
|
||||
lib/python${MODPY_VERSION}/site-packages/yubikeyedup/yubistatus.py
|
||||
share/doc/yubikeyedup/
|
||||
share/doc/yubikeyedup/LICENSE
|
||||
share/doc/yubikeyedup/README.rst
|
||||
|
|
15
security/yubiserve/pkg/yubikeyedup.rc
Normal file
15
security/yubiserve/pkg/yubikeyedup.rc
Normal file
|
@ -0,0 +1,15 @@
|
|||
#!/bin/ksh
|
||||
#
|
||||
# $OpenBSD: yubikeyedup.rc,v 1.1 2021/03/29 12:08:39 sthen Exp $
|
||||
|
||||
daemon="${TRUEPREFIX}/bin/yubikeyedup"
|
||||
daemon_flags="--db /var/db/yubiserve/yubikeys.sqlite3"
|
||||
daemon_user="_yubiserve"
|
||||
|
||||
. /etc/rc.d/rc.subr
|
||||
|
||||
pexp="${MODPY_BIN} ${daemon}${daemon_flags:+ ${daemon_flags}}"
|
||||
rc_bg=YES
|
||||
rc_reload=NO
|
||||
|
||||
rc_cmd $1
|
|
@ -1,14 +0,0 @@
|
|||
#!/bin/ksh
|
||||
#
|
||||
# $OpenBSD: yubiserve.rc,v 1.5 2018/01/11 19:27:09 rpe Exp $
|
||||
|
||||
daemon="${TRUEPREFIX}/sbin/yubiserve"
|
||||
daemon_user="_yubiserve"
|
||||
|
||||
. /etc/rc.d/rc.subr
|
||||
|
||||
pexp="${MODPY_BIN} ${daemon}${daemon_flags:+ ${daemon_flags}}"
|
||||
rc_bg=YES
|
||||
rc_reload=NO
|
||||
|
||||
rc_cmd $1
|
Loading…
Reference in New Issue
Block a user