Qubes OS Security Hardening Guide – 11 tabs + automated helper script

Okay, just breezing through this today…
So basically, this is interactive HTML file you open on a browser to automate hardening Qubes OS?

This is supposed to harden dom0 yet you don’t open browsers on dom0 but, usually, an AppVM that’s isolated from dom0 for obvious reasons.

It seems to make more sense to run the helper script in dom0 just like the Qubes Live Mode script.

1 Like

Just my 2 cents …

Running (arbitrary) scripts in dom0 is a big, BIG no-no. It’s enough (by far) to read instructions, understand what they recommend, what the commands and settings do and apply accordingly.

4 Likes

Save the script in a file, then use qvm-run --pass-io cat… > run.sh. But first, you must understand the risks and do not execute anything until you have reviewed it, because dom0 is the foundation.

2 Likes

You are correct. A person must first verify the file’s integrity themselves, because this is risky.

2 Likes

Hi @abdullah .

I finally decided to give your script a test run. I copied it into dom0, ran chmod +x auto-script.sh and then tried to run it with ./auto-script.sh but I keep getting an error which reads bash: ./auto-script.sh: cannot execute: required file not found

What am I missing here?

1 Like

I have just tested the script myself, and it works perfectly now :+1:.

Regarding the error you encountered earlier (cannot execute: required file not found), it is usually caused by one of two things:

1. Incorrect shebang (interpreter path):
Make sure the very first line of the file is exactly:
#!/bin/bash
(without any extra spaces or characters)

2. The file is saved with Windows line endings (CRLF):
If you copied the script from a browser or web editor, it might contain carriage return characters at the end of each line, which prevents the system from reading the shebang correctly.
Try converting it using:
dos2unix auto-script.sh
Or if dos2unix is not available:
sed -i 's/\r$//' auto-script.sh

To diagnose the issue, you can run:
head -n 1 auto-script.sh
to see the first line of the file, and:
file auto-script.sh
to check the file type (it should show something like Bourne-Again shell script or ASCII text executable).

After applying these fixes, the script is now working fully on my end. Thanks to its developer for this great work.

2 Likes

Hi @abdullah. The fixes worked but now I’ve got another problem.

  1. I ran the script.
  2. I selected 1) Configure kernel parameters (dom0 + VMs)
  3. I then selected 1) Configure dom0 (GRUB + Secureblue sysctl)

And I came across an error that read “Cannot extract UUID from current GRUB”
and prompted me to enter the UUID manually. So I had to look for it in /boot/grub2/grub.cfg (sudo cat /boot/grub2/grub.cfg | grep uuid) myself and copy and paste it. Thankfully that did the trick.

After I rebooted after applying that first step… Qubes still worked fine.

Now I ran 2) Configure all VMs (kernelopts and it ran smoothly.
Although I wanna ask, this option configures only currently existing VMs, right?
What about any new VMs I create afterwards?

2) MAC Randomization + Disable IPv6 and
3) Create Whonix gateways worked without any issues.

I already installed the Kicksecure-18 template by the time I ran
4) Install Kicksecure + set as default but something odd also just happened. I’ll show you a screenshot this time. It happened when I entered “y” when prompted to create a hardened DVM template from Kicksecure.

Now I ran 5) Create RAM Pool scripts and then
6) Create Amnesic Tmpfs script (That’s not my typo. It’s actually how it was spelled in the script. LOL!)…

Okay, I presumed it would do this automatically and now I’m expected to select a VM under this option manually? What am I supposed to do?

I didn’t run 7) Enable Live Mode because @linuxuser1 had recently updated his Qubes Live mode script. So I downloaded and ran that instead. Please check his new updated script and add it to yours accordingly.

8) Destruction tools (BusKill + Emergency) ran fine.

9) LUKS disk encryption hardening didn’t… Because I didn’t set up full disk encryption when I ran my Qubes install this time. I only set it up to practice and test stuff and didn’t want to waste a few extra seconds entering an encryption password everytime I’d boot up.

10) Set up automatic disk mounting in Whonix ran okay though, to be honest, I don’t know what benefit that’s supposed to have.

I presume 11) Run automatic sections (1 to 8) just goes through options 1 to 8 which I already done, right?

I only went through your guide once and was too eager to try out your script to bother researching any further. Although now that I’ve test run the script for myself, now I’m curious to dig deeper into your guide again at my earliest convenience.

2 Likes

Thank you very much for this detailed test. Your feedback is highly valuable. I will address the key points:

  1. kernelopts: This option applies the parameters to all VMs, including templates (qvm-ls --raw-list). New VMs will automatically inherit them from their templates later on.

  2. Amnesic Tmpfs: It is designed to be interactive to give you precise control, as applying it to all VMs might conflict with critical ones like sys-net.

  3. Live Mode: Great that you tried linuxuser1’s version. I will review it and integrate it with proper attribution.

  4. Automatic mounting in Whonix (10): The main goal is to bypass the noexec restriction in the /mnt path, by mounting drives to /home/user/usb so you can run scripts and portable applications smoothly.

  5. LUKS (9): It won’t work because your system is not encrypted, which is expected.

  6. Creation errors (template_for_dispvms and rw=False):

    • First error: The script used qvm-clone, which produced a TemplateVM, but the property requires an AppVM. Before replacing the old line, you should first remove the existing kicksecure-18-dvm VM (if it exists) because it was created by the previous script as a TemplateVM and will cause conflicts if not deleted. Then, replace the old qvm-clone line with the following:

      Old line (to be removed):

      qvm-clone kicksecure-18 kicksecure-18-dvm
      

      New lines (to replace it):

      qvm-create --template kicksecure-18 --label red kicksecure-18-dvm
      
    • Second error: The rw=False property on root is unstable and causes issues, so it was removed and will not be reinstated. The script will rely solely on template_for_dispvms=True.

Once again, thank you. These observations make the script better for the community.

2 Likes

@abdullah. Hi.

Have those changes been made yet? It’d be awesome to add a new post and edit your first post to let us know of any new updates made to your script. Keep up the good work and I’m glad to help. :+1:

1 Like

Also @abdullah. Now that I know what Amnesic Tmpfs is for, having gone through your guide again, can you recommend where I should apply it?

I do plan to apply it to Default-DVM. Where else do you think is safe to do it? Any of the service qubes? In whonix gateway and/or workstation?

1 Like

Hello, excellent question. Now that you understand how Amnesic Tmpfs works, here is my practical recommendation:

  • default-dvm: Excellent choice. Applying it here ensures that any disposable VM you create is automatically “memoryless,” wiping all traces of the session after shutdown. This is a strong security measure.

  • Service VMs (sys-net, sys-firewall, sys-usb): Not recommended. These VMs need to retain their settings (like firewall rules, network configurations) between sessions, and applying Amnesic may cause stability issues.

  • Whonix Gateways and Workstations: Advanced option. It can be applied, but requires additional configuration in /rw/config/rc.local to ensure Tor works properly. I recommend this only if you are prepared to manually tweak settings and have sufficient RAM (preferably 32GB).

  • Personal VMs (personal, work): Depends on your needs. If you use them for sensitive tasks and want to immediately erase traces, it is a good choice. However, if you store files or settings you need persistently, it is better to keep them outside Amnesic.


:light_bulb: Additional Tip: If you want “complete forgetting” rather than just wiping specific folders

If your goal is total amnesia (i.e., the entire VM vanishes without any trace upon shutdown), then RAM Pool scripts are the better option for you. They make the entire VM run purely in RAM, and when stopped, the VM evaporates completely without leaving any files or logs on disk.

The difference in brief:

  • Amnesic Tmpfs: Wipes only specific folders (like /home, /tmp, /var/log).
  • RAM Pool: Wipes the entire VM (OS + applications + files).

But with an important caveat: RAM Pool is very similar to the Tails experience, but it is not Tails itself; it gives you an “amnesic” experience inside Qubes, but the underlying system (dom0) remains on disk unless you use an advanced mode like “Live Mode”.

Summary: default-dvm is the safest and easiest choice for Amnesic Tmpfs. However, if you want complete deniability and have enough RAM, use RAM Pool scripts instead.

1 Like

What configuration am I supposed to make in that file?

That is exactly my goal here. I plan to use Live Mode all the time. But while I want many of my VMs to be put in the RAM Pool, others will have to be Ephemerally encrypted instead (when I run @linuxuser1’s Live Mode script so should those still be applied with Amnesic Tmpfs?

And again, has your script been updated recently? Can we expect any updates in the near future?

1 Like

Hello again, excellent questions that get right to the heart of the matter. I will answer them in detail:


1. What Settings Are Required in /rw/config/rc.local for Whonix?

Simply put, Whonix has certain “peculiarities” in its operation that require special handling. If you apply Amnesic Tmpfs to it without the correct configuration, the Tor Browser will not start.

The solution is simple: the startup commands in /rw/config/rc.local differ between a regular amnesic-dvm and an amnesic-whonix-dvm. The solution is to copy the correct Whonix-specific commands from a working template to your VM’s rc.local file. You can find the correct template in community posts on this topic.


2. Combining Live Mode, RAM Pool, and Amnesic Tmpfs – Important Warning

I do not recommend combining Amnesic Tmpfs and RAM Pool on the same VM. The reason is that they both try to achieve “amnesia” in different and conflicting ways:

  • RAM Pool: Makes the entire VM run in RAM, and when stopped, the VM vanishes completely without any trace.
  • Amnesic Tmpfs: Redirects specific folders (like /home) to RAM, but the operating system and applications remain on disk.

When applied together, Amnesic Tmpfs will try to redirect folders like /home to /volatile, while RAM Pool puts the entire VM in RAM. This overlap can cause:

  • Mount point conflicts.
  • Boot failures because the system tries to access non-existent paths.
  • Unexpected behavior from applications that expect a stable filesystem.

Therefore, the recommendation is:

  • If you want full amnesia for a specific VM, use RAM Pool only.
  • If you want partial amnesia (for specific folders only), use Amnesic Tmpfs only.
  • Do not mix them on the same VM.

For the scenario of Live Mode + RAM Pool: This is an excellent and safe combination, because Live Mode makes dom0 run in RAM, and RAM Pool does the same for individual VMs. There is no conflict between them.


3. Important Warning: Updates and Software Installation

  • For RAM Pool: If you want to update or install software on a VM using RAM Pool, you must boot that VM in normal mode (without RAM Pool) first, because the entire VM runs in RAM and any changes will not be saved after shutdown.

  • For Amnesic Tmpfs: You can update and install software without needing to return to normal mode, because the core system folders (/usr, /etc, /bin) remain on disk and are not affected by Amnesic Tmpfs. Only the redirected folders (like /home) disappear upon shutdown.

Note: dom0 is not affected by these features, so you can update it normally without restrictions.


4. Script Updates

Within this week, I will add linuxuser1’s Live Mode update to the main auto-script.sh, with proper attribution and the necessary adjustments to make it compatible with the current script’s structure.

Yes, new updates are coming. I welcome any suggestions or Pull Requests to improve the work. Stay tuned!


5. Final Recommendation (Step-by-Step Approach)

What you are describing is an advanced setup. I recommend starting gradually:

  1. First, try RAM Pool on default-dvm.
  2. Then, try Live Mode on dom0.
  3. If you want Amnesic Tmpfs, apply it only to VMs that do not use RAM Pool.

And always remember:

  • For full amnesia: Live Mode + RAM Pool is the strongest option. It wipes dom0 and VMs together, but requires large RAM (32GB+) and requires returning to normal mode for updates.
  • For partial amnesia: Amnesic Tmpfs is sufficient and does not hinder updates.

6. Quick Summary

  • Do not combine Amnesic Tmpfs and RAM Pool on the same VM.
  • RAM Pool: Full VM disappears on shutdown. Updates require normal mode.
  • Amnesic Tmpfs: Only wipes specific folders. Updates work normally.
  • Live Mode + RAM Pool: Best for full amnesia, but memory-intensive.
  • Script updates: Coming this week with linuxuser1’s Live Mode.

Final Reminder: This is an advanced setup, so start gradually and test each layer independently. Good luck with your experiment!

1 Like

Hey @abdullah

Another thought just occurred when I was reading the Portable Apps section in your guide.

You suggested that any portable apps like SimpleX and Cwitch are connected to Sys-Whonix or used in Whonix-Workstation so why do we need to use torsocks as well?

1 Like

Thank you for this precise observation that goes to the heart of the matter.

First, the primary goal of this method is to achieve full Stream Isolation. By using a direct SOCKS connection (127.0.0.1:9050), we leverage Tor’s “isolate-by-auth” feature, granting each profile (and even each contact with the Transport isolation option) its own independent Tor circuit. This is something the transparent proxy in Whonix does not provide, as it forces all applications to share a single circuit.

Second, regarding your note about the “Use .onion hosts” option, you are absolutely right. This option does not appear in the application’s interface unless the “Use SOCKS proxy” option is enabled.

This is where torsocks plays a supporting role. In some Whonix environments, the application may not detect the SOCKS proxy automatically. Using torsocks allows SimpleX to “see” the proxy, thereby making the .onion option appear in the settings.

The crucial point that warrants practical verification is this: once you enable the “.onion” option and set it to “Required” (even if this was done via torsocks), this setting is expected to be saved and continue working even after restarting the application normally (without torsocks). This is because the application will read the setting from its files and connect directly to SOCKS to enforce the use of .onion.

In summary: torsocks is merely a temporary “key” to reveal the .onion option. The optimal solution for maximum privacy is relying on direct SOCKS for stream isolation, combined with enforcing .onion exclusively.

Call for practical verification:
I invite you to test this yourself and see if the setting persists after closing torsocks. This is the best way to confirm the application’s behavior in your specific environment, and we look forward to hearing your results.

1 Like

I clicked the link but its all in farsi. is there an english button I didn’t find?

Can this orient on my browsers localization automatically pls?

1 Like

There is an English version, right at the bottom of the first post.

1 Like

Okay. What grabbed my attention was sys-whonix routing everything through the same Tor circuit so torsocks helps give everything each their own circuit, right?

If that’s the case, I suppose I should use torsocks with every AppVM routed to sys-whonix, eh?

1 Like

That link just gives me a white page x)

1 Like

Rather than stating that this guide is for advanced users, it would be more beneficiary to suggest which threat model exactly it is advised for.

I was incentivized to write this especially because of the “features” like wiping some things out and some not, which might be confusing for users with a specific need with their threat model.

I don’t want to be harsh, but year after year I am getting an impression that Qubes OS for many people is a toy: they do things with it to play with it because they can, not because of a threat model necessity. Not to speak about bringing monolithic OS way of thinking with them while playing with Qubes.

2 Likes