Commit f4b5c870 by Christian Brauner Committed by GitHub

Merge pull request #1133 from jcowgill/mips

Add MIPS support
parents 7847a507 d36c8ae3
...@@ -2079,9 +2079,13 @@ signed long lxc_config_parse_arch(const char *arch) ...@@ -2079,9 +2079,13 @@ signed long lxc_config_parse_arch(const char *arch)
{ "i586", PER_LINUX32 }, { "i586", PER_LINUX32 },
{ "i686", PER_LINUX32 }, { "i686", PER_LINUX32 },
{ "athlon", PER_LINUX32 }, { "athlon", PER_LINUX32 },
{ "mips", PER_LINUX32 },
{ "mipsel", PER_LINUX32 },
{ "linux64", PER_LINUX }, { "linux64", PER_LINUX },
{ "x86_64", PER_LINUX }, { "x86_64", PER_LINUX },
{ "amd64", PER_LINUX }, { "amd64", PER_LINUX },
{ "mips64", PER_LINUX },
{ "mips64el", PER_LINUX },
}; };
size_t len = sizeof(pername) / sizeof(pername[0]); size_t len = sizeof(pername) / sizeof(pername[0]);
......
...@@ -125,9 +125,23 @@ enum lxc_hostarch_t { ...@@ -125,9 +125,23 @@ enum lxc_hostarch_t {
lxc_seccomp_arch_ppc64, lxc_seccomp_arch_ppc64,
lxc_seccomp_arch_ppc64le, lxc_seccomp_arch_ppc64le,
lxc_seccomp_arch_ppc, lxc_seccomp_arch_ppc,
lxc_seccomp_arch_mips,
lxc_seccomp_arch_mips64,
lxc_seccomp_arch_mips64n32,
lxc_seccomp_arch_mipsel,
lxc_seccomp_arch_mipsel64,
lxc_seccomp_arch_mipsel64n32,
lxc_seccomp_arch_unknown = 999, lxc_seccomp_arch_unknown = 999,
}; };
#ifdef __MIPSEL__
# define MIPS_ARCH_O32 lxc_seccomp_arch_mipsel
# define MIPS_ARCH_N64 lxc_seccomp_arch_mipsel64
#else
# define MIPS_ARCH_O32 lxc_seccomp_arch_mips
# define MIPS_ARCH_N64 lxc_seccomp_arch_mips64
#endif
int get_hostarch(void) int get_hostarch(void)
{ {
struct utsname uts; struct utsname uts;
...@@ -149,6 +163,10 @@ int get_hostarch(void) ...@@ -149,6 +163,10 @@ int get_hostarch(void)
return lxc_seccomp_arch_ppc64; return lxc_seccomp_arch_ppc64;
else if (strncmp(uts.machine, "ppc", 3) == 0) else if (strncmp(uts.machine, "ppc", 3) == 0)
return lxc_seccomp_arch_ppc; return lxc_seccomp_arch_ppc;
else if (strncmp(uts.machine, "mips64", 6) == 0)
return MIPS_ARCH_N64;
else if (strncmp(uts.machine, "mips", 4) == 0)
return MIPS_ARCH_O32;
return lxc_seccomp_arch_unknown; return lxc_seccomp_arch_unknown;
} }
...@@ -174,6 +192,14 @@ scmp_filter_ctx get_new_ctx(enum lxc_hostarch_t n_arch, uint32_t default_policy_ ...@@ -174,6 +192,14 @@ scmp_filter_ctx get_new_ctx(enum lxc_hostarch_t n_arch, uint32_t default_policy_
#ifdef SCMP_ARCH_PPC #ifdef SCMP_ARCH_PPC
case lxc_seccomp_arch_ppc: arch = SCMP_ARCH_PPC; break; case lxc_seccomp_arch_ppc: arch = SCMP_ARCH_PPC; break;
#endif #endif
#ifdef SCMP_ARCH_MIPS
case lxc_seccomp_arch_mips: arch = SCMP_ARCH_MIPS; break;
case lxc_seccomp_arch_mips64: arch = SCMP_ARCH_MIPS64; break;
case lxc_seccomp_arch_mips64n32: arch = SCMP_ARCH_MIPS64N32; break;
case lxc_seccomp_arch_mipsel: arch = SCMP_ARCH_MIPSEL; break;
case lxc_seccomp_arch_mipsel64: arch = SCMP_ARCH_MIPSEL64; break;
case lxc_seccomp_arch_mipsel64n32: arch = SCMP_ARCH_MIPSEL64N32; break;
#endif
default: return NULL; default: return NULL;
} }
...@@ -189,7 +215,7 @@ scmp_filter_ctx get_new_ctx(enum lxc_hostarch_t n_arch, uint32_t default_policy_ ...@@ -189,7 +215,7 @@ scmp_filter_ctx get_new_ctx(enum lxc_hostarch_t n_arch, uint32_t default_policy_
ret = seccomp_arch_add(ctx, arch); ret = seccomp_arch_add(ctx, arch);
if (ret != 0) { if (ret != 0) {
ERROR("Seccomp error %d (%s) adding arch: %d", ret, ERROR("Seccomp error %d (%s) adding arch: %d", ret,
strerror(ret), (int)n_arch); strerror(-ret), (int)n_arch);
seccomp_release(ctx); seccomp_release(ctx);
return NULL; return NULL;
} }
...@@ -260,12 +286,12 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf) ...@@ -260,12 +286,12 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf)
{ {
char *p; char *p;
int ret; int ret;
scmp_filter_ctx compat_ctx = NULL; scmp_filter_ctx compat_ctx[2] = { NULL, NULL };
bool blacklist = false; bool blacklist = false;
uint32_t default_policy_action = -1, default_rule_action = -1, action; uint32_t default_policy_action = -1, default_rule_action = -1, action;
enum lxc_hostarch_t native_arch = get_hostarch(), enum lxc_hostarch_t native_arch = get_hostarch(),
cur_rule_arch = native_arch; cur_rule_arch = native_arch;
uint32_t compat_arch = SCMP_ARCH_NATIVE; uint32_t compat_arch[2] = { SCMP_ARCH_NATIVE, SCMP_ARCH_NATIVE };
if (strncmp(line, "blacklist", 9) == 0) if (strncmp(line, "blacklist", 9) == 0)
blacklist = true; blacklist = true;
...@@ -295,27 +321,49 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf) ...@@ -295,27 +321,49 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf)
if (native_arch == lxc_seccomp_arch_amd64) { if (native_arch == lxc_seccomp_arch_amd64) {
cur_rule_arch = lxc_seccomp_arch_all; cur_rule_arch = lxc_seccomp_arch_all;
compat_arch = SCMP_ARCH_X86; compat_arch[0] = SCMP_ARCH_X86;
compat_ctx = get_new_ctx(lxc_seccomp_arch_i386, compat_ctx[0] = get_new_ctx(lxc_seccomp_arch_i386,
default_policy_action); default_policy_action);
if (!compat_ctx) if (!compat_ctx[0])
goto bad; goto bad;
#ifdef SCMP_ARCH_PPC #ifdef SCMP_ARCH_PPC
} else if (native_arch == lxc_seccomp_arch_ppc64) { } else if (native_arch == lxc_seccomp_arch_ppc64) {
cur_rule_arch = lxc_seccomp_arch_all; cur_rule_arch = lxc_seccomp_arch_all;
compat_arch = SCMP_ARCH_PPC; compat_arch[0] = SCMP_ARCH_PPC;
compat_ctx = get_new_ctx(lxc_seccomp_arch_ppc, compat_ctx[0] = get_new_ctx(lxc_seccomp_arch_ppc,
default_policy_action); default_policy_action);
if (!compat_ctx) if (!compat_ctx[0])
goto bad; goto bad;
#endif #endif
#ifdef SCMP_ARCH_ARM #ifdef SCMP_ARCH_ARM
} else if (native_arch == lxc_seccomp_arch_arm64) { } else if (native_arch == lxc_seccomp_arch_arm64) {
cur_rule_arch = lxc_seccomp_arch_all; cur_rule_arch = lxc_seccomp_arch_all;
compat_arch = SCMP_ARCH_ARM; compat_arch[0] = SCMP_ARCH_ARM;
compat_ctx = get_new_ctx(lxc_seccomp_arch_arm, compat_ctx[0] = get_new_ctx(lxc_seccomp_arch_arm,
default_policy_action);
if (!compat_ctx[0])
goto bad;
#endif
#ifdef SCMP_ARCH_MIPS
} else if (native_arch == lxc_seccomp_arch_mips64) {
cur_rule_arch = lxc_seccomp_arch_all;
compat_arch[0] = SCMP_ARCH_MIPS;
compat_arch[1] = SCMP_ARCH_MIPS64N32;
compat_ctx[0] = get_new_ctx(lxc_seccomp_arch_mips,
default_policy_action);
compat_ctx[1] = get_new_ctx(lxc_seccomp_arch_mips64n32,
default_policy_action);
if (!compat_ctx[0] || !compat_ctx[1])
goto bad;
} else if (native_arch == lxc_seccomp_arch_mipsel64) {
cur_rule_arch = lxc_seccomp_arch_all;
compat_arch[0] = SCMP_ARCH_MIPSEL;
compat_arch[1] = SCMP_ARCH_MIPSEL64N32;
compat_ctx[0] = get_new_ctx(lxc_seccomp_arch_mipsel,
default_policy_action); default_policy_action);
if (!compat_ctx) compat_ctx[1] = get_new_ctx(lxc_seccomp_arch_mipsel64n32,
default_policy_action);
if (!compat_ctx[0] || !compat_ctx[1])
goto bad; goto bad;
#endif #endif
} }
...@@ -413,6 +461,53 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf) ...@@ -413,6 +461,53 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf)
cur_rule_arch = lxc_seccomp_arch_ppc; cur_rule_arch = lxc_seccomp_arch_ppc;
} }
#endif #endif
#ifdef SCMP_ARCH_MIPS
else if (strcmp(line, "[mips64]") == 0 ||
strcmp(line, "[MIPS64]") == 0) {
if (native_arch != lxc_seccomp_arch_mips64) {
cur_rule_arch = lxc_seccomp_arch_unknown;
continue;
}
cur_rule_arch = lxc_seccomp_arch_mips64;
} else if (strcmp(line, "[mips64n32]") == 0 ||
strcmp(line, "[MIPS64N32]") == 0) {
if (native_arch != lxc_seccomp_arch_mips64) {
cur_rule_arch = lxc_seccomp_arch_unknown;
continue;
}
cur_rule_arch = lxc_seccomp_arch_mips64n32;
} else if (strcmp(line, "[mips]") == 0 ||
strcmp(line, "[MIPS]") == 0) {
if (native_arch != lxc_seccomp_arch_mips &&
native_arch != lxc_seccomp_arch_mips64) {
cur_rule_arch = lxc_seccomp_arch_unknown;
continue;
}
cur_rule_arch = lxc_seccomp_arch_mips;
} else if (strcmp(line, "[mipsel64]") == 0 ||
strcmp(line, "[MIPSEL64]") == 0) {
if (native_arch != lxc_seccomp_arch_mipsel64) {
cur_rule_arch = lxc_seccomp_arch_unknown;
continue;
}
cur_rule_arch = lxc_seccomp_arch_mipsel64;
} else if (strcmp(line, "[mipsel64n32]") == 0 ||
strcmp(line, "[MIPSEL64N32]") == 0) {
if (native_arch != lxc_seccomp_arch_mipsel64) {
cur_rule_arch = lxc_seccomp_arch_unknown;
continue;
}
cur_rule_arch = lxc_seccomp_arch_mipsel64n32;
} else if (strcmp(line, "[mipsel]") == 0 ||
strcmp(line, "[MIPSEL]") == 0) {
if (native_arch != lxc_seccomp_arch_mipsel &&
native_arch != lxc_seccomp_arch_mipsel64) {
cur_rule_arch = lxc_seccomp_arch_unknown;
continue;
}
cur_rule_arch = lxc_seccomp_arch_mipsel;
}
#endif
else else
goto bad_arch; goto bad_arch;
...@@ -432,14 +527,18 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf) ...@@ -432,14 +527,18 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf)
if (cur_rule_arch == native_arch || if (cur_rule_arch == native_arch ||
cur_rule_arch == lxc_seccomp_arch_native || cur_rule_arch == lxc_seccomp_arch_native ||
compat_arch == SCMP_ARCH_NATIVE) { compat_arch[0] == SCMP_ARCH_NATIVE) {
INFO("Adding native rule for %s action %d", line, action); INFO("Adding native rule for %s action %d", line, action);
if (!do_resolve_add_rule(SCMP_ARCH_NATIVE, line, conf->seccomp_ctx, action)) if (!do_resolve_add_rule(SCMP_ARCH_NATIVE, line, conf->seccomp_ctx, action))
goto bad_rule; goto bad_rule;
} }
else if (cur_rule_arch != lxc_seccomp_arch_all) { else if (cur_rule_arch != lxc_seccomp_arch_all) {
int arch_index =
cur_rule_arch == lxc_seccomp_arch_mips64n32 ||
cur_rule_arch == lxc_seccomp_arch_mipsel64n32 ? 1 : 0;
INFO("Adding compat-only rule for %s action %d", line, action); INFO("Adding compat-only rule for %s action %d", line, action);
if (!do_resolve_add_rule(compat_arch, line, compat_ctx, action)) if (!do_resolve_add_rule(compat_arch[arch_index], line, compat_ctx[arch_index], action))
goto bad_rule; goto bad_rule;
} }
else { else {
...@@ -447,14 +546,18 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf) ...@@ -447,14 +546,18 @@ static int parse_config_v2(FILE *f, char *line, struct lxc_conf *conf)
if (!do_resolve_add_rule(SCMP_ARCH_NATIVE, line, conf->seccomp_ctx, action)) if (!do_resolve_add_rule(SCMP_ARCH_NATIVE, line, conf->seccomp_ctx, action))
goto bad_rule; goto bad_rule;
INFO("Adding compat rule for %s action %d", line, action); INFO("Adding compat rule for %s action %d", line, action);
if (!do_resolve_add_rule(compat_arch, line, compat_ctx, action)) if (!do_resolve_add_rule(compat_arch[0], line, compat_ctx[0], action))
goto bad_rule;
if (compat_arch[1] != SCMP_ARCH_NATIVE &&
!do_resolve_add_rule(compat_arch[1], line, compat_ctx[1], action))
goto bad_rule; goto bad_rule;
} }
} }
if (compat_ctx) { if (compat_ctx[0]) {
INFO("Merging in the compat seccomp ctx into the main one"); INFO("Merging in the compat seccomp ctx into the main one");
if (seccomp_merge(conf->seccomp_ctx, compat_ctx) != 0) { if (seccomp_merge(conf->seccomp_ctx, compat_ctx[0]) != 0 ||
(compat_ctx[1] != NULL && seccomp_merge(conf->seccomp_ctx, compat_ctx[1]) != 0)) {
ERROR("Error merging compat seccomp contexts"); ERROR("Error merging compat seccomp contexts");
goto bad; goto bad;
} }
...@@ -466,8 +569,10 @@ bad_arch: ...@@ -466,8 +569,10 @@ bad_arch:
ERROR("Unsupported arch: %s", line); ERROR("Unsupported arch: %s", line);
bad_rule: bad_rule:
bad: bad:
if (compat_ctx) if (compat_ctx[0])
seccomp_release(compat_ctx); seccomp_release(compat_ctx[0]);
if (compat_ctx[1])
seccomp_release(compat_ctx[1]);
return -1; return -1;
} }
#else /* HAVE_DECL_SECCOMP_SYSCALL_RESOLVE_NAME_ARCH */ #else /* HAVE_DECL_SECCOMP_SYSCALL_RESOLVE_NAME_ARCH */
......
...@@ -117,6 +117,12 @@ struct signalfd_siginfo ...@@ -117,6 +117,12 @@ struct signalfd_siginfo
# define __NR_signalfd4 322 # define __NR_signalfd4 322
# elif __arm__ # elif __arm__
# define __NR_signalfd4 355 # define __NR_signalfd4 355
# elif __mips__ && _MIPS_SIM == _ABIO32
# define __NR_signalfd4 4324
# elif __mips__ && _MIPS_SIM == _ABI64
# define __NR_signalfd4 5283
# elif __mips__ && _MIPS_SIM == _ABIN32
# define __NR_signalfd4 6287
# endif # endif
#endif #endif
...@@ -132,6 +138,12 @@ struct signalfd_siginfo ...@@ -132,6 +138,12 @@ struct signalfd_siginfo
# define __NR_signalfd 316 # define __NR_signalfd 316
# elif __arm__ # elif __arm__
# define __NR_signalfd 349 # define __NR_signalfd 349
# elif __mips__ && _MIPS_SIM == _ABIO32
# define __NR_signalfd 4317
# elif __mips__ && _MIPS_SIM == _ABI64
# define __NR_signalfd 5276
# elif __mips__ && _MIPS_SIM == _ABIN32
# define __NR_signalfd 6280
# endif # endif
#endif #endif
......
...@@ -647,6 +647,8 @@ if [ $? -ne 0 ]; then ...@@ -647,6 +647,8 @@ if [ $? -ne 0 ]; then
fi fi
eval set -- "$options" eval set -- "$options"
littleendian=$(lscpu | grep '^Byte Order' | grep -q Little && echo yes)
arch=$(uname -m) arch=$(uname -m)
if [ "$arch" = "i686" ]; then if [ "$arch" = "i686" ]; then
arch="i386" arch="i386"
...@@ -654,6 +656,10 @@ elif [ "$arch" = "x86_64" ]; then ...@@ -654,6 +656,10 @@ elif [ "$arch" = "x86_64" ]; then
arch="amd64" arch="amd64"
elif [ "$arch" = "armv7l" ]; then elif [ "$arch" = "armv7l" ]; then
arch="armhf" arch="armhf"
elif [ "$arch" = "mips" -a "$littleendian" = "yes" ]; then
arch="mipsel"
elif [ "$arch" = "mips64" -a "$littleendian" = "yes" ]; then
arch="mips64el"
fi fi
hostarch=$arch hostarch=$arch
mainonly=1 mainonly=1
...@@ -711,6 +717,14 @@ if [ "$interpreter" = "" ] ; then ...@@ -711,6 +717,14 @@ if [ "$interpreter" = "" ] ; then
echo "can't create $arch container on $hostarch" echo "can't create $arch container on $hostarch"
exit 1 exit 1
fi fi
if [ $hostarch = "mips" -a $arch != "mips" ] || \
[ $hostarch = "mipsel" -a $arch != "mipsel" ] || \
[ $hostarch = "mips64" -a $arch != "mips" -a $arch != "mips64" ] || \
[ $hostarch = "mips64el" -a $arch != "mipsel" -a $arch != "mips64el" ]; then
echo "can't create $arch container on $hostarch"
exit 1
fi
else else
if ! file -b "${interpreter}" |grep -q "statically linked" ; then if ! file -b "${interpreter}" |grep -q "statically linked" ; then
echo "'${interpreter}' must be statically linked" 1>&2 echo "'${interpreter}' must be statically linked" 1>&2
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment