#!/usr/bin/python
import argparse, os, sys, pwd, gettext

from gettext import gettext as _
gettext.textdomain("arkose")

currentdir=os.path.split(os.path.realpath(__file__))[0]
if os.path.exists(os.path.join(currentdir, "../arkose/__init__.py")):
    sys.path.insert(0, os.path.join(currentdir, ".."))

import arkose

# Get all the parameters
parser = argparse.ArgumentParser(description=_("Arkose application container"),
            add_help=False, formatter_class=argparse.RawTextHelpFormatter, epilog=_(
"""For X to work on >= 2.6.36, you need one of -n (network) or -T (real /tmp).
For older versions of the kernel, only -n (network) will work."""))

# Simple on/off options
parser.add_argument("--help",action="store_true")

parser.add_argument("-h", "--home", dest="home", action="store_true",
    help=_("Use real home directory (same as --bind $HOME)"))

parser.add_argument("-p", "--pulseaudio", dest="pulseaudio", action="store_true",
    help=_("Allow access to pulseaudio"))

# Multiple choices options

parser.add_argument("-d", "--dbus", dest="dbus", type=str,
    choices=("none", "system", "session", "both"), default="none",
    help=_("""DBUS access restriction (default: both)"""))

parser.add_argument("-n", "--network", dest="network", type=str,
    choices=("none", "direct", "filtered"), default="direct",
    help=_("""Network access restriction (default: direct)"""))

parser.add_argument("-s", "--size", dest="size", type=int,
    default=None, nargs=1,
    help=_("""Storage size in MB
(default: 2000 on ext4, 50%% of RAM on tmpfs)"""))

parser.add_argument("-t", "--type", dest="type", type=str,
    choices=("ext4", "tmpfs"), default="ext4",
    help=_("""Storage type. (default: ext4)"""))

parser.add_argument("-x", "--xserver", dest="xserver", type=str,
    choices=("none", "isolated", "direct"), default="direct",
    help=_("""Xserver access restriction (default: direct)"""))

parser.add_argument("--root", dest="root", type=str,
    default="/",
    help=_("""Path to use as root for the container (default: /)"""))

parser.add_argument("--root-type", dest="ctype", type=str,
    choices=("cow", "bind"), default="cow",
    help=_("""Type of root device mount (default: cow)"""))

parser.add_argument("--base-path", dest="path", type=str,
    default=None,
    help=_("""Where to store the container (default: ~/.arkose)"""))

# Mount related options (all these can be called multiple times)

parser.add_argument("--bind", dest="bind", type=str,
    default=[], action='append',
    help=_("""Add a bind mount to the container.
(allowed multiple times)"""))

parser.add_argument("--cow", dest="cow", type=str,
    default=[], action='append',
    help=_("""Add a copy-on-write mount to the container.
(allowed multiple times)"""))

parser.add_argument("--restrict", dest="restrict", type=str,
    default=[], action='append',
    help=_("""Mount an empty directory on the given path.
(allowed multiple times)"""))

# Similar but for devices

parser.add_argument("--device", dest="device", type=str,
    default=[], action='append',
    help=_("""Allow access to an existing device in /dev
(allowed multiple times)"""))

# Final catch-all
parser.add_argument("command", metavar='CMD', type=str,
    default=["bash"], nargs="*",
    help=_("Run specific command in container (command as argument)"))

args = parser.parse_args()
if args.help:
    parser.print_help()
    sys.exit(0)

if not os.geteuid() == 0:
    print(_("You must be root to use this command"))
    sys.exit(1)

# Start the container
if args.home:
    args.bind.append(os.getenv("HOME"))
if args.size:
    args.size=args.size[0]

# Get the current user
user=pwd.getpwuid(int(os.getenv("PKEXEC_UID",os.getenv("UID",1000))))

container=arkose.ArkoseContainer(
    pulseaudio=args.pulseaudio,
    dbus=args.dbus,
    network=args.network,
    fssize=args.size,
    fstype=args.type,
    xserver=args.xserver,
    root=args.root,
    ctype=args.ctype,
    path=args.path,
    bind=args.bind,
    cow=args.cow,
    restrict=args.restrict,
    devices=args.device
)
container.run_command(
    "su %s -c \"%s\"" % (user.pw_name, " ".join(args.command)))
container.cleanup()
