Added certainty question, fixed streamer dependency
This commit is contained in:
parent
f62de10972
commit
23810ef3c9
7 changed files with 121 additions and 73 deletions
4
debian/control
vendored
4
debian/control
vendored
|
|
@ -9,8 +9,8 @@ Vcs-Git: https://github.com/boltgolt/howdy
|
||||||
Package: howdy
|
Package: howdy
|
||||||
Homepage: https://github.com/boltgolt/howdy
|
Homepage: https://github.com/boltgolt/howdy
|
||||||
Architecture: all
|
Architecture: all
|
||||||
Depends: ${misc:Depends}, curl|wget, python3, python3-pip, python3-dev, python3-setuptools, libpam-python, fswebcam, libopencv-dev, cmake, fswebcam
|
Depends: ${misc:Depends}, curl|wget, python3, python3-pip, python3-dev, python3-setuptools, libpam-python, libopencv-dev, cmake
|
||||||
Recommends: libatlas-base-dev | libopenblas-dev | liblapack-dev
|
Recommends: libatlas-base-dev | libopenblas-dev | liblapack-dev, streamer
|
||||||
Suggests: nvidia-cuda-dev (>= 7.5)
|
Suggests: nvidia-cuda-dev (>= 7.5)
|
||||||
Description: Howdy: Windows Hello style authentication for Linux.
|
Description: Howdy: Windows Hello style authentication for Linux.
|
||||||
Use your built-in IR emitters and camera in combination with face recognition
|
Use your built-in IR emitters and camera in combination with face recognition
|
||||||
|
|
|
||||||
6
debian/postinst
vendored
6
debian/postinst
vendored
|
|
@ -196,10 +196,14 @@ handleStatus(subprocess.call(["pip3", "install", "--no-cache-dir", "opencv-pytho
|
||||||
|
|
||||||
log("Configuring howdy")
|
log("Configuring howdy")
|
||||||
|
|
||||||
|
campath = picked.split(";")[0]
|
||||||
|
cert = picked.split(";")[1]
|
||||||
|
|
||||||
# Manually change the camera id to the one picked
|
# Manually change the camera id to the one picked
|
||||||
for line in fileinput.input(["/lib/security/howdy/config.ini"], inplace=1):
|
for line in fileinput.input(["/lib/security/howdy/config.ini"], inplace=1):
|
||||||
line = line.replace("device_path = none", "device_path = " + picked)
|
line = line.replace("device_path = none", "device_path = " + campath)
|
||||||
line = line.replace("use_cnn = false", "use_cnn = " + str(cuda_used).lower())
|
line = line.replace("use_cnn = false", "use_cnn = " + str(cuda_used).lower())
|
||||||
|
line = line.replace("certainty = 3.5", "certainty = " + cert)
|
||||||
|
|
||||||
print(line, end="")
|
print(line, end="")
|
||||||
|
|
||||||
|
|
|
||||||
129
debian/preinst
vendored
129
debian/preinst
vendored
|
|
@ -7,6 +7,7 @@ def col(id):
|
||||||
if id == 1: return "\033[32m"
|
if id == 1: return "\033[32m"
|
||||||
if id == 2: return "\033[33m"
|
if id == 2: return "\033[33m"
|
||||||
if id == 3: return "\033[31m"
|
if id == 3: return "\033[31m"
|
||||||
|
if id == 4: return "\033[1m"
|
||||||
return "\033[0m"
|
return "\033[0m"
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -38,7 +39,6 @@ if "install" not in sys.argv:
|
||||||
# The default picked video device id
|
# The default picked video device id
|
||||||
picked = "none"
|
picked = "none"
|
||||||
|
|
||||||
print(col(1) + "Starting IR camera check...\n" + col(0))
|
|
||||||
|
|
||||||
# If prompting has been disabled, skip camera check
|
# If prompting has been disabled, skip camera check
|
||||||
if "HOWDY_NO_PROMPT" in os.environ:
|
if "HOWDY_NO_PROMPT" in os.environ:
|
||||||
|
|
@ -46,67 +46,104 @@ if "HOWDY_NO_PROMPT" in os.environ:
|
||||||
|
|
||||||
# Write the default device to disk and exit
|
# Write the default device to disk and exit
|
||||||
with open("/tmp/howdy_picked_device", "w") as out_file:
|
with open("/tmp/howdy_picked_device", "w") as out_file:
|
||||||
out_file.write("none")
|
out_file.write("none;3.5")
|
||||||
|
|
||||||
sys.exit(0)
|
sys.exit(0)
|
||||||
|
|
||||||
# Get all devices
|
fscheck = subprocess.call(["which", "streamer"], stdout=subprocess.PIPE)
|
||||||
devices = os.listdir("/dev/v4l/by-path")
|
|
||||||
|
|
||||||
# Loop though all devices
|
if fscheck == 1:
|
||||||
for dev in devices:
|
print(col(2) + "\nWARNING: Could not automatically find the right webcam, manual configuration after installation required\n" + col(0))
|
||||||
time.sleep(.5)
|
else:
|
||||||
|
print(col(1) + "Starting IR camera check...\n" + col(0))
|
||||||
|
|
||||||
# The full path to the device is the default name
|
# Get all devices
|
||||||
device_name = "/dev/v4l/by-path/" + dev
|
devices = os.listdir("/dev/v4l/by-path")
|
||||||
# Get the udevadm details to try to get a better name
|
|
||||||
udevadm = subprocess.check_output(["udevadm info -r --query=all -n " + device_name], shell=True).decode("utf-8")
|
|
||||||
|
|
||||||
# Loop though udevadm to search for a better name
|
# Loop though all devices
|
||||||
for line in udevadm.split("\n"):
|
for dev in devices:
|
||||||
# Match it and encase it in quotes
|
time.sleep(.5)
|
||||||
re_name = re.search('product.*=(.*)$', line, re.IGNORECASE)
|
|
||||||
if re_name:
|
|
||||||
device_name = '"' + re_name.group(1) + '"'
|
|
||||||
|
|
||||||
# Show what device we're using
|
# The full path to the device is the default name
|
||||||
print("Trying " + device_name)
|
device_name = "/dev/v4l/by-path/" + dev
|
||||||
|
# Get the udevadm details to try to get a better name
|
||||||
|
udevadm = subprocess.check_output(["udevadm info -r --query=all -n " + device_name], shell=True).decode("utf-8")
|
||||||
|
|
||||||
# Let fswebcam keep the camera open in the background
|
# Loop though udevadm to search for a better name
|
||||||
sub = subprocess.Popen(
|
for line in udevadm.split("\n"):
|
||||||
"fswebcam -l 1 -d /dev/v4l/by-path/%s" % dev,
|
# Match it and encase it in quotes
|
||||||
shell=True,
|
re_name = re.search('product.*=(.*)$', line, re.IGNORECASE)
|
||||||
preexec_fn=os.setsid,
|
if re_name:
|
||||||
stdout=subprocess.PIPE,
|
device_name = '"' + re_name.group(1) + '"'
|
||||||
stdin=subprocess.PIPE)
|
|
||||||
|
|
||||||
try:
|
# Show what device we're using
|
||||||
# Ask the user if this is the right one
|
print("Trying " + device_name)
|
||||||
print(col(2) + "One of your cameras should now be on." + col(0))
|
|
||||||
ans = input("Did your IR emitters turn on? [y/N]: ")
|
# Let fswebcam keep the camera open in the background
|
||||||
except KeyboardInterrupt:
|
sub = subprocess.Popen(
|
||||||
# Kill fswebcam if the user aborts
|
["streamer -t 1:0:0 -c /dev/v4l/by-path/" + dev + " -b 16 -f rgb24 -o /dev/null 1>/dev/null 2>/dev/null"],
|
||||||
|
shell=True,
|
||||||
|
preexec_fn=os.setsid,
|
||||||
|
stdout=subprocess.PIPE,
|
||||||
|
stdin=subprocess.PIPE)
|
||||||
|
|
||||||
|
try:
|
||||||
|
# Ask the user if this is the right one
|
||||||
|
print(col(2) + "One of your cameras should now be on." + col(0))
|
||||||
|
ans = input("Did your IR emitters turn on? [y/N]: ")
|
||||||
|
except KeyboardInterrupt:
|
||||||
|
# Kill fswebcam if the user aborts
|
||||||
|
os.killpg(os.getpgid(sub.pid), signal.SIGTERM)
|
||||||
|
raise
|
||||||
|
|
||||||
|
# The user has answered, kill fswebcam
|
||||||
os.killpg(os.getpgid(sub.pid), signal.SIGTERM)
|
os.killpg(os.getpgid(sub.pid), signal.SIGTERM)
|
||||||
raise
|
|
||||||
|
|
||||||
# The user has answered, kill fswebcam
|
# Set this camera as picked if the answer was yes, go to the next one if no
|
||||||
os.killpg(os.getpgid(sub.pid), signal.SIGTERM)
|
if ans.lower().strip() == "y" or ans.lower().strip() == "yes":
|
||||||
|
picked = dev
|
||||||
|
break
|
||||||
|
else:
|
||||||
|
print("Interpreting as a " + col(3) + "\"NO\"\n" + col(0))
|
||||||
|
|
||||||
# Set this camera as picked if the answer was yes, go to the next one if no
|
# Abort if no camera was picked
|
||||||
if ans.lower().strip() == "y" or ans.lower().strip() == "yes":
|
if picked == "none":
|
||||||
picked = dev
|
print(col(3) + "No suitable IR camera found, aborting install." + col(0))
|
||||||
break
|
sys.exit(23)
|
||||||
else:
|
|
||||||
print("Interpreting as a " + col(3) + "\"NO\"\n" + col(0))
|
|
||||||
|
|
||||||
# Abort if no camera was picked
|
cert = 3.5
|
||||||
if picked == "none":
|
|
||||||
print(col(3) + "No suitable IR camera found, aborting install." + col(0))
|
# Give time to read
|
||||||
sys.exit(23)
|
time.sleep(.5)
|
||||||
|
|
||||||
|
print(col(1) + "\nStarting certainty auto config..." + col(0))
|
||||||
|
|
||||||
|
# Give more time to read
|
||||||
|
time.sleep(.5)
|
||||||
|
|
||||||
|
print("\n\nAfter detection, Howdy knows how certain it is that the match is correct.")
|
||||||
|
print("How certain Howdy needs to be before authenticating you can be customized.")
|
||||||
|
|
||||||
|
print(col(4) + "\nF: Fast." + col(0))
|
||||||
|
print("Allows more fuzzy matches, but speeds up the scanning process greatly.")
|
||||||
|
print(col(4) + "\nB: Balanced." + col(0))
|
||||||
|
print("Still relatively quick detection, but might not log you in when further away.")
|
||||||
|
print(col(4) + "\nS: Secure." + col(0))
|
||||||
|
print("The safest option, but will take much longer to authenticate you.")
|
||||||
|
|
||||||
|
print("\nYou can always change this setting in the config.")
|
||||||
|
prof = input("What profile would you like to use? [f/b/s]: ")
|
||||||
|
|
||||||
|
if prof.lower().strip() == "f" or prof.lower().strip() == "fast":
|
||||||
|
cert = 1.5
|
||||||
|
elif prof.lower().strip() == "b" or prof.lower().strip() == "balanced":
|
||||||
|
cert = 2.8
|
||||||
|
elif prof.lower().strip() == "s" or prof.lower().strip() == "secure":
|
||||||
|
cert = 4
|
||||||
|
|
||||||
# Write the result to disk so postinst can have a look at it
|
# Write the result to disk so postinst can have a look at it
|
||||||
with open("/tmp/howdy_picked_device", "w") as out_file:
|
with open("/tmp/howdy_picked_device", "w") as out_file:
|
||||||
out_file.write("/dev/v4l/by-path/" + picked)
|
out_file.write("/dev/v4l/by-path/" + picked + ";" + str(cert))
|
||||||
|
|
||||||
# Add a line break
|
# Add a line break
|
||||||
print("")
|
print("")
|
||||||
|
|
|
||||||
1
debian/source/options
vendored
1
debian/source/options
vendored
|
|
@ -2,6 +2,7 @@ tar-ignore = ".git"
|
||||||
tar-ignore = ".gitignore"
|
tar-ignore = ".gitignore"
|
||||||
tar-ignore = ".github"
|
tar-ignore = ".github"
|
||||||
tar-ignore = "models"
|
tar-ignore = "models"
|
||||||
|
tar-ignore = "snapshots"
|
||||||
tar-ignore = "tests"
|
tar-ignore = "tests"
|
||||||
tar-ignore = "README.md"
|
tar-ignore = "README.md"
|
||||||
tar-ignore = ".travis.yml"
|
tar-ignore = ".travis.yml"
|
||||||
|
|
|
||||||
50
src/cli.py
50
src/cli.py
|
|
@ -26,38 +26,44 @@ if user == "root" or user is None:
|
||||||
user = env_user
|
user = env_user
|
||||||
|
|
||||||
# Basic command setup
|
# Basic command setup
|
||||||
parser = argparse.ArgumentParser(description="Command line interface for Howdy face authentication.",
|
parser = argparse.ArgumentParser(
|
||||||
formatter_class=argparse.RawDescriptionHelpFormatter,
|
description="Command line interface for Howdy face authentication.",
|
||||||
add_help=False,
|
formatter_class=argparse.RawDescriptionHelpFormatter,
|
||||||
prog="howdy",
|
add_help=False,
|
||||||
epilog="For support please visit\nhttps://github.com/boltgolt/howdy")
|
prog="howdy",
|
||||||
|
epilog="For support please visit\nhttps://github.com/boltgolt/howdy")
|
||||||
|
|
||||||
# Add an argument for the command
|
# Add an argument for the command
|
||||||
parser.add_argument("command",
|
parser.add_argument(
|
||||||
help="The command option to execute, can be one of the following: add, clear, config, disable, list, remove, snapshot, test or version.",
|
"command",
|
||||||
metavar="command",
|
help="The command option to execute, can be one of the following: add, clear, config, disable, list, remove, snapshot, test or version.",
|
||||||
choices=["add", "clear", "config", "disable", "list", "remove", "snapshot", "test", "version"])
|
metavar="command",
|
||||||
|
choices=["add", "clear", "config", "disable", "list", "remove", "snapshot", "test", "version"])
|
||||||
|
|
||||||
# Add an argument for the extra arguments of diable and remove
|
# Add an argument for the extra arguments of diable and remove
|
||||||
parser.add_argument("argument",
|
parser.add_argument(
|
||||||
help="Either 0 (enable) or 1 (disable) for the disable command, or the model ID for the remove command.",
|
"argument",
|
||||||
nargs="?")
|
help="Either 0 (enable) or 1 (disable) for the disable command, or the model ID for the remove command.",
|
||||||
|
nargs="?")
|
||||||
|
|
||||||
# Add the user flag
|
# Add the user flag
|
||||||
parser.add_argument("-U", "--user",
|
parser.add_argument(
|
||||||
default=user,
|
"-U", "--user",
|
||||||
help="Set the user account to use.")
|
default=user,
|
||||||
|
help="Set the user account to use.")
|
||||||
|
|
||||||
# Add the -y flag
|
# Add the -y flag
|
||||||
parser.add_argument("-y",
|
parser.add_argument(
|
||||||
help="Skip all questions.",
|
"-y",
|
||||||
action="store_true")
|
help="Skip all questions.",
|
||||||
|
action="store_true")
|
||||||
|
|
||||||
# Overwrite the default help message so we can use a uppercase S
|
# Overwrite the default help message so we can use a uppercase S
|
||||||
parser.add_argument("-h", "--help",
|
parser.add_argument(
|
||||||
action="help",
|
"-h", "--help",
|
||||||
default=argparse.SUPPRESS,
|
action="help",
|
||||||
help="Show this help message and exit.")
|
default=argparse.SUPPRESS,
|
||||||
|
help="Show this help message and exit.")
|
||||||
|
|
||||||
# If we only have 1 argument we print the help text
|
# If we only have 1 argument we print the help text
|
||||||
if len(sys.argv) < 2:
|
if len(sys.argv) < 2:
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ try:
|
||||||
encodings = json.load(open(enc_file))
|
encodings = json.load(open(enc_file))
|
||||||
except FileNotFoundError:
|
except FileNotFoundError:
|
||||||
print("No face model known for the user " + user + ", please run:")
|
print("No face model known for the user " + user + ", please run:")
|
||||||
print("\n\thowdy " + user + " add\n")
|
print("\n\tsudo howdy -U " + user + " add\n")
|
||||||
sys.exit(1)
|
sys.exit(1)
|
||||||
|
|
||||||
# Print a header
|
# Print a header
|
||||||
|
|
|
||||||
|
|
@ -22,4 +22,4 @@ fi
|
||||||
|
|
||||||
# Uncompress the data files and delete the original archive
|
# Uncompress the data files and delete the original archive
|
||||||
echo "Unpacking..."
|
echo "Unpacking..."
|
||||||
bzip2 -d *.bz2
|
bzip2 -d -f *.bz2
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue