modif: replace --keep-hostname with new --hostname-randomize

Changes:

* Keep hostname by default (same as using `--keep-hostname`)
* Add  `--hostname-randomize` command to randomize the hostname
* Ignore `--keep-hostname` command and print a warning if it is used

Setting a different hostname inside of the sandbox may prevent X11
programs from authenticating to the X server and displaying windows at
all (see #7062).

To avoid breakage, keep the hostname as is by default and only set it to
a random value if a new `hostname-randomize` command is used.

This also avoids potentially surprising behavior, as the user might not
expect the hostname to be changed inside of the sandbox, considering
that usually the protections that are applied firejail involve
restricting access to resources (like file paths), rather than modifying
their values inside of the sandbox.

Fixes #7062

Relates to #7048 #7069.
This commit is contained in:
Kelvin M. Klann 2026-03-07 10:02:52 -03:00
parent 2e9a96bbdb
commit 09329b990f
15 changed files with 87 additions and 53 deletions

View file

@ -443,15 +443,21 @@ full path or a relative path for the filename.
Parent is shutting down, bye…
```
### --keep-hostname
### --hostname-randomize
```text
--keep-hostname
By default, the hostname is replaced by a random name generated
by firejail at startup. Use this option to disable this feature.
--hostname-randomize
Set sandbox hostname to a random value generated by firejail.
This is incompatible with --hostname.
Example:
$ firejail --keep-hostname
$ firejail --hostname-randomize /usr/bin/firefox
Note: Changing the hostname may cause breakage related to
networking (see #7048
<https://github.com/netblue30/firejail/issues/7048>) and may
cause X11 programs to crash on startup due to not being able to
authenticate to the X server (see #7062
<https://github.com/netblue30/firejail/issues/7062>).
```
### Landlock support - ongoing/experimental

View file

@ -7,7 +7,9 @@ firejail (0.9.79) baseline; urgency=low
for sandbox escape (cbf4308 c8a6707)
* feature: hide PID 1 inside of the sandbox and add --unhide-pid1 command to
unhide (#7046)
* feature: add --keep-hostname command and profile option (#7069)
* feature: add --hostname-randomize command and profile option - stop
randomizing the hostname by default to fix breakage with X11 programs
(#7062 #7069 #7095)
* feature: add --debug-syscall-groups command (#7049 #7055)
* feature: add apparmor profiles for --nettrace command (#7093)
* modif: reorganize & update syscall groups (#7024 #7027 #7034 #7039 #7042

View file

@ -8,6 +8,7 @@ caps
deterministic-exit-code
deterministic-shutdown
disable-mnt
hostname-randomize
ipc-namespace
keep-config-pulse
keep-dev-ntsync

View file

@ -6,6 +6,8 @@ include libreoffice.local
# Persistent global definitions
include globals.local
ignore hostname-randomize
noblacklist ${HOME}/.config/libreoffice
noblacklist ${HOME}/.local/share/gvfs-metadata
noblacklist /usr/local/sbin
@ -44,8 +46,6 @@ include whitelist-var-common.inc
#ignore seccomp
#ignore tracelog
keep-hostname
apparmor
caps.drop all
netfilter

View file

@ -25,7 +25,6 @@ keep-dev-ntsync
keep-dev-shm
keep-dev-tpm
keep-fd all
keep-hostname
keep-shell-rc
keep-var-tmp
writable-etc

View file

@ -168,7 +168,6 @@ include globals.local
##keep-dev-shm
##keep-dev-tpm
##keep-fd all
##keep-hostname
##keep-shell-rc
##keep-var-tmp
##writable-etc
@ -181,6 +180,7 @@ include globals.local
#caps.drop all
##caps.keep CAPS
##hostname NAME
##hostname-randomize
# CLI only
##ipc-namespace
# breaks audio and sometimes dbus related functions

View file

@ -375,7 +375,7 @@ extern int arg_netlock; // netlocker
extern int arg_restrict_namespaces;
extern int arg_allow_bwrap;
extern int arg_unhide_pid1;
extern int arg_keep_hostname;
extern int arg_hostname_randomize;
typedef enum {
DBUS_POLICY_ALLOW, // Allow unrestricted access to the bus
@ -691,7 +691,8 @@ void fs_tracefile(void);
void fs_trace(void);
// fs_hostname.c
void fs_hostname(void);
char *random_hostname(void);
void fs_hostname(const char *orig_hostname);
char *fs_check_hosts_file(const char *fname);
void fs_store_hosts_file(void);
void fs_mount_hosts_file(void);

View file

@ -25,9 +25,7 @@
#include <fcntl.h>
// build a random host name
static char *random_hostname(void) {
assert(!arg_keep_hostname);
char *random_hostname(void) {
char vowels[] = { 'a', 'e', 'i', 'o', 'u'};
char consonants[] = {'b', 'c', 'c', 'c', 'g', 'h', 'h', 'h', 'h', 'h',
'j', 'j', 'k', 'k', 'k', 'k', 'k', 'k', 'k', 'k', 'k', 'k', 'm', 'm', 'm', 'm', 'n', 'n', 'n', 'n', 'n',
@ -54,11 +52,16 @@ static char *random_hostname(void) {
return name;
}
void fs_hostname(void) {
assert(!arg_keep_hostname);
void fs_hostname(const char *orig_hostname) {
char tmp[256] = "";
const char *hostname = orig_hostname;
if (!hostname) {
if (gethostname(tmp, 256 - 1))
errExit("gethostname");
hostname = tmp;
}
assert(hostname);
if (!cfg.hostname)
cfg.hostname = random_hostname();
struct stat s;
// create a new /etc/hostname
@ -70,7 +73,7 @@ void fs_hostname(void) {
FILE *fp = fopen(RUN_HOSTNAME_FILE, "we");
if (!fp)
goto errexit;
fprintf(fp, "%s\n", cfg.hostname);
fprintf(fp, "%s\n", hostname);
SET_PERMS_STREAM(fp, 0, 0, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
fclose(fp);
@ -108,12 +111,12 @@ void fs_hostname(void) {
// copy line
if (strstr(buf, "127.0.0.1") && done_ipv4 == 0) {
done_ipv4 = 1;
fprintf(fp2, "127.0.0.1 %s\n", cfg.hostname);
fprintf(fp2, "127.0.0.1 %s\n", hostname);
fprintf(fp2, "127.0.0.1 localhost\n");
}
else if (strstr(buf, "::1") && done_ipv6 == 0) {
done_ipv6 = 1;
fprintf(fp2, "::1 %s\n", cfg.hostname);
fprintf(fp2, "::1 %s\n", hostname);
fprintf(fp2, "::1 localhost\n");
}
else

View file

@ -171,7 +171,7 @@ int arg_netlock = 0;
int arg_restrict_namespaces = 0;
int arg_allow_bwrap = 0;
int arg_unhide_pid1 = 0;
int arg_keep_hostname = 0;
int arg_hostname_randomize = 0;
int parent_to_child_fds[2];
int child_to_parent_fds[2];
@ -2128,8 +2128,8 @@ int main(int argc, char **argv, char **envp) {
}
}
else if (strncmp(argv[i], "--hostname=", 11) == 0) {
if (arg_keep_hostname) {
fprintf(stderr, "Error: hostname and keep-hostname are mutually exclusive\n");
if (arg_hostname_randomize) {
fprintf(stderr, "Error: hostname and hostname-randomize are mutually exclusive\n");
exit(1);
}
cfg.hostname = argv[i] + 11;
@ -2142,13 +2142,16 @@ int main(int argc, char **argv, char **envp) {
return 1;
}
}
else if (strcmp(argv[i], "--keep-hostname") == 0) {
else if (strcmp(argv[i], "--hostname-randomize") == 0) {
if (cfg.hostname) {
fprintf(stderr, "Error: hostname and keep-hostname are mutually exclusive\n");
fprintf(stderr, "Error: hostname and hostname-randomize are mutually exclusive\n");
exit(1);
}
arg_keep_hostname = 1;
arg_hostname_randomize = 1;
}
// TODO: Fully remove keep-hostname after 0.9.80.
else if (strcmp(argv[i], "--keep-hostname") == 0)
fwarning("ignoring removed command: --keep-hostname (see --hostname-randomize)\n");
else if (strcmp(argv[i], "--nogroups") == 0)
arg_nogroups = 1;
#ifdef HAVE_USERNS

View file

@ -1200,8 +1200,8 @@ int profile_check_line(char *ptr, int lineno, const char *fname) {
// hostname
if (strncmp(ptr, "hostname ", 9) == 0) {
if (arg_keep_hostname) {
fprintf(stderr, "Error: hostname and keep-hostname are mutually exclusive\n");
if (arg_hostname_randomize) {
fprintf(stderr, "Error: hostname and hostname-randomize are mutually exclusive\n");
exit(1);
}
cfg.hostname = ptr + 9;
@ -1215,12 +1215,17 @@ int profile_check_line(char *ptr, int lineno, const char *fname) {
}
return 0;
}
if (strncmp(ptr, "keep-hostname", 13) == 0) {
if (strncmp(ptr, "hostname-randomize", 18) == 0) {
if (cfg.hostname) {
fprintf(stderr, "Error: hostname and keep-hostname are mutually exclusive\n");
fprintf(stderr, "Error: hostname and hostname-randomize are mutually exclusive\n");
exit(1);
}
arg_keep_hostname = 1;
arg_hostname_randomize = 1;
return 0;
}
// TODO: Fully remove keep-hostname after 0.9.80.
if (strncmp(ptr, "keep-hostname", 13) == 0) {
fwarning("ignoring removed command: keep-hostname (see hostname-randomize)\n");
return 0;
}

View file

@ -980,15 +980,18 @@ int sandbox(void* sandbox_arg) {
//****************************
// hosts and hostname
//****************************
if (!arg_keep_hostname) {
fs_hostname();
if (!cfg.hostname && arg_hostname_randomize)
cfg.hostname = random_hostname();
if (cfg.hostname) {
// /usr/bin/hostname is blacklisted in default.profile
// test this using cat /proc/sys/kernel/hostname,
assert(cfg.hostname);
if (sethostname(cfg.hostname, strlen(cfg.hostname)) < 0)
errExit("sethostname");
}
fs_hostname(cfg.hostname);
//****************************
// /etc overrides from the network namespace
//****************************

View file

@ -108,6 +108,7 @@ static const char *const usage_str =
#endif
" --help, -? - this help screen.\n"
" --hostname=name - set sandbox hostname.\n"
" --hostname-randomize - set sandbox hostname to a random value.\n"
" --hosts-file=file - use file as /etc/hosts.\n"
#ifdef HAVE_NETWORK
" --icmptrace - monitor Server Name Indiication (TLS/SNI).\n"
@ -136,7 +137,6 @@ static const char *const usage_str =
" --keep-dev-shm - /dev/shm directory is untouched (even with --private-dev).\n"
" --keep-dev-tpm - /dev/tpm* devices are untouched (even with --private-dev).\n"
" --keep-fd - inherit open file descriptors to sandbox.\n"
" --keep-hostname - use the current hostname\n"
" --keep-shell-rc - do not copy shell rc files from /etc/skel\n"
" --keep-var-tmp - /var/tmp directory is untouched.\n"
#ifdef HAVE_LANDLOCK

View file

@ -915,9 +915,8 @@ Set a DNS server for the sandbox. Up to three DNS servers can be defined.
Set a hostname for the sandbox.
.TP
\fBkeep\-hostname
By default, the hostname is replaced by a random name generated
by firejail at startup. Use this option to disable this feature.
\fBhostname\-randomize
Set sandbox hostname to a random value generated by firejail.
.TP
\fBhosts\-file file

View file

@ -985,6 +985,8 @@ Print options end exit.
\fB\-\-hostname=name
Set sandbox hostname.
.br
This is incompatible with \fB\-\-hostname\-randomize\fR.
.br
For valid names, see the \fBNAME VALIDATION\fR section.
.br
@ -993,6 +995,28 @@ Example:
.br
$ firejail \-\-hostname=officepc /usr/bin/firefox
.TP
\fB\-\-hostname\-randomize
Set sandbox hostname to a random value generated by firejail.
.br
This is incompatible with \fB\-\-hostname\fR.
.br
.br
Example:
.br
$ firejail \-\-hostname-randomize /usr/bin/firefox
.br
Note: Changing the hostname may cause breakage related to networking (see
.UR https://github.com/netblue30/firejail/issues/7048
#7048
.UE )
and may cause X11 programs to crash on startup due to not being able to
authenticate to the X server (see
.UR https://github.com/netblue30/firejail/issues/7062
#7062
.UE ).
.TP
\fB\-\-hosts-file=file
Use file as /etc/hosts.
@ -1357,18 +1381,6 @@ Example:
.br
$ firejail \-\-keep\-fd=3,4,5
.TP
\fB\-\-keep\-hostname
By default, the hostname is replaced by a random name generated by firejail
at startup. Use this option to disable this feature.
.br
.br
Example:
.br
$ firejail \-\-keep\-hostname
.br
.TP
\fB\-\-keep\-shell\-rc
By default, when using a private home directory, firejail copies files from the

View file

@ -108,7 +108,7 @@ expect {
sleep 1
# random hostname
send -- "firejail cat /etc/hostname\r"
send -- "firejail --hostname-randomize cat /etc/hostname\r"
expect {
timeout {puts "TESTING ERROR 8\n";exit}
"Child process initialized"