Merge remote-tracking branch 'cd/master'

This commit is contained in:
makefu 2016-02-22 14:35:59 +01:00
commit b25d15573a
54 changed files with 1418 additions and 1120 deletions

View File

@ -1,5 +1,32 @@
ifndef system stockholm ?= .
$(error unbound variable: system)
ifndef nixos-config
$(if $(system),,$(error unbound variable: system))
nixos-config = ./$(LOGNAME)/1systems/$(system).nix
endif
# target = [target_user@]target_host[:target_port][/target_path]
ifdef target
_target_user != echo $(target) | sed -n 's/@.*//p'
_target_path != echo $(target) | sed -n 's/^[^/]*//p'
_target_port != echo $(target) | sed -En 's|^.*:([^/]*)(/.*)?$$|\1|p'
_target_host != echo $(target) | sed -En 's/^(.*@)?([^:/]*).*/\2/p'
ifneq ($(_target_host),)
$(if $(target_host),$(error cannot define both, target_host and host in target))
target_host ?= $(_target_host)
endif
ifneq ($(_target_user),)
$(if $(target_user),$(error cannot define both, target_user and user in target))
target_user ?= $(_target_user)
endif
ifneq ($(_target_port),)
$(if $(target_port),$(error cannot define both, target_port and port in target))
target_port ?= $(_target_port)
endif
ifneq ($(_target_path),)
$(if $(target_path),$(error cannot define both, target_path and path in target))
target_path ?= $(_target_path)
endif
endif endif
export target_host ?= $(system) export target_host ?= $(system)
@ -7,29 +34,37 @@ export target_user ?= root
export target_port ?= 22 export target_port ?= 22
export target_path ?= /var/src export target_path ?= /var/src
$(if $(target_host),,$(error unbound variable: target_host))
$(if $(target_user),,$(error unbound variable: target_user))
$(if $(target_port),,$(error unbound variable: target_port))
$(if $(target_path),,$(error unbound variable: target_path))
evaluate = \ evaluate = \
nix-instantiate \ nix-instantiate \
--eval \ --eval \
--readonly-mode \ --readonly-mode \
--show-trace \ --show-trace \
-I nixos-config=./$(LOGNAME)/1systems/$(system).nix \ -I nixos-config=$(nixos-config) \
-I stockholm=. \ -I stockholm=$(stockholm) \
$(1) -E '{ eval, f }: f eval' \
--arg eval 'import ./.' \
--arg f "eval@{ config, ... }: $(1)"
execute = \ execute = \
result=$$($(call evaluate,-A config.krebs.build.$(1) --json)) && \ result=$$($(call evaluate,config.krebs.build.$(1))) && \
script=$$(echo "$$result" | jq -r .) && \ script=$$(echo "$$result" | jq -r .) && \
echo "$$script" | sh echo "$$script" | PS5=% sh
# usage: make deploy system=foo [target_host=bar] # usage: make deploy system=foo [target_host=bar]
deploy: ssh ?= ssh
deploy: deploy:
$(call execute,populate) $(call execute,populate)
ssh $(target_user)@$(target_host) -p $(target_port) \ $(ssh) $(target_user)@$(target_host) -p $(target_port) \
nixos-rebuild switch --show-trace -I $(target_path) nixos-rebuild switch --show-trace -I $(target_path)
# usage: make LOGNAME=shared system=wolf eval.config.krebs.build.host.name # usage: make LOGNAME=shared system=wolf eval.config.krebs.build.host.name
eval eval.:;@$(call evaluate) eval eval.:;@$(call evaluate,$${expr-eval})
eval.%:;@$(call evaluate,-A $*) eval.%:;@$(call evaluate,$*)
# usage: make install system=foo [target_host=bar] # usage: make install system=foo [target_host=bar]
install: ssh ?= ssh -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null install: ssh ?= ssh -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null
@ -41,3 +76,21 @@ install:
$(ssh) $(target_user)@$(target_host) -p $(target_port) \ $(ssh) $(target_user)@$(target_host) -p $(target_port) \
env NIXOS_CONFIG=$(target_path)/nixos-config \ env NIXOS_CONFIG=$(target_path)/nixos-config \
nixos-install nixos-install
# usage: make test system=foo [target=bar] [method={eval,build}]
method ?= eval
ifeq ($(method),build)
test: command = nix-build --no-out-link
else
ifeq ($(method),eval)
test: command ?= nix-instantiate --eval --json --readonly-mode --strict
else
$(error bad method: $(method))
endif
endif
test: ssh ?= ssh
test:
$(call execute,populate)
$(ssh) $(target_user)@$(target_host) -p $(target_port) \
$(command) --show-trace -I $(target_path) \
-A config.system.build.toplevel $(target_path)/stockholm

View File

@ -117,6 +117,14 @@ let
"$dst_user@$dst_host" \ "$dst_user@$dst_host" \
-T "$with_dst_path_lock_script" -T "$with_dst_path_lock_script"
} }
rsh="ssh -F /dev/null -i $identity ''${dst_port:+-p $dst_port}"
local_rsync() {
rsync "$@"
}
remote_rsync=${shell.escape (concatStringsSep " && " [
"mkdir -m 0700 -p ${shell.escape plan.dst.path}/current"
"exec flock -n ${shell.escape plan.dst.path} rsync"
])}
''; '';
pull = '' pull = ''
identity=${shell.escape plan.dst.host.ssh.privkey.path} identity=${shell.escape plan.dst.host.ssh.privkey.path}
@ -131,6 +139,12 @@ let
dst_shell() { dst_shell() {
eval "$with_dst_path_lock_script" eval "$with_dst_path_lock_script"
} }
rsh="ssh -F /dev/null -i $identity ''${src_port:+-p $src_port}"
local_rsync() {
mkdir -m 0700 -p ${shell.escape plan.dst.path}/current
flock -n ${shell.escape plan.dst.path} rsync "$@"
}
remote_rsync=rsync
''; '';
}} }}
# Note that this only works because we trust date +%s to produce output # Note that this only works because we trust date +%s to produce output
@ -140,13 +154,10 @@ let
with_dst_path_lock_script="exec env start_date=$(date +%s) "${shell.escape with_dst_path_lock_script="exec env start_date=$(date +%s) "${shell.escape
"flock -n ${shell.escape plan.dst.path} /bin/sh" "flock -n ${shell.escape plan.dst.path} /bin/sh"
} }
rsync >&2 \ local_rsync >&2 \
-aAXF --delete \ -aAXF --delete \
-e "ssh -F /dev/null -i $identity ''${dst_port:+-p $dst_port}" \ --rsh="$rsh" \
--rsync-path ${shell.escape (concatStringsSep " && " [ --rsync-path="$remote_rsync" \
"mkdir -m 0700 -p ${shell.escape plan.dst.path}/current"
"exec flock -n ${shell.escape plan.dst.path} rsync"
])} \
--link-dest="$dst_path/current" \ --link-dest="$dst_path/current" \
"$src/" \ "$src/" \
"$dst/.partial" "$dst/.partial"

View File

@ -20,35 +20,19 @@ let
type = types.user; type = types.user;
}; };
options.krebs.build.source = let options.krebs.build.source = mkOption {
raw = types.either types.str types.path; type = with types; attrsOf (either str (submodule {
url = types.submodule {
options = { options = {
url = mkOption { url = str;
type = types.str; rev = str;
}; };
rev = mkOption { }));
type = types.str;
};
dev = mkOption {
type = types.str;
};
};
};
in mkOption {
type = types.attrsOf (types.either types.str url);
apply = let f = mapAttrs (_: value: {
string = value;
path = toString value;
set = f value;
}.${typeOf value}); in f;
default = {}; default = {};
}; };
options.krebs.build.populate = mkOption { options.krebs.build.populate = mkOption {
type = types.str; type = types.str;
default = let default = let
source = config.krebs.build.source;
target-user = maybeEnv "target_user" "root"; target-user = maybeEnv "target_user" "root";
target-host = maybeEnv "target_host" config.krebs.build.host.name; target-host = maybeEnv "target_host" config.krebs.build.host.name;
target-port = maybeEnv "target_port" "22"; target-port = maybeEnv "target_port" "22";
@ -57,13 +41,16 @@ let
#! /bin/sh #! /bin/sh
set -eu set -eu
ssh=''${ssh-ssh}
verbose() { verbose() {
printf '+%s\n' "$(printf ' %q' "$@")" >&2 printf '%s%s\n' "$PS5$(printf ' %q' "$@")" >&2
"$@" "$@"
} }
echo ${shell.escape git-script} \ { printf 'PS5=%q%q\n' @ "$PS5"
| ssh -p ${shell.escape target-port} \ echo ${shell.escape git-script}
} | verbose $ssh -p ${shell.escape target-port} \
${shell.escape "${target-user}@${target-host}"} -T ${shell.escape "${target-user}@${target-host}"} -T
unset tmpdir unset tmpdir
@ -75,61 +62,34 @@ let
tmpdir=$(mktemp -dt stockholm.XXXXXXXX) tmpdir=$(mktemp -dt stockholm.XXXXXXXX)
chmod 0755 "$tmpdir" chmod 0755 "$tmpdir"
${concatStringsSep "\n" ${concatStringsSep "\n" (mapAttrsToList (name: symlink: ''
(mapAttrsToList verbose ln -s ${shell.escape symlink.target} \
(name: spec: let dst = removePrefix "symlink:" (get-url spec); in "$tmpdir"/${shell.escape name}
"verbose ln -s ${shell.escape dst} $tmpdir/${shell.escape name}") '') source-by-method.symlink)}
symlink-specs)}
verbose proot \ verbose proot \
-b $tmpdir:${shell.escape target-path} \ -b "$tmpdir":${shell.escape target-path} \
${concatStringsSep " \\\n " ${concatStringsSep " \\\n " (mapAttrsToList (name: file:
(mapAttrsToList "-b ${shell.escape "${file.path}:${target-path}/${name}"}"
(name: spec: ) source-by-method.file)} \
"-b ${shell.escape "${get-url spec}:${target-path}/${name}"}")
file-specs)} \
rsync \ rsync \
-f ${shell.escape "P /*"} \ -f ${shell.escape "P /*"} \
${concatMapStringsSep " \\\n " ${concatMapStringsSep " \\\n " (name:
(name: "-f ${shell.escape "R /${name}"}") "-f ${shell.escape "R /${name}"}"
(attrNames file-specs)} \ ) (attrNames source-by-method.file)} \
--delete \ --delete \
-vFrlptD \ -vFrlptD \
-e ${shell.escape "ssh -p ${target-port}"} \ -e "$ssh -p ${shell.escape target-port}" \
${shell.escape target-path}/ \ ${shell.escape target-path}/ \
${shell.escape "${target-user}@${target-host}:${target-path}"} ${shell.escape "${target-user}@${target-host}:${target-path}"}
''; '';
get-schema = uri:
if substring 0 1 uri == "/"
then "file"
else head (splitString ":" uri);
has-schema = schema: uri: get-schema uri == schema;
get-url = spec: {
string = spec;
path = toString spec;
set = get-url spec.url;
}.${typeOf spec};
git-specs =
filterAttrs (_: spec: has-schema "https" (get-url spec)) source //
filterAttrs (_: spec: has-schema "http" (get-url spec)) source //
filterAttrs (_: spec: has-schema "git" (get-url spec)) source;
file-specs =
filterAttrs (_: spec: has-schema "file" (get-url spec)) source;
symlink-specs =
filterAttrs (_: spec: has-schema "symlink" (get-url spec)) source;
git-script = '' git-script = ''
#! /bin/sh #! /bin/sh
set -efu set -efu
verbose() { verbose() {
printf '+%s\n' "$(printf ' %q' "$@")" >&2 printf '%s%s\n' "$PS5$(printf ' %q' "$@")" >&2
"$@" "$@"
} }
@ -156,26 +116,48 @@ let
if ! test "$(git log --format=%H -1)" = "$hash"; then if ! test "$(git log --format=%H -1)" = "$hash"; then
git fetch origin git fetch origin
git checkout "$hash" -- "$dst_dir" git checkout "$hash" -- "$dst_dir"
git checkout "$hash" git checkout -f "$hash"
fi fi
git clean -dxf git clean -dxf
)} )}
${concatStringsSep "\n" ${concatStringsSep "\n" (mapAttrsToList (name: git: ''
(mapAttrsToList verbose fetch_git ${concatMapStringsSep " " shell.escape [
(name: spec: toString (map shell.escape [
"verbose"
"fetch_git"
"${target-path}/${name}" "${target-path}/${name}"
spec.url git.url
spec.rev git.rev
])) ]}
git-specs)} '') source-by-method.git)}
''; '';
in out; in out;
}; };
}; };
source-by-method = let
known-methods = ["git" "file" "symlink"];
in genAttrs known-methods (const {}) // recursiveUpdate source-by-scheme {
git = source-by-scheme.http or {} //
source-by-scheme.https or {};
};
source-by-scheme = foldl' (out: { k, v }: recursiveUpdate out {
${v.scheme}.${k} = v;
}) {} (mapAttrsToList (k: v: { inherit k v; }) normalized-source);
normalized-source = mapAttrs (name: let f = x: getAttr (typeOf x) {
path = f (toString x);
string = f {
url = if substring 0 1 x == "/" then "file://${x}" else x;
};
set = let scheme = head (splitString ":" x.url); in recursiveUpdate x {
inherit scheme;
} // {
symlink.target = removePrefix "symlink:" x.url;
file.path = # TODO file://host/...
assert hasPrefix "file:///" x.url;
removePrefix "file://" x.url;
}.${scheme} or {};
}; in f) config.krebs.build.source;
in out in out

View File

@ -28,6 +28,7 @@ let
./realwallpaper.nix ./realwallpaper.nix
./retiolum-bootstrap.nix ./retiolum-bootstrap.nix
./retiolum.nix ./retiolum.nix
./secret.nix
./setuid.nix ./setuid.nix
./tinc_graphs.nix ./tinc_graphs.nix
./urlwatch.nix ./urlwatch.nix
@ -42,9 +43,7 @@ let
dns = { dns = {
providers = mkOption { providers = mkOption {
# TODO with types; tree dns.label dns.provider, so we can merge. type = with types; attrsOf str;
# Currently providers can only be merged if aliases occur just once.
type = with types; attrsOf unspecified;
}; };
}; };
@ -94,7 +93,7 @@ let
{ krebs = import ./tv { inherit config lib; }; } { krebs = import ./tv { inherit config lib; }; }
{ {
krebs.dns.providers = { krebs.dns.providers = {
de.krebsco = "zones"; "krebsco.de" = "zones";
gg23 = "hosts"; gg23 = "hosts";
shack = "hosts"; shack = "hosts";
i = "hosts"; i = "hosts";
@ -103,13 +102,27 @@ let
retiolum = "hosts"; retiolum = "hosts";
}; };
networking.extraHosts = concatStringsSep "\n" (flatten ( krebs.users = {
krebs = {
home = "/krebs";
mail = "spam@krebsco.de";
};
root = {
home = "/root";
pubkey = config.krebs.build.host.ssh.pubkey;
uid = 0;
};
};
networking.extraHosts = let
domains = attrNames (filterAttrs (_: eq "hosts") cfg.dns.providers);
check = hostname: any (domain: hasSuffix ".${domain}" hostname) domains;
in concatStringsSep "\n" (flatten (
mapAttrsToList (hostname: host: mapAttrsToList (hostname: host:
mapAttrsToList (netname: net: mapAttrsToList (netname: net:
let let
aliases = longs ++ shorts; aliases = longs ++ shorts;
providers = dns.split-by-provider net.aliases cfg.dns.providers; longs = filter check net.aliases;
longs = providers.hosts;
shorts = let s = ".${cfg.search-domain}"; in shorts = let s = ".${cfg.search-domain}"; in
map (removeSuffix s) (filter (hasSuffix s) longs); map (removeSuffix s) (filter (hasSuffix s) longs);
in in
@ -130,12 +143,11 @@ let
{ text=(stripEmptyLines value); }) all-zones; { text=(stripEmptyLines value); }) all-zones;
krebs.exim-smarthost.internet-aliases = let krebs.exim-smarthost.internet-aliases = let
format = from: to: format = from: to: {
inherit from;
# TODO assert is-retiolum-mail-address to; # TODO assert is-retiolum-mail-address to;
{ inherit from; to = concatMapStringsSep "," (getAttr "mail") (toList to);
to = if typeOf to == "list" };
then concatMapStringsSep "," (getAttr "mail") to
else to.mail; };
in mapAttrsToList format (with config.krebs.users; let in mapAttrsToList format (with config.krebs.users; let
spam-ml = [ spam-ml = [
lass lass
@ -154,6 +166,10 @@ let
"makefu@retiolum" = makefu; "makefu@retiolum" = makefu;
"spam@retiolum" = spam-ml; "spam@retiolum" = spam-ml;
"tv@retiolum" = tv; "tv@retiolum" = tv;
"lass@r" = lass;
"makefu@r" = makefu;
"spam@r" = spam-ml;
"tv@r" = tv;
}); });
services.openssh.hostKeys = services.openssh.hostKeys =

View File

@ -11,6 +11,24 @@ let
api = { api = {
enable = mkEnableOption "krebs.exim-retiolum"; enable = mkEnableOption "krebs.exim-retiolum";
local_domains = mkOption {
type = with types; listOf hostname;
default = ["localhost"] ++ config.krebs.build.host.nets.retiolum.aliases;
};
primary_hostname = mkOption {
type = types.str;
default = let x = "${config.krebs.build.host.name}.r"; in
assert elem x config.krebs.build.host.nets.retiolum.aliases;
x;
};
relay_to_domains = mkOption {
# TODO hostname with wildcards
type = with types; listOf str;
default = [
"*.r"
"*.retiolum"
];
};
}; };
imp = { imp = {
@ -21,9 +39,9 @@ let
# TODO modular configuration # TODO modular configuration
assert config.krebs.retiolum.enable; assert config.krebs.retiolum.enable;
'' ''
primary_hostname = ${retiolumHostname} primary_hostname = ${cfg.primary_hostname}
domainlist local_domains = @ : localhost domainlist local_domains = ${concatStringsSep ":" cfg.local_domains}
domainlist relay_to_domains = *.retiolum domainlist relay_to_domains = ${concatStringsSep ":" cfg.relay_to_domains}
hostlist relay_from_hosts = <; 127.0.0.1 ; ::1 hostlist relay_from_hosts = <; 127.0.0.1 ; ::1
acl_smtp_rcpt = acl_check_rcpt acl_smtp_rcpt = acl_check_rcpt
@ -85,7 +103,7 @@ let
retiolum: retiolum:
driver = manualroute driver = manualroute
domains = ! ${retiolumHostname} : *.retiolum domains = ! +local_domains : +relay_to_domains
transport = remote_smtp transport = remote_smtp
route_list = ^.* $0 byname route_list = ^.* $0 byname
no_more no_more
@ -125,7 +143,7 @@ let
# mode = 0660 # mode = 0660
begin retry begin retry
*.retiolum * F,42d,1m ${concatMapStringsSep "\n" (k: "${k} * F,42d,1m") cfg.relay_to_domains}
* * F,2h,15m; G,16h,1h,1.5; F,4d,6h * * F,2h,15m; G,16h,1h,1.5; F,4d,6h
begin rewrite begin rewrite
@ -134,8 +152,4 @@ let
''; '';
}; };
}; };
in out
# TODO get the hostname from somewhere else.
retiolumHostname = "${config.networking.hostName}.retiolum";
in
out

View File

@ -25,14 +25,31 @@ let
})); }));
}; };
local_domains = mkOption {
type = with types; listOf hostname;
default = ["localhost"] ++ config.krebs.build.host.nets.retiolum.aliases;
};
relay_from_hosts = mkOption { relay_from_hosts = mkOption {
type = with types; listOf str; type = with types; listOf str;
default = []; default = [];
apply = xs: ["127.0.0.1" "::1"] ++ xs;
};
relay_to_domains = mkOption {
# TODO hostname with wildcards
type = with types; listOf str;
default = [
"*.r"
"*.retiolum"
];
}; };
primary_hostname = mkOption { primary_hostname = mkOption {
type = types.str; type = types.str;
default = "${config.networking.hostName}.retiolum"; default = let x = "${config.krebs.build.host.name}.r"; in
assert elem x config.krebs.build.host.nets.retiolum.aliases;
x;
}; };
sender_domains = mkOption { sender_domains = mkOption {
@ -63,19 +80,11 @@ let
# HOST_REDIR contains the real destinations for "local_domains". # HOST_REDIR contains the real destinations for "local_domains".
#HOST_REDIR = /etc/exim4/host_redirect #HOST_REDIR = /etc/exim4/host_redirect
# Domains not listed in local_domains need to be deliverable remotely. # Domains not listed in local_domains need to be deliverable remotely.
# XXX We abuse local_domains to mean "domains, we're the gateway for". # XXX We abuse local_domains to mean "domains, we're the gateway for".
domainlist local_domains = @ : localhost domainlist local_domains = ${concatStringsSep ":" cfg.local_domains}
domainlist relay_to_domains = domainlist relay_to_domains = ${concatStringsSep ":" cfg.relay_to_domains}
hostlist relay_from_hosts = <;${concatStringsSep ";" ( hostlist relay_from_hosts = <;${concatStringsSep ";" cfg.relay_from_hosts}
[
"127.0.0.1"
"::1"
]
++
cfg.relay_from_hosts
)}
acl_smtp_rcpt = acl_check_rcpt acl_smtp_rcpt = acl_check_rcpt
acl_smtp_data = acl_check_data acl_smtp_data = acl_check_data
@ -144,7 +153,7 @@ let
retiolum: retiolum:
debug_print = "R: retiolum for $local_part@$domain" debug_print = "R: retiolum for $local_part@$domain"
driver = manualroute driver = manualroute
domains = ! ${cfg.primary_hostname} : *.retiolum domains = ! +local_domains : +relay_to_domains
transport = retiolum_smtp transport = retiolum_smtp
route_list = ^.* $0 byname route_list = ^.* $0 byname
no_more no_more
@ -197,7 +206,10 @@ let
return_path_add return_path_add
begin retry begin retry
*.retiolum * F,42d,1m ${concatMapStringsSep "\n" (k: "${k} * F,42d,1m") cfg.relay_to_domains}
${concatMapStringsSep "\n" (k: "${k} * F,42d,1m")
# TODO don't include relay_to_domains
(map (getAttr "from") cfg.internet-aliases)}
* * F,2h,15m; G,16h,1h,1.5; F,4d,6h * * F,2h,15m; G,16h,1h,1.5; F,4d,6h
begin rewrite begin rewrite

View File

@ -232,13 +232,15 @@ let
]) (filter (rule: rule.perm.allow-receive-ref != null) cfg.rules)); ]) (filter (rule: rule.perm.allow-receive-ref != null) cfg.rules));
}; };
users.extraUsers = singleton rec { # TODO cfg.user
users.users.git = rec {
description = "Git repository hosting user"; description = "Git repository hosting user";
name = "git"; name = "git";
shell = "/bin/sh"; shell = "/bin/sh";
openssh.authorizedKeys.keys = openssh.authorizedKeys.keys =
mapAttrsToList (_: makeAuthorizedKey git-ssh-command) mapAttrsToList (_: makeAuthorizedKey git-ssh-command)
config.krebs.users; (filterAttrs (_: user: isString user.pubkey)
config.krebs.users);
uid = genid name; uid = genid name;
}; };
}; };

View File

@ -3,7 +3,7 @@
with config.krebs.lib; with config.krebs.lib;
{ {
hosts = { hosts = mapAttrs (_: setAttr "owner" config.krebs.users.lass) {
dishfire = { dishfire = {
cores = 4; cores = 4;
nets = rec { nets = rec {

View File

@ -10,6 +10,6 @@ let
type = types.attrs; type = types.attrs;
}; };
imp = { imp = {
krebs.lib = lib // import ../4lib { inherit lib; } // builtins; krebs.lib = lib // import ../4lib { inherit config lib; } // builtins;
}; };
in out in out

View File

@ -3,7 +3,7 @@
with config.krebs.lib; with config.krebs.lib;
{ {
hosts = { hosts = mapAttrs (_: setAttr "owner" config.krebs.users.makefu) {
pnp = { pnp = {
cores = 1; cores = 1;
nets = { nets = {

View File

@ -3,7 +3,7 @@
with config.krebs.lib; with config.krebs.lib;
{ {
hosts = { hosts = mapAttrs (_: setAttr "owner" config.krebs.users.miefda) {
bobby = { bobby = {
cores = 4; cores = 4;
nets = { nets = {

View File

@ -3,7 +3,7 @@
with config.krebs.lib; with config.krebs.lib;
{ {
hosts = { hosts = mapAttrs (_: setAttr "owner" config.krebs.users.mv) {
stro = { stro = {
cores = 4; cores = 4;
nets = { nets = {

39
krebs/3modules/secret.nix Normal file
View File

@ -0,0 +1,39 @@
{ config, lib, pkgs, ... }@args: with config.krebs.lib; let
cfg = config.krebs.secret;
in {
options.krebs.secret = {
files = mkOption {
type = with types; attrsOf secret-file;
default = {};
};
};
config = lib.mkIf (cfg.files != {}) {
systemd.services.secret = let
# TODO fail if two files have the same path but differ otherwise
files = unique (map (flip removeAttrs ["_module"])
(attrValues cfg.files));
in {
serviceConfig = {
Type = "oneshot";
RemainAfterExit = "yes";
SyslogIdentifier = "secret";
ExecStart = pkgs.writeDash "install-secret-files" ''
exit_code=0
${concatMapStringsSep "\n" (file: ''
${pkgs.coreutils}/bin/install \
-D \
--compare \
--verbose \
--mode=${shell.escape file.mode} \
--owner=${shell.escape file.owner.name} \
--group=${shell.escape file.group-name} \
${shell.escape file.source-path} \
${shell.escape file.path} \
|| exit_code=1
'') files}
exit $exit_code
'';
};
};
};
}

View File

@ -15,6 +15,7 @@ let
addrs4 = ["10.243.111.111"]; addrs4 = ["10.243.111.111"];
addrs6 = ["42:0:0:0:0:0:0:7357"]; addrs6 = ["42:0:0:0:0:0:0:7357"];
aliases = [ aliases = [
"test.r"
"test.retiolum" "test.retiolum"
]; ];
tinc.pubkey = '' tinc.pubkey = ''

View File

@ -4,9 +4,9 @@ with config.krebs.lib;
{ {
dns.providers = { dns.providers = {
de.viljetic = "regfish"; "viljetic.de" = "regfish";
}; };
hosts = { hosts = mapAttrs (_: setAttr "owner" config.krebs.users.tv) {
cd = rec { cd = rec {
cores = 2; cores = 2;
extraZones = { extraZones = {
@ -352,8 +352,9 @@ with config.krebs.lib;
pubkey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGer9e2+Lew7vnisgBbsFNECEIkpNJgEaqQqgb9inWkQ mv@vod"; pubkey = "ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIGer9e2+Lew7vnisgBbsFNECEIkpNJgEaqQqgb9inWkQ mv@vod";
}; };
tv = { tv = {
mail = "tv@wu.retiolum"; mail = "tv@nomic.retiolum";
pubkey = "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAEAQDFR//RnCvEZAt0F6ExDsatKZ/DDdifanuSL360mqOhaFieKI34RoOwfQT9T+Ga52Vh5V2La6esvlph686EdgzeKLvDoxEwFM9ZYFBcMrNzu4bMTlgE7YUYw5JiORyXNfznBGnme6qpuvx9ibYhUyiZo99kM8ys5YrUHrP2JXQJMezDFZHxT4GFMOuSdh/1daGoKKD6hYL/jEHX8CI4E3BSmKK6ygYr1fVX0K0Tv77lIi5mLXucjR7CytWYWYnhM6DC3Hxpv2zRkPgf3k0x/Y1hrw3V/r0Me5h90pd2C8pFaWA2ZoUT/fmyVqvx1tZPYToU/O2dMItY0zgx2kR0yD+6g7Aahz3R+KlXkV8k5c8bbTbfGnZWDR1ZlbLRM9Yt5vosfwapUD90MmVkpmR3wUkO2sUKi80QfC7b4KvSDXQ+MImbGxMaU5Bnsq1PqLN95q+uat3nlAVBAELkcx51FlE9CaIS65y4J7FEDg8BE5JeuCNshh62VSYRXVSFt8bk3f/TFGgzC8OIo14BhVmiRQQ503Z1sROyf5xLX2a/EJavMm1i2Bs2TH6ROKY9z5Pz8hT5US0r381V8oG7TZyLF9HTtoy3wCYsgWA5EmLanjAsVU2YEeAA0rxzdtYP8Y2okFiJ6u+M4HQZ3Wg3peSodyp3vxdYce2vk4EKeqEFuuS82850DYb7Et7fmp+wQQUT8Q/bMO0DreWjHoMM5lE4LJ4ME6AxksmMiFtfo/4Fe2q9D+LAqZ+ANOcv9M+8Rn6ngiYmuRNd0l/a02q1PEvO6vTfXgcl4f7Z1IULHPEaDNZHCJS1K5RXYFqYQ6OHsTmOm7hnwaRAS97+VFMo1i5uvTx9nYaAcY7yzq3Ckfb67dMBKApGOpJpkvPgfrP7bgBO5rOZXM1opXqVPb09nljAhhAhyCTh1e/8+mJrBo0cLQ/LupQzVxGDgm3awSMPxsZAN45PSWz76zzxdDa1MMo51do+VJHfs7Wl0NcXAQrniOBYL9Wqt0qNkn1gY5smkkISGeQ/vxNap4MmzeZE7b5fpOy+2fpcRVQLpc4nooQzJvSVTFz+25lgZ6iHf45K87gQFMIAri1Pf/EDDpL87az+bRWvWi+BA2kMe1kf+Ay1LyMz8r+g51H0ma0bNFh6+fbWMfUiD9JCepIObclnUJ4NlWfcgHxTf17d/4tl6z4DTcLpCCk8Da77JouSHgvtcRbRlFV1OfhWZLXUsrlfpaQTiItv6TGIr3k7+7b66o3Qw/GQVs5GmYifaIZIz8n8my4XjkaMBd0SZfBzzvFjHMq6YUP9+SbjvReqofuoO+5tW1wTYZXitFFBfwuHlXm6w77K5QDBW6olT7pat41/F5eGxLcz tv@wu"; pubkey = "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAEAQDFR//RnCvEZAt0F6ExDsatKZ/DDdifanuSL360mqOhaFieKI34RoOwfQT9T+Ga52Vh5V2La6esvlph686EdgzeKLvDoxEwFM9ZYFBcMrNzu4bMTlgE7YUYw5JiORyXNfznBGnme6qpuvx9ibYhUyiZo99kM8ys5YrUHrP2JXQJMezDFZHxT4GFMOuSdh/1daGoKKD6hYL/jEHX8CI4E3BSmKK6ygYr1fVX0K0Tv77lIi5mLXucjR7CytWYWYnhM6DC3Hxpv2zRkPgf3k0x/Y1hrw3V/r0Me5h90pd2C8pFaWA2ZoUT/fmyVqvx1tZPYToU/O2dMItY0zgx2kR0yD+6g7Aahz3R+KlXkV8k5c8bbTbfGnZWDR1ZlbLRM9Yt5vosfwapUD90MmVkpmR3wUkO2sUKi80QfC7b4KvSDXQ+MImbGxMaU5Bnsq1PqLN95q+uat3nlAVBAELkcx51FlE9CaIS65y4J7FEDg8BE5JeuCNshh62VSYRXVSFt8bk3f/TFGgzC8OIo14BhVmiRQQ503Z1sROyf5xLX2a/EJavMm1i2Bs2TH6ROKY9z5Pz8hT5US0r381V8oG7TZyLF9HTtoy3wCYsgWA5EmLanjAsVU2YEeAA0rxzdtYP8Y2okFiJ6u+M4HQZ3Wg3peSodyp3vxdYce2vk4EKeqEFuuS82850DYb7Et7fmp+wQQUT8Q/bMO0DreWjHoMM5lE4LJ4ME6AxksmMiFtfo/4Fe2q9D+LAqZ+ANOcv9M+8Rn6ngiYmuRNd0l/a02q1PEvO6vTfXgcl4f7Z1IULHPEaDNZHCJS1K5RXYFqYQ6OHsTmOm7hnwaRAS97+VFMo1i5uvTx9nYaAcY7yzq3Ckfb67dMBKApGOpJpkvPgfrP7bgBO5rOZXM1opXqVPb09nljAhhAhyCTh1e/8+mJrBo0cLQ/LupQzVxGDgm3awSMPxsZAN45PSWz76zzxdDa1MMo51do+VJHfs7Wl0NcXAQrniOBYL9Wqt0qNkn1gY5smkkISGeQ/vxNap4MmzeZE7b5fpOy+2fpcRVQLpc4nooQzJvSVTFz+25lgZ6iHf45K87gQFMIAri1Pf/EDDpL87az+bRWvWi+BA2kMe1kf+Ay1LyMz8r+g51H0ma0bNFh6+fbWMfUiD9JCepIObclnUJ4NlWfcgHxTf17d/4tl6z4DTcLpCCk8Da77JouSHgvtcRbRlFV1OfhWZLXUsrlfpaQTiItv6TGIr3k7+7b66o3Qw/GQVs5GmYifaIZIz8n8my4XjkaMBd0SZfBzzvFjHMq6YUP9+SbjvReqofuoO+5tW1wTYZXitFFBfwuHlXm6w77K5QDBW6olT7pat41/F5eGxLcz tv@wu";
uid = 1337; # TODO use default
}; };
tv-nomic = { tv-nomic = {
inherit (tv) mail; inherit (tv) mail;

View File

@ -3,7 +3,6 @@
# TODO multiple users # TODO multiple users
# TODO inform about unused caches # TODO inform about unused caches
# cache = url: "${cfg.dataDir}/.urlwatch/cache/${hashString "sha1" url}" # cache = url: "${cfg.dataDir}/.urlwatch/cache/${hashString "sha1" url}"
# TODO hooks.py
with config.krebs.lib; with config.krebs.lib;
let let
@ -32,6 +31,14 @@ let
Content of the From: header of the generated mails. Content of the From: header of the generated mails.
''; '';
}; };
# TODO hooks :: attrsOf hook
hooksFile = mkOption {
type = with types; nullOr path;
default = null;
description = ''
File to use as hooks.py module.
'';
};
mailto = mkOption { mailto = mkOption {
type = types.str; type = types.str;
default = config.krebs.build.user.mail; default = config.krebs.build.user.mail;
@ -48,7 +55,7 @@ let
''; '';
}; };
urls = mkOption { urls = mkOption {
type = with types; listOf str; type = with types; listOf (either str subtypes.job);
default = []; default = [];
description = "URL to watch."; description = "URL to watch.";
example = [ example = [
@ -56,7 +63,10 @@ let
]; ];
apply = map (x: getAttr (typeOf x) { apply = map (x: getAttr (typeOf x) {
set = x; set = x;
string.url = x; string = {
url = x;
filter = null;
};
}); });
}; };
verbose = mkOption { verbose = mkOption {
@ -68,9 +78,12 @@ let
}; };
}; };
urlsFile = toFile "urls" (concatMapStringsSep "\n---\n" toJSON cfg.urls); urlsFile = pkgs.writeText "urls"
(concatMapStringsSep "\n---\n" toJSON cfg.urls);
configFile = toFile "urlwatch.yaml" (toJSON { hooksFile = cfg.hooksFile;
configFile = pkgs.writeText "urlwatch.yaml" (toJSON {
display = { display = {
error = true; error = true;
new = true; new = true;
@ -127,10 +140,10 @@ let
User = user.name; User = user.name;
PermissionsStartOnly = "true"; PermissionsStartOnly = "true";
PrivateTmp = "true"; PrivateTmp = "true";
SyslogIdentifier = "urlwatch";
Type = "oneshot"; Type = "oneshot";
ExecStartPre = ExecStartPre =
pkgs.writeScript "urlwatch-prestart" '' pkgs.writeDash "urlwatch-prestart" ''
#! /bin/sh
set -euf set -euf
dataDir=$HOME dataDir=$HOME
@ -140,31 +153,29 @@ let
chown ${user.name}: "$dataDir" chown ${user.name}: "$dataDir"
fi fi
''; '';
ExecStart = pkgs.writeScript "urlwatch" '' ExecStart = pkgs.writeDash "urlwatch" ''
#! /bin/sh
set -euf set -euf
from=${escapeShellArg cfg.from}
mailto=${escapeShellArg cfg.mailto}
urlsFile=${escapeShellArg urlsFile}
configFile=${escapeShellArg configFile}
cd /tmp cd /tmp
urlwatch \ urlwatch \
${optionalString cfg.verbose "-v"} \ ${optionalString cfg.verbose "-v"} \
--urls="$urlsFile" \ --config=${shell.escape configFile} \
--config="$configFile" \ ${optionalString (hooksFile != null)
"--hooks=${shell.escape hooksFile}"
} \
--urls=${shell.escape urlsFile} \
> changes || : > changes || :
if test -s changes; then if test -s changes; then
date=$(date -R)
subject=$(sed -n 's/^\(CHANGED\|ERROR\|NEW\): //p' changes \
| tr \\n \ )
{ {
echo "Date: $date" echo Date: $(date -R)
echo "From: $from" echo From: ${shell.escape cfg.from}
echo "Subject: $subject" echo Subject: $(
echo "To: $mailto" sed -n 's/^\(CHANGED\|ERROR\|NEW\): //p' changes \
| tr '\n' ' '
)
echo To: ${shell.escape cfg.mailto}
echo echo
cat changes cat changes
} | /var/setuid-wrappers/sendmail -t } | /var/setuid-wrappers/sendmail -t
@ -181,5 +192,15 @@ let
name = "urlwatch"; name = "urlwatch";
uid = genid name; uid = genid name;
}; };
in
out subtypes.job = types.submodule {
options = {
url = mkOption {
type = types.str;
};
filter = mkOption {
type = with types; nullOr str; # TODO nullOr subtypes.filter
};
};
};
in out

View File

@ -1,4 +1,4 @@
{ lib, ... }: { config, lib, ... }:
with builtins; with builtins;
with lib; with lib;
@ -15,14 +15,15 @@ let out = rec {
addNames = mapAttrs addName; addNames = mapAttrs addName;
types = import ./types.nix { inherit lib; }; types = import ./types.nix {
inherit config;
lib = lib // { inherit genid; };
};
dir.has-default-nix = path: pathExists (path + "/default.nix"); dir.has-default-nix = path: pathExists (path + "/default.nix");
dns = import ./dns.nix { inherit lib; };
genid = import ./genid.nix { lib = lib // out; }; genid = import ./genid.nix { lib = lib // out; };
git = import ./git.nix { lib = lib // out; }; git = import ./git.nix { lib = lib // out; };
listset = import ./listset.nix { inherit lib; };
shell = import ./shell.nix { inherit lib; }; shell = import ./shell.nix { inherit lib; };
tree = import ./tree.nix { inherit lib; }; tree = import ./tree.nix { inherit lib; };

View File

@ -1,31 +0,0 @@
{ lib, ... }:
let
listset = import ./listset.nix { inherit lib; };
in
with builtins;
with lib;
rec {
# label = string
# TODO does it make sense to have alias = list label?
# split-by-provider :
# [[label]] -> tree label provider -> listset provider alias
split-by-provider = as: providers:
foldl (m: a: listset.insert (provider-of a providers) a m) {} as;
# provider-of : alias -> tree label provider -> provider
# Note that we cannot use tree.get here, because path can be longer
# than the tree depth.
provider-of = a:
let
go = path: tree:
if typeOf tree == "string"
then tree
else go (tail path) tree.${head path};
in
go (reverseList (splitString "." a));
}

View File

@ -184,26 +184,21 @@ prepare_common() {(
. /root/.nix-profile/etc/profile.d/nix.sh . /root/.nix-profile/etc/profile.d/nix.sh
for i in \ mkdir -p /mnt/"$target_path"
bash \ mkdir -p "$target_path"
coreutils \
# This line intentionally left blank.
do
if ! nix-env -q $i | grep -q .; then
nix-env -iA nixpkgs.pkgs.$i
fi
done
# install nixos-install if ! mountpoint "$target_path"; then
if ! type nixos-install 2>/dev/null; then mount --rbind /mnt/"$target_path" "$target_path"
nixpkgs_expr='import <nixpkgs> { system = builtins.currentSystem; }' fi
nixpkgs_path=$(find /nix/store -mindepth 1 -maxdepth 1 -name *-nixpkgs-* -type d)
nix-env \ mkdir -p bin
--arg config "{ nix.package = ($nixpkgs_expr).nix; }" \ rm -f bin/nixos-install
--arg pkgs "$nixpkgs_expr" \ cp "$(type -p nixos-install)" bin/nixos-install
--arg modulesPath 'throw "no modulesPath"' \ sed -i "s@^NIX_PATH=\"[^\"]*\"@NIX_PATH=$target_path@" bin/nixos-install
-f $nixpkgs_path/nixpkgs/nixos/modules/installer/tools/tools.nix \
-iA config.system.build.nixos-install if ! grep -q '^PATH.*#krebs' .bashrc; then
echo '. /root/.nix-profile/etc/profile.d/nix.sh' >> .bashrc
echo 'PATH=$HOME/bin:$PATH #krebs' >> .bashrc
fi fi
)} )}

View File

@ -1,11 +0,0 @@
{ lib, ... }:
with lib;
rec {
# listset k v = set k [v]
# insert : k -> v -> listset k v -> listset k v
insert = name: value: set:
set // { ${name} = set.${name} or [] ++ [value]; };
}

View File

@ -1,9 +1,14 @@
{ lib, ... }: { config, lib, ... }:
with builtins; with builtins;
with lib; with lib;
with types; with types;
let
# Inherited attributes are used in submodules that have their own `config`.
inherit (config.krebs) users;
in
types // rec { types // rec {
host = submodule ({ config, ... }: { host = submodule ({ config, ... }: {
@ -20,25 +25,17 @@ types // rec {
default = {}; default = {};
}; };
owner = mkOption {
type = user;
default = users.krebs;
};
extraZones = mkOption { extraZones = mkOption {
default = {}; default = {};
# TODO: string is either MX, NS, A or AAAA # TODO: string is either MX, NS, A or AAAA
type = with types; attrsOf string; type = with types; attrsOf string;
}; };
infest = {
addr = mkOption {
type = str;
apply = trace "Obsolete option `krebs.hosts.${config.name}.infest.addr' is used. It was replaced by the `target' argument to `make` or `get`. See Makefile for more information.";
};
port = mkOption {
type = int;
default = 22;
# TODO replacement: allow target with port, SSH-style: [lol]:666
apply = trace "Obsolete option `krebs.hosts.${config.name}.infest.port' is used. It's gone without replacement.";
};
};
secure = mkOption { secure = mkOption {
type = bool; type = bool;
default = false; default = false;
@ -147,6 +144,25 @@ types // rec {
merge = mergeOneOption; merge = mergeOneOption;
}; };
secret-file = submodule ({ config, ... }: {
options = {
path = mkOption { type = str; };
mode = mkOption { type = str; default = "0400"; };
owner = mkOption {
type = user;
default = config.krebs.users.root;
};
group-name = mkOption {
type = str;
default = "root";
};
source-path = mkOption {
type = str;
default = toString <secrets> + "/${config._module.args.name}";
};
};
});
suffixed-str = suffs: suffixed-str = suffs:
mkOptionType { mkOptionType {
name = "string suffixed by ${concatStringsSep ", " suffs}"; name = "string suffixed by ${concatStringsSep ", " suffs}";
@ -156,6 +172,10 @@ types // rec {
user = submodule ({ config, ... }: { user = submodule ({ config, ... }: {
options = { options = {
home = mkOption {
type = absolute-pathname;
default = "/home/${config.name}";
};
mail = mkOption { mail = mkOption {
type = str; # TODO retiolum mail address type = str; # TODO retiolum mail address
}; };
@ -164,7 +184,12 @@ types // rec {
default = config._module.args.name; default = config._module.args.name;
}; };
pubkey = mkOption { pubkey = mkOption {
type = str; type = nullOr str;
default = null;
};
uid = mkOption {
type = int;
default = genid config.name;
}; };
}; };
}); });
@ -217,6 +242,21 @@ types // rec {
merge = mergeOneOption; merge = mergeOneOption;
}; };
# POSIX.12013, 3.2 Absolute Pathname
# TODO normalize slashes
# TODO two slashes
absolute-pathname = mkOptionType {
name = "POSIX absolute pathname";
check = s: pathname.check s && substring 0 1 s == "/";
};
# POSIX.12013, 3.267 Pathname
# TODO normalize slashes
pathname = mkOptionType {
name = "POSIX pathname";
check = s: isString s && all filename.check (splitString "/" s);
};
# POSIX.1-2013, 3.431 User Name # POSIX.1-2013, 3.431 User Name
username = mkOptionType { username = mkOptionType {
name = "POSIX username"; name = "POSIX username";

View File

@ -1,12 +1,12 @@
{ stdenv, fetchgit, bc, cac-cert, coreutils, curl, dash, gnugrep, gnused, inotifyTools, jq, ncurses, openssh, sshpass, ... }: { stdenv, fetchgit, bc, cac-cert, coreutils, curl, dash, gnugrep, gnused, inotifyTools, jq, ncurses, openssh, sshpass, ... }:
stdenv.mkDerivation { stdenv.mkDerivation {
name = "cac-api-1.1.0"; name = "cac-api-1.1.2";
src = fetchgit { src = fetchgit {
url = http://cgit.cd.krebsco.de/cac-api; url = http://cgit.cd.krebsco.de/cac-api;
rev = "0809fae379239687ed1170e04311dc2880ef0aba"; rev = "67e93510e7742acae44db30275abbfe671aa9b7b";
sha256 = "357ced27c9ed88028967c934178a1d230bf38617a7494cd4632fabdd2a04fcdd"; sha256 = "1vxh57j7vrq5sg9j1sam0538kkkhqpgf230vvdz2ifzgkj01z27l";
}; };
phases = [ phases = [
@ -29,7 +29,7 @@ stdenv.mkDerivation {
ncurses ncurses
openssh openssh
sshpass sshpass
]} ]}:"$PATH"
EOF EOF
# [1]: Disable fetching tasks; listtasks is currently broken: # [1]: Disable fetching tasks; listtasks is currently broken:
# Unknown column 'iod.apitask.cid' in 'field list' # Unknown column 'iod.apitask.cid' in 'field list'

View File

@ -1,20 +1,21 @@
{ fetchgit, lib, stdenv { fetchgit, lib, stdenv
, coreutils , coreutils
, get
, git , git
, gnumake
, gnused , gnused
, jq , jq
, nix
, openssh , openssh
, parallel , parallel
, ... }: , ... }:
stdenv.mkDerivation { stdenv.mkDerivation {
name = "push-1.1.1"; name = "push-1.1.2";
src = fetchgit { src = fetchgit {
url = http://cgit.cd.krebsco.de/push; url = http://cgit.cd.krebsco.de/push;
rev = "ea8b76569c6b226fe148e559477669b095408472"; rev = "da5b3a4b05ef822cc41d36b6cc2071a2e78506d4";
sha256 = "c305a1515d30603f6ed825d44487e863fdc7d90400620ceaf2c335a3b5d1e221"; sha256 = "0gfxz207lm11g77rw02jcqpvzhx07j9hzgjgscbmslzl5r8icd6g";
}; };
phases = [ phases = [
@ -26,10 +27,11 @@ stdenv.mkDerivation {
let let
path = lib.makeSearchPath "bin" [ path = lib.makeSearchPath "bin" [
coreutils coreutils
get
git git
gnumake
gnused gnused
jq jq
nix
openssh openssh
parallel parallel
]; ];

View File

@ -1,4 +1,4 @@
# nix-shell -p gnumake jq openssh cac-api cac-panel # nix-shell -p gnumake jq openssh cac-api cac-panel sshpass
set -eufx set -eufx
# 2 secrets are required: # 2 secrets are required:
@ -99,7 +99,7 @@ defer "cac-api delete $id;$old_trapstr"
mkdir -p shared/2configs/temp mkdir -p shared/2configs/temp
cac-api generatenetworking $id > \ cac-api generatenetworking $id > \
shared/2configs/temp/networking.nix shared/2configs/temp/networking.nix
# new temporary ssh key we will use to log in after infest # new temporary ssh key we will use to log in after install
ssh-keygen -f $krebs_ssh -N "" ssh-keygen -f $krebs_ssh -N ""
cp $retiolum_key $krebs_secrets/retiolum.rsa_key.priv cp $retiolum_key $krebs_secrets/retiolum.rsa_key.priv
# we override the directories for secrets and stockholm # we override the directories for secrets and stockholm
@ -118,12 +118,12 @@ _: {
} }
EOF EOF
LOGNAME=shared make eval get=krebs.infest \ make install \
target=derp system=test-centos7 filter=json \ LOGNAME=shared \
| sed -e "s#^ssh.*<<#cac-api ssh $id<<#" \ SSHPASS="$(cac-api getserver $id | jq -r .rootpass)" \
-e "/^rsync/a -e 'cac-api ssh $id' \\\\" \ ssh='sshpass -e ssh -S none -o StrictHostKeyChecking=no -o UserKnownHostsFile=/dev/null' \
-e "s#root.derp:#:#" > $krebs_secrets/infest system=test-centos7 \
sh -x $krebs_secrets/infest target=$ip
# TODO: generate secrets directory $krebs_secrets for nix import # TODO: generate secrets directory $krebs_secrets for nix import
cac-api powerop $id reset cac-api powerop $id reset

View File

@ -8,6 +8,7 @@ with builtins;
../2configs/browsers.nix ../2configs/browsers.nix
../2configs/programs.nix ../2configs/programs.nix
../2configs/git.nix ../2configs/git.nix
../2configs/pass.nix
#{ #{
# users.extraUsers = { # users.extraUsers = {
# root = { # root = {
@ -17,6 +18,15 @@ with builtins;
# }; # };
# }; # };
#} #}
{
krebs.iptables = {
tables = {
filter.INPUT.rules = [
{ predicate = "-p tcp --dport 8000"; target = "ACCEPT"; precedence = 9001; }
];
};
};
}
]; ];
krebs.build.host = config.krebs.hosts.helios; krebs.build.host = config.krebs.hosts.helios;
@ -53,15 +63,6 @@ with builtins;
# SUBSYSTEM=="net", ATTR{address}=="f0:de:f1:b8:c8:2e", NAME="et0" # SUBSYSTEM=="net", ATTR{address}=="f0:de:f1:b8:c8:2e", NAME="et0"
#''; #'';
services.xserver = {
videoDriver = "intel";
vaapiDrivers = [ pkgs.vaapiIntel ];
deviceSection = ''
Option "AccelMethod" "sna"
BusID "PCI:0:2:0"
'';
};
services.xserver.synaptics = { services.xserver.synaptics = {
enable = true; enable = true;
twoFingerScroll = true; twoFingerScroll = true;

View File

@ -20,12 +20,12 @@
../2configs/git.nix ../2configs/git.nix
#../2configs/wordpress.nix #../2configs/wordpress.nix
../2configs/bitlbee.nix ../2configs/bitlbee.nix
../2configs/firefoxPatched.nix #../2configs/firefoxPatched.nix
../2configs/skype.nix ../2configs/skype.nix
../2configs/teamviewer.nix ../2configs/teamviewer.nix
../2configs/libvirt.nix ../2configs/libvirt.nix
../2configs/fetchWallpaper.nix ../2configs/fetchWallpaper.nix
../2configs/buildbot-standalone.nix #../2configs/buildbot-standalone.nix
{ {
#risk of rain port #risk of rain port
krebs.iptables.tables.filter.INPUT.rules = [ krebs.iptables.tables.filter.INPUT.rules = [
@ -97,6 +97,54 @@
# { predicate = "-i retiolum -p tcp --dport 80"; target = "ACCEPT"; precedence = 9998; } # { predicate = "-i retiolum -p tcp --dport 80"; target = "ACCEPT"; precedence = 9998; }
# ]; # ];
#} #}
{
containers.pythonenv = {
config = {
services.openssh.enable = true;
users.users.root.openssh.authorizedKeys.keys = [
config.krebs.users.lass.pubkey
];
environment = {
systemPackages = with pkgs; [
git
libxml2
libxslt
libzip
python27Full
python27Packages.buildout
stdenv
zlib
];
pathsToLink = [ "/include" ];
shellInit = ''
# help pip to find libz.so when building lxml
export LIBRARY_PATH=/var/run/current-system/sw/lib
# ditto for header files, e.g. sqlite
export C_INCLUDE_PATH=/var/run/current-system/sw/include
'';
};
};
};
}
{
services.mysql = {
enable = true;
package = pkgs.mariadb;
rootPassword = "<secrets>/mysql_rootPassword";
};
}
{
services.elasticsearch = {
enable = true;
plugins = [
pkgs.elasticsearchPlugins.elasticsearch_kopf
];
};
}
]; ];
krebs.build.host = config.krebs.hosts.mors; krebs.build.host = config.krebs.hosts.mors;
@ -170,6 +218,11 @@
device = "/dev/big/public"; device = "/dev/big/public";
fsType = "ext4"; fsType = "ext4";
}; };
"/mnt/conf" = {
device = "/dev/big/conf";
fsType = "ext4";
};
}; };
services.udev.extraRules = '' services.udev.extraRules = ''

View File

@ -58,7 +58,7 @@ in {
( createChromiumUser "cr" [ "audio" ] [ pkgs.chromium ] ) ( createChromiumUser "cr" [ "audio" ] [ pkgs.chromium ] )
( createChromiumUser "fb" [ ] [ pkgs.chromium ] ) ( createChromiumUser "fb" [ ] [ pkgs.chromium ] )
( createChromiumUser "gm" [ ] [ pkgs.chromium ] ) ( createChromiumUser "gm" [ ] [ pkgs.chromium ] )
( createChromiumUser "flash" [ ] [ pkgs.flash ] ) ( createChromiumUser "flash" [ "audio" ] [ pkgs.flash ] )
]; ];
nixpkgs.config.packageOverrides = pkgs : { nixpkgs.config.packageOverrides = pkgs : {

View File

@ -42,6 +42,8 @@ let
brain = { brain = {
collaborators = with config.krebs.users; [ tv makefu ]; collaborators = with config.krebs.users; [ tv makefu ];
}; };
extraction_webinterface = {};
politics-fetching = {};
} // } //
import <secrets/repos.nix> { inherit config lib pkgs; } import <secrets/repos.nix> { inherit config lib pkgs; }
); );

View File

@ -2,13 +2,14 @@
let let
mainUser = config.users.extraUsers.mainUser; mainUser = config.users.extraUsers.mainUser;
inherit (config.krebs.lib) genid;
in { in {
virtualisation.libvirtd.enable = true; virtualisation.libvirtd.enable = true;
users.extraUsers = { users.extraUsers = {
libvirt = { libvirt = {
uid = lib.genid "libvirt"; uid = genid "libvirt";
description = "user for running libvirt stuff"; description = "user for running libvirt stuff";
home = "/home/libvirt"; home = "/home/libvirt";
useDefaultShell = true; useDefaultShell = true;

View File

@ -2,12 +2,13 @@
let let
mainUser = config.users.extraUsers.mainUser; mainUser = config.users.extraUsers.mainUser;
inherit (config.krebs.lib) genid;
in { in {
users.extraUsers = { users.extraUsers = {
skype = { skype = {
name = "skype"; name = "skype";
uid = lib.genid "skype"; uid = genid "skype";
description = "user for running skype"; description = "user for running skype";
home = "/home/skype"; home = "/home/skype";
useDefaultShell = true; useDefaultShell = true;

View File

@ -93,11 +93,9 @@ let
xmonad-start = pkgs.writeScriptBin "xmonad" '' xmonad-start = pkgs.writeScriptBin "xmonad" ''
#! ${pkgs.bash}/bin/bash #! ${pkgs.bash}/bin/bash
set -efu set -efu
export PATH; PATH=${makeSearchPath "bin" [ export PATH; PATH=${makeSearchPath "bin" ([
pkgs.alsaUtils
pkgs.pulseaudioLight
pkgs.rxvt_unicode pkgs.rxvt_unicode
]}:/var/setuid-wrappers ] ++ config.environment.systemPackages)}:/var/setuid-wrappers
settle() {( settle() {(
# Use PATH for a clean journal # Use PATH for a clean journal
command=''${1##*/} command=''${1##*/}

View File

@ -1,16 +1,13 @@
{ pkgs, ... }: { pkgs, ... }:
let
inherit (pkgs) callPackage;
in
{ {
nixpkgs.config.packageOverrides = rec { nixpkgs.config.packageOverrides = rec {
firefoxPlugins = { firefoxPlugins = {
noscript = callPackage ./firefoxPlugins/noscript.nix {}; noscript = pkgs.callPackage ./firefoxPlugins/noscript.nix {};
ublock = callPackage ./firefoxPlugins/ublock.nix {}; ublock = pkgs.callPackage ./firefoxPlugins/ublock.nix {};
vimperator = callPackage ./firefoxPlugins/vimperator.nix {}; vimperator = pkgs.callPackage ./firefoxPlugins/vimperator.nix {};
}; };
newsbot-js = callPackage ./newsbot-js/default.nix {}; newsbot-js = pkgs.callPackage ./newsbot-js/default.nix {};
xmonad-lass = xmonad-lass =
let src = pkgs.writeNixFromCabal "xmonad-lass.nix" ./xmonad-lass; in let src = pkgs.writeNixFromCabal "xmonad-lass.nix" ./xmonad-lass; in
pkgs.haskellPackages.callPackage src {}; pkgs.haskellPackages.callPackage src {};

View File

@ -12,7 +12,6 @@ import XMonad
import System.IO (hPutStrLn, stderr) import System.IO (hPutStrLn, stderr)
import System.Environment (getArgs, withArgs, getEnv, getEnvironment) import System.Environment (getArgs, withArgs, getEnv, getEnvironment)
import System.Posix.Process (executeFile) import System.Posix.Process (executeFile)
import XMonad.Prompt (defaultXPConfig)
import XMonad.Actions.DynamicWorkspaces ( addWorkspacePrompt, renameWorkspace import XMonad.Actions.DynamicWorkspaces ( addWorkspacePrompt, renameWorkspace
, removeEmptyWorkspace) , removeEmptyWorkspace)
import XMonad.Actions.GridSelect import XMonad.Actions.GridSelect
@ -73,7 +72,7 @@ mainNoArgs = do
-- $ withUrgencyHook borderUrgencyHook "magenta" -- $ withUrgencyHook borderUrgencyHook "magenta"
-- $ withUrgencyHookC BorderUrgencyHook { urgencyBorderColor = "magenta" } urgencyConfig { suppressWhen = Never } -- $ withUrgencyHookC BorderUrgencyHook { urgencyBorderColor = "magenta" } urgencyConfig { suppressWhen = Never }
$ withUrgencyHook (SpawnUrgencyHook "echo emit Urgency ") $ withUrgencyHook (SpawnUrgencyHook "echo emit Urgency ")
$ defaultConfig $ def
{ terminal = myTerm { terminal = myTerm
, modMask = mod4Mask , modMask = mod4Mask
, workspaces = workspaces0 , workspaces = workspaces0
@ -169,7 +168,7 @@ myWSConfig = myGSConfig
} }
pagerConfig :: PagerConfig pagerConfig :: PagerConfig
pagerConfig = defaultPagerConfig pagerConfig = def
{ pc_font = myFont { pc_font = myFont
, pc_cellwidth = 64 , pc_cellwidth = 64
--, pc_cellheight = 36 -- TODO automatically keep screen aspect --, pc_cellheight = 36 -- TODO automatically keep screen aspect
@ -182,13 +181,13 @@ pagerConfig = defaultPagerConfig
where where
windowColors _ _ _ True _ = ("#ef4242","#ff2323") windowColors _ _ _ True _ = ("#ef4242","#ff2323")
windowColors wsf m c u wf = do windowColors wsf m c u wf = do
let def = defaultWindowColors wsf m c u wf let y = defaultWindowColors wsf m c u wf
if m == False && wf == True if m == False && wf == True
then ("#402020", snd def) then ("#402020", snd y)
else def else y
wGSConfig :: GSConfig Window wGSConfig :: GSConfig Window
wGSConfig = defaultGSConfig wGSConfig = def
{ gs_cellheight = 20 { gs_cellheight = 20
, gs_cellwidth = 192 , gs_cellwidth = 192
, gs_cellpadding = 5 , gs_cellpadding = 5

View File

@ -3,5 +3,6 @@ _:
imports = [ imports = [
../krebs ../krebs
./3modules ./3modules
./5pkgs
]; ];
} }

View File

@ -19,9 +19,13 @@ in {
username = "lol"; username = "lol";
password = "wut"; password = "wut";
}; };
exim-retiolum.enable = true; exim-retiolum = {
enable = true;
primary_hostname = "test.r";
};
exim-smarthost = { exim-smarthost = {
enable = true; enable = true;
primary_hostname = "test.r";
system-aliases = [ { from = "dick"; to = "butt"; } ]; system-aliases = [ { from = "dick"; to = "butt"; } ];
}; };
go.enable = true; go.enable = true;

View File

@ -14,11 +14,14 @@ with config.krebs.lib;
../2configs/retiolum.nix ../2configs/retiolum.nix
../2configs/urlwatch.nix ../2configs/urlwatch.nix
{ {
imports = [ ../2configs/charybdis.nix ];
tv.charybdis = { tv.charybdis = {
enable = true; enable = true;
sslCert = ../Zcerts/charybdis_cd.crt.pem; ssl_cert = ../Zcerts/charybdis_cd.crt.pem;
}; };
tv.iptables.input-retiolum-accept-new-tcp = [
config.tv.charybdis.port
config.tv.charybdis.sslport
];
} }
{ {
tv.ejabberd = { tv.ejabberd = {

View File

@ -10,6 +10,8 @@ with config.krebs.lib;
../2configs/hw/AO753.nix ../2configs/hw/AO753.nix
../2configs/exim-retiolum.nix ../2configs/exim-retiolum.nix
../2configs/git.nix ../2configs/git.nix
../2configs/im.nix
../2configs/mail-client.nix
../2configs/nginx-public_html.nix ../2configs/nginx-public_html.nix
../2configs/pulse.nix ../2configs/pulse.nix
../2configs/retiolum.nix ../2configs/retiolum.nix

View File

@ -10,7 +10,9 @@ with config.krebs.lib;
../2configs/hw/w110er.nix ../2configs/hw/w110er.nix
../2configs/exim-retiolum.nix ../2configs/exim-retiolum.nix
../2configs/git.nix ../2configs/git.nix
../2configs/im.nix
../2configs/mail-client.nix ../2configs/mail-client.nix
../2configs/man.nix
../2configs/nginx-public_html.nix ../2configs/nginx-public_html.nix
../2configs/pulse.nix ../2configs/pulse.nix
../2configs/retiolum.nix ../2configs/retiolum.nix
@ -23,19 +25,6 @@ with config.krebs.lib;
hashPassword hashPassword
haskellPackages.lentil haskellPackages.lentil
parallel parallel
(pkgs.writeScriptBin "im" ''
#! ${pkgs.bash}/bin/bash
export PATH=${makeSearchPath "bin" (with pkgs; [
tmux
gnugrep
weechat
])}
if tmux list-sessions -F\#S | grep -q '^im''$'; then
exec tmux attach -t im
else
exec tmux new -s im weechat
fi
'')
# root # root
cryptsetup cryptsetup
@ -52,14 +41,12 @@ with config.krebs.lib;
haskellPackages.hledger haskellPackages.hledger
htop htop
jq jq
manpages
mkpasswd mkpasswd
netcat netcat
nix-repl nix-repl
nmap nmap
nq nq
p7zip p7zip
posix_man_pages
push push
qrencode qrencode
texLive texLive
@ -165,11 +152,7 @@ with config.krebs.lib;
hardware.opengl.driSupport32Bit = true; hardware.opengl.driSupport32Bit = true;
environment.systemPackages = with pkgs; [ environment.systemPackages = with pkgs; [
xlibs.fontschumachermisc
slock
ethtool ethtool
#firefoxWrapper # with plugins
#chromiumDevWrapper
tinc tinc
iptables iptables
#jack2 #jack2
@ -177,7 +160,6 @@ with config.krebs.lib;
security.setuidPrograms = [ security.setuidPrograms = [
"sendmail" # for cron "sendmail" # for cron
"slock"
]; ];
services.printing.enable = true; services.printing.enable = true;
@ -201,12 +183,6 @@ with config.krebs.lib;
KERNEL=="hpet", GROUP="audio" KERNEL=="hpet", GROUP="audio"
''; '';
services.bitlbee = {
enable = true;
plugins = [
pkgs.bitlbee-facebook
];
};
services.tor.client.enable = true; services.tor.client.enable = true;
services.tor.enable = true; services.tor.enable = true;
services.virtualboxHost.enable = true; services.virtualboxHost.enable = true;

View File

@ -11,6 +11,7 @@ with config.krebs.lib;
../2configs/exim-retiolum.nix ../2configs/exim-retiolum.nix
../2configs/git.nix ../2configs/git.nix
../2configs/mail-client.nix ../2configs/mail-client.nix
../2configs/man.nix
../2configs/nginx-public_html.nix ../2configs/nginx-public_html.nix
../2configs/pulse.nix ../2configs/pulse.nix
../2configs/retiolum.nix ../2configs/retiolum.nix
@ -52,7 +53,6 @@ with config.krebs.lib;
haskellPackages.hledger haskellPackages.hledger
htop htop
jq jq
manpages
mkpasswd mkpasswd
netcat netcat
nix-repl nix-repl
@ -60,7 +60,6 @@ with config.krebs.lib;
nq nq
p7zip p7zip
pass pass
posix_man_pages
qrencode qrencode
texLive texLive
tmux tmux
@ -163,11 +162,7 @@ with config.krebs.lib;
#hardware.opengl.driSupport32Bit = true; #hardware.opengl.driSupport32Bit = true;
environment.systemPackages = with pkgs; [ environment.systemPackages = with pkgs; [
#xlibs.fontschumachermisc
#slock
ethtool ethtool
#firefoxWrapper # with plugins
#chromiumDevWrapper
tinc tinc
iptables iptables
#jack2 #jack2

View File

@ -2,29 +2,43 @@
with config.krebs.lib; with config.krebs.lib;
{ {
krebs.backup.plans = { krebs.backup.plans = {
wu-home-xu = { } // mapAttrs (_: recursiveUpdate {
method = "push";
src = { host = config.krebs.hosts.wu; path = "/home"; };
dst = { host = config.krebs.hosts.xu; path = "/bku/wu-home"; };
startAt = "05:00";
snapshots = { snapshots = {
daily = { format = "%Y-%m-%d"; retain = 7; }; daily = { format = "%Y-%m-%d"; retain = 7; };
weekly = { format = "%YW%W"; retain = 4; }; weekly = { format = "%YW%W"; retain = 4; };
monthly = { format = "%Y-%m"; retain = 12; }; monthly = { format = "%Y-%m"; retain = 12; };
yearly = { format = "%Y"; }; yearly = { format = "%Y"; };
}; };
}) {
nomic-home-xu = {
method = "push";
src = { host = config.krebs.hosts.nomic; path = "/home"; };
dst = { host = config.krebs.hosts.xu; path = "/bku/nomic-home"; };
startAt = "05:00";
};
wu-home-xu = {
method = "push";
src = { host = config.krebs.hosts.wu; path = "/home"; };
dst = { host = config.krebs.hosts.xu; path = "/bku/wu-home"; };
startAt = "05:00";
}; };
xu-home-wu = { xu-home-wu = {
method = "push"; method = "push";
src = { host = config.krebs.hosts.xu; path = "/home"; }; src = { host = config.krebs.hosts.xu; path = "/home"; };
dst = { host = config.krebs.hosts.wu; path = "/bku/xu-home"; }; dst = { host = config.krebs.hosts.wu; path = "/bku/xu-home"; };
startAt = "06:00"; startAt = "06:00";
snapshots = {
daily = { format = "%Y-%m-%d"; retain = 7; };
weekly = { format = "%YW%W"; retain = 4; };
monthly = { format = "%Y-%m"; retain = 12; };
yearly = { format = "%Y"; };
}; };
xu-pull-cd-ejabberd = {
method = "pull";
src = { host = config.krebs.hosts.cd; path = "/var/ejabberd"; };
dst = { host = config.krebs.hosts.xu; path = "/bku/cd-ejabberd"; };
startAt = "07:00";
};
xu-pull-cd-home = {
method = "pull";
src = { host = config.krebs.hosts.cd; path = "/home"; };
dst = { host = config.krebs.hosts.xu; path = "/bku/cd-home"; };
startAt = "07:00";
}; };
} // mapAttrs (_: recursiveUpdate { } // mapAttrs (_: recursiveUpdate {
snapshots = { snapshots = {

View File

@ -1,601 +0,0 @@
{ config, lib, pkgs, ... }:
with config.krebs.lib;
let
cfg = config.tv.charybdis;
out = {
options.tv.charybdis = api;
config = lib.mkIf cfg.enable (lib.mkMerge [
imp
{ tv.iptables.input-retiolum-accept-new-tcp = [ 6667 6697 ]; }
]);
};
api = {
enable = mkEnableOption "tv.charybdis";
dataDir = mkOption {
type = types.str;
default = "/var/lib/charybdis";
};
dhParams = mkOption {
type = types.str;
default = toString <secrets/charybdis.dh.pem>;
};
motd = mkOption {
type = types.str;
default = "/join #retiolum";
};
sslCert = mkOption {
type = types.path;
};
sslKey = mkOption {
type = types.str;
default = toString <secrets/charybdis.key.pem>;
};
};
imp = {
systemd.services.charybdis = {
wantedBy = [ "multi-user.target" ];
environment = {
BANDB_DBPATH = "${cfg.dataDir}/ban.db";
};
serviceConfig = {
PermissionsStartOnly = "true";
SyslogIdentifier = "charybdis";
User = user.name;
PrivateTmp = "true";
Restart = "always";
ExecStartPre = pkgs.writeScript "charybdis-init" ''
#! /bin/sh
mkdir -p ${cfg.dataDir}
chown ${user.name}: ${cfg.dataDir}
install -o ${user.name} -m 0400 ${cfg.sslKey} /tmp/ssl.key
install -o ${user.name} -m 0400 ${cfg.dhParams} /tmp/dh.pem
echo ${escapeShellArg cfg.motd} > /tmp/ircd.motd
'';
ExecStart = pkgs.writeScript "charybdis-service" ''
#! /bin/sh
set -euf
exec ${pkgs.charybdis}/bin/charybdis-ircd \
-foreground \
-logfile /dev/stderr \
-configfile ${configFile}
'';
};
};
users.extraUsers = singleton {
inherit (user) name uid;
};
};
user = rec {
name = "charybdis";
uid = genid name;
};
configFile = toFile "charybdis-ircd.conf" ''
/* doc/example.conf - brief example configuration file
*
* Copyright (C) 2000-2002 Hybrid Development Team
* Copyright (C) 2002-2005 ircd-ratbox development team
* Copyright (C) 2005-2006 charybdis development team
*
* $Id: example.conf 3582 2007-11-17 21:55:48Z jilles $
*
* See reference.conf for more information.
*/
/* Extensions */
#loadmodule "extensions/chm_operonly_compat.so";
#loadmodule "extensions/chm_quietunreg_compat.so";
#loadmodule "extensions/chm_sslonly_compat.so";
#loadmodule "extensions/createauthonly.so";
#loadmodule "extensions/extb_account.so";
#loadmodule "extensions/extb_canjoin.so";
#loadmodule "extensions/extb_channel.so";
#loadmodule "extensions/extb_extgecos.so";
#loadmodule "extensions/extb_oper.so";
#loadmodule "extensions/extb_realname.so";
#loadmodule "extensions/extb_server.so";
#loadmodule "extensions/extb_ssl.so";
#loadmodule "extensions/hurt.so";
#loadmodule "extensions/m_findforwards.so";
#loadmodule "extensions/m_identify.so";
#loadmodule "extensions/no_oper_invis.so";
#loadmodule "extensions/sno_farconnect.so";
#loadmodule "extensions/sno_globalkline.so";
#loadmodule "extensions/sno_globaloper.so";
#loadmodule "extensions/sno_whois.so";
loadmodule "extensions/override.so";
/*
* IP cloaking extensions: use ip_cloaking_4.0
* if you're linking 3.2 and later, otherwise use
* ip_cloaking.so, for compatibility with older 3.x
* releases.
*/
#loadmodule "extensions/ip_cloaking_4.0.so";
#loadmodule "extensions/ip_cloaking.so";
serverinfo {
name = ${toJSON (head config.krebs.build.host.nets.retiolum.aliases)};
sid = "4z3";
description = "miep!";
network_name = "irc.retiolum";
#network_desc = "Retiolum IRC Network";
hub = yes;
/* On multi-homed hosts you may need the following. These define
* the addresses we connect from to other servers. */
/* for IPv4 */
vhost = ${concatMapStringsSep ", " toJSON config.krebs.build.host.nets.retiolum.addrs4};
/* for IPv6 */
vhost6 = ${concatMapStringsSep ", " toJSON config.krebs.build.host.nets.retiolum.addrs6};
/* ssl_private_key: our ssl private key */
ssl_private_key = "/tmp/ssl.key";
/* ssl_cert: certificate for our ssl server */
ssl_cert = ${toJSON cfg.sslCert};
/* ssl_dh_params: DH parameters, generate with openssl dhparam -out dh.pem 1024 */
ssl_dh_params = "/tmp/dh.pem";
/* ssld_count: number of ssld processes you want to start, if you
* have a really busy server, using N-1 where N is the number of
* cpu/cpu cores you have might be useful. A number greater than one
* can also be useful in case of bugs in ssld and because ssld needs
* two file descriptors per SSL connection.
*/
ssld_count = 1;
/* default max clients: the default maximum number of clients
* allowed to connect. This can be changed once ircd has started by
* issuing:
* /quote set maxclients <limit>
*/
default_max_clients = 1024;
/* nicklen: enforced nickname length (for this server only; must not
* be longer than the maximum length set while building).
*/
nicklen = 30;
};
admin {
name = "tv";
description = "peer";
mail = "${config.krebs.users.tv.mail}";
};
log {
fname_userlog = "/dev/stderr";
fname_fuserlog = "/dev/stderr";
fname_operlog = "/dev/stderr";
fname_foperlog = "/dev/stderr";
fname_serverlog = "/dev/stderr";
fname_klinelog = "/dev/stderr";
fname_killlog = "/dev/stderr";
fname_operspylog = "/dev/stderr";
fname_ioerrorlog = "/dev/stderr";
};
/* class {} blocks MUST be specified before anything that uses them. That
* means they must be defined before auth {} and before connect {}.
*/
class "krebs" {
ping_time = 2 minutes;
number_per_ident = 10;
number_per_ip = 2048;
number_per_ip_global = 4096;
cidr_ipv4_bitlen = 24;
cidr_ipv6_bitlen = 64;
number_per_cidr = 65536;
max_number = 3000;
sendq = 1 megabyte;
};
class "users" {
ping_time = 2 minutes;
number_per_ident = 10;
number_per_ip = 1024;
number_per_ip_global = 4096;
cidr_ipv4_bitlen = 24;
cidr_ipv6_bitlen = 64;
number_per_cidr = 65536;
max_number = 3000;
sendq = 400 kbytes;
};
class "opers" {
ping_time = 5 minutes;
number_per_ip = 10;
max_number = 1000;
sendq = 1 megabyte;
};
class "server" {
ping_time = 5 minutes;
connectfreq = 5 minutes;
max_number = 1;
sendq = 4 megabytes;
};
listen {
/* defer_accept: wait for clients to send IRC handshake data before
* accepting them. if you intend to use software which depends on the
* server replying first, such as BOPM, you should disable this feature.
* otherwise, you probably want to leave it on.
*/
defer_accept = yes;
/* If you want to listen on a specific IP only, specify host.
* host definitions apply only to the following port line.
*/
# XXX This is stupid because only one host is allowed[?]
#host = ''${concatMapStringsSep ", " toJSON (
# config.krebs.build.host.nets.retiolum.addrs
#)};
port = 6667;
sslport = 6697;
};
/* auth {}: allow users to connect to the ircd (OLD I:)
* auth {} blocks MUST be specified in order of precedence. The first one
* that matches a user will be used. So place spoofs first, then specials,
* then general access, then restricted.
*/
auth {
/* user: the user@host allowed to connect. Multiple IPv4/IPv6 user
* lines are permitted per auth block. This is matched against the
* hostname and IP address (using :: shortening for IPv6 and
* prepending a 0 if it starts with a colon) and can also use CIDR
* masks.
*/
user = "*@10.243.0.0/12";
user = "*@42::/16";
/* password: an optional password that is required to use this block.
* By default this is not encrypted, specify the flag "encrypted" in
* flags = ...; below if it is.
*/
#password = "letmein";
/* spoof: fake the users user@host to be be this. You may either
* specify a host or a user@host to spoof to. This is free-form,
* just do everyone a favour and dont abuse it. (OLD I: = flag)
*/
#spoof = "I.still.hate.packets";
/* Possible flags in auth:
*
* encrypted | password is encrypted with mkpasswd
* spoof_notice | give a notice when spoofing hosts
* exceed_limit (old > flag) | allow user to exceed class user limits
* kline_exempt (old ^ flag) | exempt this user from k/g/xlines&dnsbls
* dnsbl_exempt | exempt this user from dnsbls
* spambot_exempt | exempt this user from spambot checks
* shide_exempt | exempt this user from serverhiding
* jupe_exempt | exempt this user from generating
* warnings joining juped channels
* resv_exempt | exempt this user from resvs
* flood_exempt | exempt this user from flood limits
* USE WITH CAUTION.
* no_tilde (old - flag) | don't prefix ~ to username if no ident
* need_ident (old + flag) | require ident for user in this class
* need_ssl | require SSL/TLS for user in this class
* need_sasl | require SASL id for user in this class
*/
flags = kline_exempt, exceed_limit, flood_exempt;
/* class: the class the user is placed in */
class = "krebs";
};
auth {
user = "*@*";
class = "users";
};
/* privset {} blocks MUST be specified before anything that uses them. That
* means they must be defined before operator {}.
*/
privset "local_op" {
privs = oper:local_kill, oper:operwall;
};
privset "server_bot" {
extends = "local_op";
privs = oper:kline, oper:remoteban, snomask:nick_changes;
};
privset "global_op" {
extends = "local_op";
privs = oper:global_kill, oper:routing, oper:kline, oper:unkline, oper:xline,
oper:resv, oper:mass_notice, oper:remoteban;
};
privset "admin" {
extends = "global_op";
privs = oper:admin, oper:die, oper:rehash, oper:spy, oper:override;
};
privset "aids" {
privs = oper:override, oper:rehash;
};
operator "aids" {
user = "*@10.243.*";
privset = "aids";
flags = ~encrypted;
password = "balls";
};
operator "god" {
/* name: the name of the oper must go above */
/* user: the user@host required for this operator. CIDR *is*
* supported now. auth{} spoofs work here, other spoofs do not.
* multiple user="" lines are supported.
*/
user = "*god@127.0.0.1";
/* password: the password required to oper. Unless ~encrypted is
* contained in flags = ...; this will need to be encrypted using
* mkpasswd, MD5 is supported
*/
password = "5";
/* rsa key: the public key for this oper when using Challenge.
* A password should not be defined when this is used, see
* doc/challenge.txt for more information.
*/
#rsa_public_key_file = "/usr/local/ircd/etc/oper.pub";
/* umodes: the specific umodes this oper gets when they oper.
* If this is specified an oper will not be given oper_umodes
* These are described above oper_only_umodes in general {};
*/
#umodes = locops, servnotice, operwall, wallop;
/* fingerprint: if specified, the oper's client certificate
* fingerprint will be checked against the specified fingerprint
* below.
*/
#fingerprint = "c77106576abf7f9f90cca0f63874a60f2e40a64b";
/* snomask: specific server notice mask on oper up.
* If this is specified an oper will not be given oper_snomask.
*/
snomask = "+Zbfkrsuy";
/* flags: misc options for the operator. You may prefix an option
* with ~ to disable it, e.g. ~encrypted.
*
* Default flags are encrypted.
*
* Available options:
*
* encrypted: the password above is encrypted [DEFAULT]
* need_ssl: must be using SSL/TLS to oper up
*/
flags = encrypted;
/* privset: privileges set to grant */
privset = "admin";
};
service {
name = "services.int";
};
cluster {
name = "*";
flags = kline, tkline, unkline, xline, txline, unxline, resv, tresv, unresv;
};
shared {
oper = "*@*", "*";
flags = all, rehash;
};
/* exempt {}: IPs that are exempt from Dlines and rejectcache. (OLD d:) */
exempt {
ip = "127.0.0.1";
};
channel {
use_invex = yes;
use_except = yes;
use_forward = yes;
use_knock = yes;
knock_delay = 5 minutes;
knock_delay_channel = 1 minute;
max_chans_per_user = 15;
max_bans = 100;
max_bans_large = 500;
default_split_user_count = 0;
default_split_server_count = 0;
no_create_on_split = no;
no_join_on_split = no;
burst_topicwho = yes;
kick_on_split_riding = no;
only_ascii_channels = no;
resv_forcepart = yes;
channel_target_change = yes;
disable_local_channels = no;
};
serverhide {
flatten_links = yes;
links_delay = 5 minutes;
hidden = no;
disable_hidden = no;
};
/* These are the blacklist settings.
* You can have multiple combinations of host and rejection reasons.
* They are used in pairs of one host/rejection reason.
*
* These settings should be adequate for most networks, and are (presently)
* required for use on StaticBox.
*
* Word to the wise: Do not use blacklists like SPEWS for blocking IRC
* connections.
*
* As of charybdis 2.2, you can do some keyword substitution on the rejection
* reason. The available keyword substitutions are:
*
* ''${ip} - the user's IP
* ''${host} - the user's canonical hostname
* ''${dnsbl-host} - the dnsbl hostname the lookup was done against
* ''${nick} - the user's nickname
* ''${network-name} - the name of the network
*
* As of charybdis 3.4, a type parameter is supported, which specifies the
* address families the blacklist supports. IPv4 and IPv6 are supported.
* IPv4 is currently the default as few blacklists support IPv6 operation
* as of this writing.
*
* Note: AHBL (the providers of the below *.ahbl.org BLs) request that they be
* contacted, via email, at admins@2mbit.com before using these BLs.
* See <http://www.ahbl.org/services.php> for more information.
*/
blacklist {
host = "rbl.efnetrbl.org";
type = ipv4;
reject_reason = "''${nick}, your IP (''${ip}) is listed in EFnet's RBL. For assistance, see http://efnetrbl.org/?i=''${ip}";
# host = "ircbl.ahbl.org";
# type = ipv4;
# reject_reason = "''${nick}, your IP (''${ip}) is listed in ''${dnsbl-host} for having an open proxy. In order to protect ''${network-name} from abuse, we are not allowing connections with open proxies to connect.";
#
# host = "tor.ahbl.org";
# type = ipv4;
# reject_reason = "''${nick}, your IP (''${ip}) is listed as a TOR exit node. In order to protect ''${network-name} from tor-based abuse, we are not allowing TOR exit nodes to connect to our network.";
#
/* Example of a blacklist that supports both IPv4 and IPv6 */
# host = "foobl.blacklist.invalid";
# type = ipv4, ipv6;
# reject_reason = "''${nick}, your IP (''${ip}) is listed in ''${dnsbl-host} for some reason. In order to protect ''${network-name} from abuse, we are not allowing connections listed in ''${dnsbl-host} to connect";
};
alias "NickServ" {
target = "NickServ";
};
alias "ChanServ" {
target = "ChanServ";
};
alias "OperServ" {
target = "OperServ";
};
alias "MemoServ" {
target = "MemoServ";
};
alias "NS" {
target = "NickServ";
};
alias "CS" {
target = "ChanServ";
};
alias "OS" {
target = "OperServ";
};
alias "MS" {
target = "MemoServ";
};
general {
hide_error_messages = opers;
hide_spoof_ips = yes;
/*
* default_umodes: umodes to enable on connect.
* If you have enabled the new ip_cloaking_4.0 module, and you want
* to make use of it, add +x to this option, i.e.:
* default_umodes = "+ix";
*
* If you have enabled the old ip_cloaking module, and you want
* to make use of it, add +h to this option, i.e.:
* default_umodes = "+ih";
*/
default_umodes = "+i";
default_operstring = "is an IRC Operator";
default_adminstring = "is a Server Administrator";
servicestring = "is a Network Service";
disable_fake_channels = no;
tkline_expire_notices = no;
default_floodcount = 1000;
failed_oper_notice = yes;
dots_in_ident=2;
min_nonwildcard = 4;
min_nonwildcard_simple = 3;
max_accept = 100;
max_monitor = 100;
anti_nick_flood = yes;
max_nick_time = 20 seconds;
max_nick_changes = 5;
anti_spam_exit_message_time = 5 minutes;
ts_warn_delta = 30 seconds;
ts_max_delta = 5 minutes;
client_exit = yes;
collision_fnc = yes;
resv_fnc = yes;
global_snotices = yes;
dline_with_reason = yes;
kline_delay = 0 seconds;
kline_with_reason = yes;
kline_reason = "K-Lined";
identify_service = "NickServ@services.int";
identify_command = "IDENTIFY";
non_redundant_klines = yes;
warn_no_nline = yes;
use_propagated_bans = yes;
stats_e_disabled = no;
stats_c_oper_only=no;
stats_h_oper_only=no;
client_flood_max_lines = 16000;
client_flood_burst_rate = 32000;
client_flood_burst_max = 32000;
client_flood_message_num = 32000;
client_flood_message_time = 32000;
use_whois_actually = no;
oper_only_umodes = operwall, locops, servnotice;
oper_umodes = locops, servnotice, operwall, wallop;
oper_snomask = "+s";
burst_away = yes;
nick_delay = 0 seconds; # 15 minutes if you want to enable this
reject_ban_time = 1 minute;
reject_after_count = 3;
reject_duration = 5 minutes;
throttle_duration = 60;
throttle_count = 4;
max_ratelimit_tokens = 30;
away_interval = 30;
disable_auth = yes;
};
modules {
path = "modules";
path = "modules/autoload";
};
exempt {
ip = "10.243.0.0/16";
};
'';
in
out

View File

@ -40,8 +40,8 @@ with config.krebs.lib;
mutableUsers = false; mutableUsers = false;
users = { users = {
tv = { tv = {
inherit (config.krebs.users.tv) home uid;
isNormalUser = true; isNormalUser = true;
uid = 1337;
extraGroups = [ "tv" ]; extraGroups = [ "tv" ];
}; };
}; };
@ -50,6 +50,7 @@ with config.krebs.lib;
{ {
security.sudo.extraConfig = '' security.sudo.extraConfig = ''
Defaults mailto="${config.krebs.users.tv.mail}" Defaults mailto="${config.krebs.users.tv.mail}"
Defaults !lecture
''; '';
time.timeZone = "Europe/Berlin"; time.timeZone = "Europe/Berlin";
} }
@ -123,7 +124,7 @@ with config.krebs.lib;
0) 0)
PS1='\[\e[1;31m\]\w\[\e[0m\] ' PS1='\[\e[1;31m\]\w\[\e[0m\] '
;; ;;
1337) ${toString config.krebs.users.tv.uid})
PS1='\[\e[1;32m\]\w\[\e[0m\] ' PS1='\[\e[1;32m\]\w\[\e[0m\] '
;; ;;
*) *)

View File

@ -5,19 +5,23 @@ with config.krebs.lib;
{ {
krebs.exim-smarthost = { krebs.exim-smarthost = {
enable = true; enable = true;
primary_hostname = "${config.networking.hostName}.retiolum";
sender_domains = [ sender_domains = [
"krebsco.de"
"shackspace.de" "shackspace.de"
"viljetic.de" "viljetic.de"
]; ];
relay_from_hosts = [ relay_from_hosts = concatMap (host: host.nets.retiolum.addrs4) [
"10.243.13.37" config.krebs.hosts.nomic
config.krebs.hosts.wu
config.krebs.hosts.xu
]; ];
internet-aliases = with config.krebs.users; [ internet-aliases = with config.krebs.users; [
{ from = "postmaster@viljetic.de"; to = tv.mail; } # RFC 822
{ from = "mirko@viljetic.de"; to = mv.mail; } { from = "mirko@viljetic.de"; to = mv.mail; }
{ from = "tomislav@viljetic.de"; to = tv.mail; } { from = "tomislav@viljetic.de"; to = tv.mail; }
{ from = "tv@destroy.dyn.shackspace.de"; to = tv.mail; } { from = "tv@destroy.dyn.shackspace.de"; to = tv.mail; }
{ from = "tv@viljetic.de"; to = tv.mail; } { from = "tv@viljetic.de"; to = tv.mail; }
{ from = "tv@shackspace.de"; to = tv.mail; }
]; ];
system-aliases = [ system-aliases = [
{ from = "mailer-daemon"; to = "postmaster"; } { from = "mailer-daemon"; to = "postmaster"; }

24
tv/2configs/im.nix Normal file
View File

@ -0,0 +1,24 @@
{ config, lib, pkgs, ... }:
with config.krebs.lib;
{
environment.systemPackages = with pkgs; [
(pkgs.writeDashBin "im" ''
export PATH=${makeSearchPath "bin" (with pkgs; [
tmux
gnugrep
weechat
])}
if tmux list-sessions -F\#S | grep -q '^im''$'; then
exec tmux attach -t im
else
exec tmux new -s im weechat
fi
'')
];
services.bitlbee = {
enable = true;
plugins = [
pkgs.bitlbee-facebook
];
};
}

12
tv/2configs/man.nix Normal file
View File

@ -0,0 +1,12 @@
{ config, lib, pkgs, ... }:
{
environment.etc."man.conf".source = pkgs.runCommand "man.conf" {} ''
${pkgs.gnused}/bin/sed <${pkgs.man}/lib/man.conf >$out '
s:^NROFF\t.*:& -Wbreak:
'
'';
environment.systemPackages = with pkgs; [
manpages
posix_man_pages
];
}

View File

@ -1,5 +1,5 @@
{ config, ... }: { config, pkgs, ... }:
with config.krebs.lib;
{ {
krebs.urlwatch = { krebs.urlwatch = {
enable = true; enable = true;
@ -52,8 +52,43 @@
# is derived from `configFile` in: # is derived from `configFile` in:
https://raw.githubusercontent.com/NixOS/nixpkgs/master/nixos/modules/services/x11/xserver.nix https://raw.githubusercontent.com/NixOS/nixpkgs/master/nixos/modules/services/x11/xserver.nix
https://pypi.python.org/pypi/vncdotool {
url = https://pypi.python.org/pypi/vncdotool/json;
filter = "system:${pkgs.jq}/bin/jq -r '.releases|keys[]'";
}
https://api.github.com/repos/kanaka/noVNC/tags https://api.github.com/repos/kanaka/noVNC/tags
]; ];
hooksFile = toFile "hooks.py" ''
import subprocess
import urlwatch
class CaseFilter(urlwatch.filters.FilterBase):
"""Filter for piping data through an external process"""
__kind__ = 'system'
def filter(self, data, subfilter=None):
if subfilter is None:
raise ValueError('The system filter needs a command')
proc = subprocess.Popen(
subfilter,
shell=True,
stdin=subprocess.PIPE,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
)
(stdout, stderr) = proc.communicate(data.encode())
if proc.returncode != 0:
raise RuntimeError(
"system filter returned non-zero exit status %d; stderr:\n"
% proc.returncode
+ stderr.decode()
)
return stdout.decode()
'';
}; };
} }

View File

@ -15,18 +15,26 @@ in
# #
# make [install] system=xu-qemu0 target_host=10.56.0.101 # make [install] system=xu-qemu0 target_host=10.56.0.101
# TODO iptables -A FORWARD -m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT
# TODO iptables -A FORWARD -i qemubr0 -s 10.56.0.1/24 -m conntrack --ctstate NEW -j ACCEPT
# TODO iptables -A POSTROUTING -t nat -j MASQUERADE
# TODO iptables -A INPUT -i qemubr0 -p udp -m udp --dport bootps -j ACCEPT
# TODO iptables -A INPUT -i qemubr0 -p udp -m udp --dport domain -j ACCEPT
with config.krebs.lib; with config.krebs.lib;
{ {
networking.dhcpcd.denyInterfaces = [ "qemubr0" ]; networking.dhcpcd.denyInterfaces = [ "qemubr0" ];
tv.iptables.extra = {
nat.POSTROUTING = ["-j MASQUERADE"];
filter.FORWARD = [
"-m conntrack --ctstate ESTABLISHED,RELATED -j ACCEPT"
"-i qemubr0 -s 10.56.0.1/24 -m conntrack --ctstate NEW -j ACCEPT"
];
filter.INPUT = [
"-i qemubr0 -p udp -m udp --dport bootps -j ACCEPT"
"-i qemubr0 -p udp -m udp --dport domain -j ACCEPT"
];
};
systemd.network.enable = true; systemd.network.enable = true;
systemd.services.systemd-networkd-wait-online.enable = false;
services.resolved.enable = mkForce false; services.resolved.enable = mkForce false;
boot.kernel.sysctl."net.ipv4.ip_forward" = 1; boot.kernel.sysctl."net.ipv4.ip_forward" = 1;

View File

@ -0,0 +1,522 @@
{ config, ... }: with config.krebs.lib; let
cfg = config.tv.charybdis;
in toFile "charybdis.conf" ''
/* doc/example.conf - brief example configuration file
*
* Copyright (C) 2000-2002 Hybrid Development Team
* Copyright (C) 2002-2005 ircd-ratbox development team
* Copyright (C) 2005-2006 charybdis development team
*
* $Id: example.conf 3582 2007-11-17 21:55:48Z jilles $
*
* See reference.conf for more information.
*/
/* Extensions */
#loadmodule "extensions/chm_operonly_compat.so";
#loadmodule "extensions/chm_quietunreg_compat.so";
#loadmodule "extensions/chm_sslonly_compat.so";
#loadmodule "extensions/createauthonly.so";
#loadmodule "extensions/extb_account.so";
#loadmodule "extensions/extb_canjoin.so";
#loadmodule "extensions/extb_channel.so";
#loadmodule "extensions/extb_extgecos.so";
#loadmodule "extensions/extb_oper.so";
#loadmodule "extensions/extb_realname.so";
#loadmodule "extensions/extb_server.so";
#loadmodule "extensions/extb_ssl.so";
#loadmodule "extensions/hurt.so";
#loadmodule "extensions/m_findforwards.so";
#loadmodule "extensions/m_identify.so";
#loadmodule "extensions/no_oper_invis.so";
#loadmodule "extensions/sno_farconnect.so";
#loadmodule "extensions/sno_globalkline.so";
#loadmodule "extensions/sno_globaloper.so";
#loadmodule "extensions/sno_whois.so";
loadmodule "extensions/override.so";
/*
* IP cloaking extensions: use ip_cloaking_4.0
* if you're linking 3.2 and later, otherwise use
* ip_cloaking.so, for compatibility with older 3.x
* releases.
*/
#loadmodule "extensions/ip_cloaking_4.0.so";
#loadmodule "extensions/ip_cloaking.so";
serverinfo {
name = ${toJSON (head config.krebs.build.host.nets.retiolum.aliases)};
sid = "4z3";
description = "miep!";
network_name = "irc.retiolum";
#network_desc = "Retiolum IRC Network";
hub = yes;
/* On multi-homed hosts you may need the following. These define
* the addresses we connect from to other servers. */
/* for IPv4 */
vhost = ${concatMapStringsSep ", " toJSON config.krebs.build.host.nets.retiolum.addrs4};
/* for IPv6 */
vhost6 = ${concatMapStringsSep ", " toJSON config.krebs.build.host.nets.retiolum.addrs6};
/* ssl_private_key: our ssl private key */
ssl_private_key = ${toJSON cfg.ssl_private_key.path};
/* ssl_cert: certificate for our ssl server */
ssl_cert = ${toJSON cfg.ssl_cert};
/* ssl_dh_params: DH parameters, generate with openssl dhparam -out dh.pem 1024 */
ssl_dh_params = ${toJSON cfg.ssl_dh_params.path};
/* ssld_count: number of ssld processes you want to start, if you
* have a really busy server, using N-1 where N is the number of
* cpu/cpu cores you have might be useful. A number greater than one
* can also be useful in case of bugs in ssld and because ssld needs
* two file descriptors per SSL connection.
*/
ssld_count = 1;
/* default max clients: the default maximum number of clients
* allowed to connect. This can be changed once ircd has started by
* issuing:
* /quote set maxclients <limit>
*/
default_max_clients = 1024;
/* nicklen: enforced nickname length (for this server only; must not
* be longer than the maximum length set while building).
*/
nicklen = 30;
};
admin {
name = "tv";
description = "peer";
};
log {
fname_userlog = "/dev/stderr";
fname_fuserlog = "/dev/stderr";
fname_operlog = "/dev/stderr";
fname_foperlog = "/dev/stderr";
fname_serverlog = "/dev/stderr";
fname_klinelog = "/dev/stderr";
fname_killlog = "/dev/stderr";
fname_operspylog = "/dev/stderr";
fname_ioerrorlog = "/dev/stderr";
};
/* class {} blocks MUST be specified before anything that uses them. That
* means they must be defined before auth {} and before connect {}.
*/
class "krebs" {
ping_time = 2 minutes;
number_per_ident = 10;
number_per_ip = 2048;
number_per_ip_global = 4096;
cidr_ipv4_bitlen = 24;
cidr_ipv6_bitlen = 64;
number_per_cidr = 65536;
max_number = 3000;
sendq = 1 megabyte;
};
class "users" {
ping_time = 2 minutes;
number_per_ident = 10;
number_per_ip = 1024;
number_per_ip_global = 4096;
cidr_ipv4_bitlen = 24;
cidr_ipv6_bitlen = 64;
number_per_cidr = 65536;
max_number = 3000;
sendq = 400 kbytes;
};
class "opers" {
ping_time = 5 minutes;
number_per_ip = 10;
max_number = 1000;
sendq = 1 megabyte;
};
class "server" {
ping_time = 5 minutes;
connectfreq = 5 minutes;
max_number = 1;
sendq = 4 megabytes;
};
listen {
/* defer_accept: wait for clients to send IRC handshake data before
* accepting them. if you intend to use software which depends on the
* server replying first, such as BOPM, you should disable this feature.
* otherwise, you probably want to leave it on.
*/
defer_accept = yes;
/* If you want to listen on a specific IP only, specify host.
* host definitions apply only to the following port line.
*/
# XXX This is stupid because only one host is allowed[?]
#host = ''${concatMapStringsSep ", " toJSON (
# config.krebs.build.host.nets.retiolum.addrs
#)};
port = ${toString cfg.port};
sslport = ${toString cfg.sslport};
};
/* auth {}: allow users to connect to the ircd (OLD I:)
* auth {} blocks MUST be specified in order of precedence. The first one
* that matches a user will be used. So place spoofs first, then specials,
* then general access, then restricted.
*/
auth {
/* user: the user@host allowed to connect. Multiple IPv4/IPv6 user
* lines are permitted per auth block. This is matched against the
* hostname and IP address (using :: shortening for IPv6 and
* prepending a 0 if it starts with a colon) and can also use CIDR
* masks.
*/
user = "*@10.243.0.0/16";
user = "*@42::/16";
/* password: an optional password that is required to use this block.
* By default this is not encrypted, specify the flag "encrypted" in
* flags = ...; below if it is.
*/
#password = "letmein";
/* spoof: fake the users user@host to be be this. You may either
* specify a host or a user@host to spoof to. This is free-form,
* just do everyone a favour and dont abuse it. (OLD I: = flag)
*/
#spoof = "I.still.hate.packets";
/* Possible flags in auth:
*
* encrypted | password is encrypted with mkpasswd
* spoof_notice | give a notice when spoofing hosts
* exceed_limit (old > flag) | allow user to exceed class user limits
* kline_exempt (old ^ flag) | exempt this user from k/g/xlines&dnsbls
* dnsbl_exempt | exempt this user from dnsbls
* spambot_exempt | exempt this user from spambot checks
* shide_exempt | exempt this user from serverhiding
* jupe_exempt | exempt this user from generating
* warnings joining juped channels
* resv_exempt | exempt this user from resvs
* flood_exempt | exempt this user from flood limits
* USE WITH CAUTION.
* no_tilde (old - flag) | don't prefix ~ to username if no ident
* need_ident (old + flag) | require ident for user in this class
* need_ssl | require SSL/TLS for user in this class
* need_sasl | require SASL id for user in this class
*/
flags = kline_exempt, exceed_limit, flood_exempt;
/* class: the class the user is placed in */
class = "krebs";
};
auth {
user = "*@*";
class = "users";
};
/* privset {} blocks MUST be specified before anything that uses them. That
* means they must be defined before operator {}.
*/
privset "local_op" {
privs = oper:local_kill, oper:operwall;
};
privset "server_bot" {
extends = "local_op";
privs = oper:kline, oper:remoteban, snomask:nick_changes;
};
privset "global_op" {
extends = "local_op";
privs = oper:global_kill, oper:routing, oper:kline, oper:unkline, oper:xline,
oper:resv, oper:mass_notice, oper:remoteban;
};
privset "admin" {
extends = "global_op";
privs = oper:admin, oper:die, oper:rehash, oper:spy, oper:override;
};
privset "aids" {
privs = oper:override, oper:rehash;
};
operator "aids" {
user = "*@10.243.*";
privset = "aids";
flags = ~encrypted;
password = "balls";
};
operator "god" {
/* name: the name of the oper must go above */
/* user: the user@host required for this operator. CIDR *is*
* supported now. auth{} spoofs work here, other spoofs do not.
* multiple user="" lines are supported.
*/
user = "*god@127.0.0.1";
/* password: the password required to oper. Unless ~encrypted is
* contained in flags = ...; this will need to be encrypted using
* mkpasswd, MD5 is supported
*/
password = "5";
/* rsa key: the public key for this oper when using Challenge.
* A password should not be defined when this is used, see
* doc/challenge.txt for more information.
*/
#rsa_public_key_file = "/usr/local/ircd/etc/oper.pub";
/* umodes: the specific umodes this oper gets when they oper.
* If this is specified an oper will not be given oper_umodes
* These are described above oper_only_umodes in general {};
*/
#umodes = locops, servnotice, operwall, wallop;
/* fingerprint: if specified, the oper's client certificate
* fingerprint will be checked against the specified fingerprint
* below.
*/
#fingerprint = "c77106576abf7f9f90cca0f63874a60f2e40a64b";
/* snomask: specific server notice mask on oper up.
* If this is specified an oper will not be given oper_snomask.
*/
snomask = "+Zbfkrsuy";
/* flags: misc options for the operator. You may prefix an option
* with ~ to disable it, e.g. ~encrypted.
*
* Default flags are encrypted.
*
* Available options:
*
* encrypted: the password above is encrypted [DEFAULT]
* need_ssl: must be using SSL/TLS to oper up
*/
flags = encrypted;
/* privset: privileges set to grant */
privset = "admin";
};
service {
name = "services.int";
};
cluster {
name = "*";
flags = kline, tkline, unkline, xline, txline, unxline, resv, tresv, unresv;
};
shared {
oper = "*@*", "*";
flags = all, rehash;
};
/* exempt {}: IPs that are exempt from Dlines and rejectcache. (OLD d:) */
exempt {
ip = "127.0.0.1";
};
channel {
use_invex = yes;
use_except = yes;
use_forward = yes;
use_knock = yes;
knock_delay = 5 minutes;
knock_delay_channel = 1 minute;
max_chans_per_user = 15;
max_bans = 100;
max_bans_large = 500;
default_split_user_count = 0;
default_split_server_count = 0;
no_create_on_split = no;
no_join_on_split = no;
burst_topicwho = yes;
kick_on_split_riding = no;
only_ascii_channels = no;
resv_forcepart = yes;
channel_target_change = yes;
disable_local_channels = no;
};
serverhide {
flatten_links = yes;
links_delay = 5 minutes;
hidden = no;
disable_hidden = no;
};
/* These are the blacklist settings.
* You can have multiple combinations of host and rejection reasons.
* They are used in pairs of one host/rejection reason.
*
* These settings should be adequate for most networks, and are (presently)
* required for use on StaticBox.
*
* Word to the wise: Do not use blacklists like SPEWS for blocking IRC
* connections.
*
* As of charybdis 2.2, you can do some keyword substitution on the rejection
* reason. The available keyword substitutions are:
*
* ''${ip} - the user's IP
* ''${host} - the user's canonical hostname
* ''${dnsbl-host} - the dnsbl hostname the lookup was done against
* ''${nick} - the user's nickname
* ''${network-name} - the name of the network
*
* As of charybdis 3.4, a type parameter is supported, which specifies the
* address families the blacklist supports. IPv4 and IPv6 are supported.
* IPv4 is currently the default as few blacklists support IPv6 operation
* as of this writing.
*
* Note: AHBL (the providers of the below *.ahbl.org BLs) request that they be
* contacted, via email, at admins@2mbit.com before using these BLs.
* See <http://www.ahbl.org/services.php> for more information.
*/
blacklist {
host = "rbl.efnetrbl.org";
type = ipv4;
reject_reason = "''${nick}, your IP (''${ip}) is listed in EFnet's RBL. For assistance, see http://efnetrbl.org/?i=''${ip}";
# host = "ircbl.ahbl.org";
# type = ipv4;
# reject_reason = "''${nick}, your IP (''${ip}) is listed in ''${dnsbl-host} for having an open proxy. In order to protect ''${network-name} from abuse, we are not allowing connections with open proxies to connect.";
#
# host = "tor.ahbl.org";
# type = ipv4;
# reject_reason = "''${nick}, your IP (''${ip}) is listed as a TOR exit node. In order to protect ''${network-name} from tor-based abuse, we are not allowing TOR exit nodes to connect to our network.";
#
/* Example of a blacklist that supports both IPv4 and IPv6 */
# host = "foobl.blacklist.invalid";
# type = ipv4, ipv6;
# reject_reason = "''${nick}, your IP (''${ip}) is listed in ''${dnsbl-host} for some reason. In order to protect ''${network-name} from abuse, we are not allowing connections listed in ''${dnsbl-host} to connect";
};
alias "NickServ" {
target = "NickServ";
};
alias "ChanServ" {
target = "ChanServ";
};
alias "OperServ" {
target = "OperServ";
};
alias "MemoServ" {
target = "MemoServ";
};
alias "NS" {
target = "NickServ";
};
alias "CS" {
target = "ChanServ";
};
alias "OS" {
target = "OperServ";
};
alias "MS" {
target = "MemoServ";
};
general {
hide_error_messages = opers;
hide_spoof_ips = yes;
/*
* default_umodes: umodes to enable on connect.
* If you have enabled the new ip_cloaking_4.0 module, and you want
* to make use of it, add +x to this option, i.e.:
* default_umodes = "+ix";
*
* If you have enabled the old ip_cloaking module, and you want
* to make use of it, add +h to this option, i.e.:
* default_umodes = "+ih";
*/
default_umodes = "+i";
default_operstring = "is an IRC Operator";
default_adminstring = "is a Server Administrator";
servicestring = "is a Network Service";
disable_fake_channels = no;
tkline_expire_notices = no;
default_floodcount = 1000;
failed_oper_notice = yes;
dots_in_ident=2;
min_nonwildcard = 4;
min_nonwildcard_simple = 3;
max_accept = 100;
max_monitor = 100;
anti_nick_flood = yes;
max_nick_time = 20 seconds;
max_nick_changes = 5;
anti_spam_exit_message_time = 5 minutes;
ts_warn_delta = 30 seconds;
ts_max_delta = 5 minutes;
client_exit = yes;
collision_fnc = yes;
resv_fnc = yes;
global_snotices = yes;
dline_with_reason = yes;
kline_delay = 0 seconds;
kline_with_reason = yes;
kline_reason = "K-Lined";
identify_service = "NickServ@services.int";
identify_command = "IDENTIFY";
non_redundant_klines = yes;
warn_no_nline = yes;
use_propagated_bans = yes;
stats_e_disabled = no;
stats_c_oper_only=no;
stats_h_oper_only=no;
client_flood_max_lines = 16000;
client_flood_burst_rate = 32000;
client_flood_burst_max = 32000;
client_flood_message_num = 32000;
client_flood_message_time = 32000;
use_whois_actually = no;
oper_only_umodes = operwall, locops, servnotice;
oper_umodes = locops, servnotice, operwall, wallop;
oper_snomask = "+s";
burst_away = yes;
nick_delay = 0 seconds; # 15 minutes if you want to enable this
reject_ban_time = 1 minute;
reject_after_count = 3;
reject_duration = 5 minutes;
throttle_duration = 60;
throttle_count = 4;
max_ratelimit_tokens = 30;
away_interval = 30;
disable_auth = yes;
};
modules {
path = "modules";
path = "modules/autoload";
};
exempt {
ip = "10.243.0.0/16";
};
''

View File

@ -0,0 +1,80 @@
{ config, lib, pkgs, ... }@args: with config.krebs.lib; let
cfg = config.tv.charybdis;
in {
options.tv.charybdis = {
enable = mkEnableOption "tv.charybdis";
motd = mkOption {
type = types.str;
default = "/join #retiolum";
};
port = mkOption {
type = types.int;
default = 6667;
};
ssl_cert = mkOption {
type = types.path;
};
ssl_dh_params = mkOption {
type = types.secret-file;
default = {
path = "${cfg.user.home}/dh.pem";
owner = cfg.user;
source-path = toString <secrets> + "/charybdis.dh.pem";
};
};
ssl_private_key = mkOption {
type = types.secret-file;
default = {
path = "${cfg.user.home}/ssl.key.pem";
owner = cfg.user;
source-path = toString <secrets> + "/charybdis.key.pem";
};
};
sslport = mkOption {
type = types.int;
default = 6697;
};
user = mkOption {
type = types.user;
default = {
name = "charybdis";
home = "/var/lib/charybdis";
};
};
};
config = lib.mkIf cfg.enable {
krebs.secret.files.charybdis-ssl_dh_params = cfg.ssl_dh_params;
krebs.secret.files.charybdis-ssl_private_key = cfg.ssl_private_key;
environment.etc."charybdis-ircd.motd".text = cfg.motd;
systemd.services.charybdis = {
wantedBy = [ "multi-user.target" ];
requires = [ "secret.service" ];
after = [ "network.target" "secret.service" ];
environment = {
BANDB_DBPATH = "${cfg.user.home}/ban.db";
};
serviceConfig = {
SyslogIdentifier = "charybdis";
User = cfg.user.name;
PrivateTmp = true;
Restart = "always";
ExecStartPre =
"${pkgs.coreutils}/bin/ln -s /etc/charybdis-ircd.motd /tmp/ircd.motd";
ExecStart = toString [
"${pkgs.charybdis}/bin/charybdis-ircd"
"-configfile ${import ./config.nix args}"
"-foreground"
"-logfile /dev/stderr"
];
};
};
users.users.${cfg.user.name} = {
inherit (cfg.user) home name uid;
createHome = true;
};
};
}

View File

@ -2,7 +2,8 @@ _:
{ {
imports = [ imports = [
./ejabberd.nix ./charybdis
./ejabberd
./iptables.nix ./iptables.nix
]; ];
} }

View File

@ -1,165 +0,0 @@
{ config, lib, pkgs, ... }:
with config.krebs.lib;
let
cfg = config.tv.ejabberd;
out = {
options.tv.ejabberd = api;
config = lib.mkIf cfg.enable imp;
};
api = {
enable = mkEnableOption "tv.ejabberd";
certFile = mkOption {
type = types.str;
default = toString <secrets/ejabberd.pem>;
};
hosts = mkOption {
type = with types; listOf str;
};
};
imp = {
environment.systemPackages = [ my-ejabberdctl ];
systemd.services.ejabberd = {
wantedBy = [ "multi-user.target" ];
after = [ "network.target" ];
serviceConfig = {
Type = "oneshot";
RemainAfterExit = "yes";
PermissionsStartOnly = "true";
SyslogIdentifier = "ejabberd";
User = user.name;
ExecStartPre = pkgs.writeScript "ejabberd-start" ''
#! /bin/sh
install -o ${user.name} -m 0400 ${cfg.certFile} /etc/ejabberd/ejabberd.pem
'';
ExecStart = pkgs.writeScript "ejabberd-service" ''
#! /bin/sh
${my-ejabberdctl}/bin/ejabberdctl start
'';
};
};
users.extraUsers = singleton {
inherit (user) name uid;
home = "/var/ejabberd";
createHome = true;
};
};
user = rec {
name = "ejabberd";
uid = genid name;
};
my-ejabberdctl = pkgs.writeScriptBin "ejabberdctl" ''
#! /bin/sh
set -euf
exec env \
SPOOLDIR=/var/ejabberd \
EJABBERD_CONFIG_PATH=${config-file} \
${pkgs.ejabberd}/bin/ejabberdctl \
--logs /var/ejabberd \
"$@"
'';
config-file = pkgs.writeText "ejabberd.cfg" ''
{loglevel, 3}.
{hosts, ${toErlang cfg.hosts}}.
{listen,
[
{5222, ejabberd_c2s, [
starttls,
{certfile, "/etc/ejabberd/ejabberd.pem"},
{access, c2s},
{shaper, c2s_shaper},
{max_stanza_size, 65536}
]},
{5269, ejabberd_s2s_in, [
{shaper, s2s_shaper},
{max_stanza_size, 131072}
]},
{5280, ejabberd_http, [
captcha,
http_bind,
http_poll,
web_admin
]}
]}.
{s2s_use_starttls, required}.
{s2s_certfile, "/etc/ejabberd/ejabberd.pem"}.
{auth_method, internal}.
{shaper, normal, {maxrate, 1000}}.
{shaper, fast, {maxrate, 50000}}.
{max_fsm_queue, 1000}.
{acl, local, {user_regexp, ""}}.
{access, max_user_sessions, [{10, all}]}.
{access, max_user_offline_messages, [{5000, admin}, {100, all}]}.
{access, local, [{allow, local}]}.
{access, c2s, [{deny, blocked},
{allow, all}]}.
{access, c2s_shaper, [{none, admin},
{normal, all}]}.
{access, s2s_shaper, [{fast, all}]}.
{access, announce, [{allow, admin}]}.
{access, configure, [{allow, admin}]}.
{access, muc_admin, [{allow, admin}]}.
{access, muc_create, [{allow, local}]}.
{access, muc, [{allow, all}]}.
{access, pubsub_createnode, [{allow, local}]}.
{access, register, [{allow, all}]}.
{language, "en"}.
{modules,
[
{mod_adhoc, []},
{mod_announce, [{access, announce}]},
{mod_blocking,[]},
{mod_caps, []},
{mod_configure,[]},
{mod_disco, []},
{mod_irc, []},
{mod_http_bind, []},
{mod_last, []},
{mod_muc, [
{access, muc},
{access_create, muc_create},
{access_persistent, muc_create},
{access_admin, muc_admin}
]},
{mod_offline, [{access_max_user_messages, max_user_offline_messages}]},
{mod_ping, []},
{mod_privacy, []},
{mod_private, []},
{mod_pubsub, [
{access_createnode, pubsub_createnode},
{ignore_pep_from_offline, true},
{last_item_cache, false},
{plugins, ["flat", "hometree", "pep"]}
]},
{mod_register, [
{welcome_message, {"Welcome!",
"Hi.\nWelcome to this XMPP server."}},
{ip_access, [{allow, "127.0.0.0/8"},
{deny, "0.0.0.0/0"}]},
{access, register}
]},
{mod_roster, []},
{mod_shared_roster,[]},
{mod_stats, []},
{mod_time, []},
{mod_vcard, []},
{mod_version, []}
]}.
'';
# XXX this is a placeholder that happens to work the default strings.
toErlang = builtins.toJSON;
in
out

View File

@ -0,0 +1,93 @@
{ config, ... }: with config.krebs.lib; let
cfg = config.tv.ejabberd;
# XXX this is a placeholder that happens to work the default strings.
toErlang = builtins.toJSON;
in toFile "ejabberd.conf" ''
{loglevel, 3}.
{hosts, ${toErlang cfg.hosts}}.
{listen,
[
{5222, ejabberd_c2s, [
starttls,
{certfile, ${toErlang cfg.certfile.path}},
{access, c2s},
{shaper, c2s_shaper},
{max_stanza_size, 65536}
]},
{5269, ejabberd_s2s_in, [
{shaper, s2s_shaper},
{max_stanza_size, 131072}
]},
{5280, ejabberd_http, [
captcha,
http_bind,
http_poll,
web_admin
]}
]}.
{s2s_use_starttls, required}.
{s2s_certfile, ${toErlang cfg.s2s_certfile.path}}.
{auth_method, internal}.
{shaper, normal, {maxrate, 1000}}.
{shaper, fast, {maxrate, 50000}}.
{max_fsm_queue, 1000}.
{acl, local, {user_regexp, ""}}.
{access, max_user_sessions, [{10, all}]}.
{access, max_user_offline_messages, [{5000, admin}, {100, all}]}.
{access, local, [{allow, local}]}.
{access, c2s, [{deny, blocked},
{allow, all}]}.
{access, c2s_shaper, [{none, admin},
{normal, all}]}.
{access, s2s_shaper, [{fast, all}]}.
{access, announce, [{allow, admin}]}.
{access, configure, [{allow, admin}]}.
{access, muc_admin, [{allow, admin}]}.
{access, muc_create, [{allow, local}]}.
{access, muc, [{allow, all}]}.
{access, pubsub_createnode, [{allow, local}]}.
{access, register, [{allow, all}]}.
{language, "en"}.
{modules,
[
{mod_adhoc, []},
{mod_announce, [{access, announce}]},
{mod_blocking,[]},
{mod_caps, []},
{mod_configure,[]},
{mod_disco, []},
{mod_irc, []},
{mod_http_bind, []},
{mod_last, []},
{mod_muc, [
{access, muc},
{access_create, muc_create},
{access_persistent, muc_create},
{access_admin, muc_admin}
]},
{mod_offline, [{access_max_user_messages, max_user_offline_messages}]},
{mod_ping, []},
{mod_privacy, []},
{mod_private, []},
{mod_pubsub, [
{access_createnode, pubsub_createnode},
{ignore_pep_from_offline, true},
{last_item_cache, false},
{plugins, ["flat", "hometree", "pep"]}
]},
{mod_register, [
{welcome_message, {"Welcome!",
"Hi.\nWelcome to this XMPP server."}},
{ip_access, [{allow, "127.0.0.0/8"},
{deny, "0.0.0.0/0"}]},
{access, register}
]},
{mod_roster, []},
{mod_shared_roster,[]},
{mod_stats, []},
{mod_time, []},
{mod_vcard, []},
{mod_version, []}
]}.
''

View File

@ -0,0 +1,67 @@
{ config, lib, pkgs, ... }@args: with config.krebs.lib; let
cfg = config.tv.ejabberd;
in {
options.tv.ejabberd = {
enable = mkEnableOption "tv.ejabberd";
certfile = mkOption {
type = types.secret-file;
default = {
path = "${cfg.user.home}/ejabberd.pem";
owner = cfg.user;
source-path = toString <secrets> + "/ejabberd.pem";
};
};
hosts = mkOption {
type = with types; listOf str;
};
pkgs.ejabberdctl = mkOption {
type = types.package;
default = pkgs.writeDashBin "ejabberdctl" ''
set -efu
export SPOOLDIR=${shell.escape cfg.user.home}
export EJABBERD_CONFIG_PATH=${shell.escape (import ./config.nix args)}
exec ${pkgs.ejabberd}/bin/ejabberdctl \
--logs ${shell.escape cfg.user.home} \
"$@"
'';
};
s2s_certfile = mkOption {
type = types.secret-file;
default = cfg.certfile;
};
user = mkOption {
type = types.user;
default = {
name = "ejabberd";
home = "/var/ejabberd";
};
};
};
config = lib.mkIf cfg.enable {
environment.systemPackages = [ cfg.pkgs.ejabberdctl ];
krebs.secret.files = {
ejabberd-certfile = cfg.certfile;
ejabberd-s2s_certfile = cfg.s2s_certfile;
};
systemd.services.ejabberd = {
wantedBy = [ "multi-user.target" ];
requires = [ "secret.service" ];
after = [ "network.target" "secret.service" ];
serviceConfig = {
Type = "oneshot";
RemainAfterExit = "yes";
PermissionsStartOnly = "true";
SyslogIdentifier = "ejabberd";
User = cfg.user.name;
ExecStart = "${cfg.pkgs.ejabberdctl}/bin/ejabberdctl start";
};
};
users.users.${cfg.user.name} = {
inherit (cfg.user) home name uid;
createHome = true;
};
};
}

View File

@ -26,6 +26,21 @@ let
type = with types; listOf (either int str); type = with types; listOf (either int str);
default = []; default = [];
}; };
extra = {
nat.POSTROUTING = mkOption {
type = with types; listOf str;
default = [];
};
filter.FORWARD = mkOption {
type = with types; listOf str;
default = [];
};
filter.INPUT = mkOption {
type = with types; listOf str;
default = [];
};
};
}; };
imp = { imp = {
@ -57,6 +72,11 @@ let
}; };
}; };
formatTable = table:
(concatStringsSep "\n"
(mapAttrsToList
(chain: concatMapStringsSep "\n" (rule: "-A ${chain} ${rule}"))
table));
rules = iptables-version: let rules = iptables-version: let
accept-echo-request = { accept-echo-request = {
@ -79,6 +99,7 @@ let
${concatMapStringsSep "\n" (rule: "-A OUTPUT ${rule}") [ ${concatMapStringsSep "\n" (rule: "-A OUTPUT ${rule}") [
"-o lo -p tcp -m tcp --dport 11423 -j REDIRECT --to-ports 22" "-o lo -p tcp -m tcp --dport 11423 -j REDIRECT --to-ports 22"
]} ]}
${formatTable cfg.extra.nat}
COMMIT COMMIT
*filter *filter
:INPUT DROP [0:0] :INPUT DROP [0:0]
@ -94,6 +115,7 @@ let
++ map accept-new-tcp (unique (map toString cfg.input-internet-accept-new-tcp)) ++ map accept-new-tcp (unique (map toString cfg.input-internet-accept-new-tcp))
++ ["-i retiolum -j Retiolum"] ++ ["-i retiolum -j Retiolum"]
)} )}
${formatTable cfg.extra.filter}
${concatMapStringsSep "\n" (rule: "-A Retiolum ${rule}") ([] ${concatMapStringsSep "\n" (rule: "-A Retiolum ${rule}") ([]
++ optional (cfg.accept-echo-request == "retiolum") accept-echo-request ++ optional (cfg.accept-echo-request == "retiolum") accept-echo-request
++ map accept-new-tcp (unique (map toString cfg.input-retiolum-accept-new-tcp)) ++ map accept-new-tcp (unique (map toString cfg.input-retiolum-accept-new-tcp))