Raspberry Pi Minecraft Server Setup Script w/ Startup Service

Minecraft 1.17 - Caves and Cliffs Update
Minecraft 1.17 – Caves and Cliffs Update

Minecraft 1.17 (Caves and Cliffs Update) is here! This script and guide are written to help you get a great performing Raspberry Pi Minecraft server up and running in only a few minutes.

This is the standalone version. It runs on most flavors of Linux and should work on most architectures as well (arm, aarch64, etc.).

I highly recommend using Docker over the standalone version for most people. Installing Docker is as simple as sudo apt install docker.io. There are 3 Docker options available:

It’s now possible to convert your worlds between Bedrock and Java versions. Check out my guide on Chunker here for more information.

Features

  • Sets up fully operational Minecraft server in a couple of minutes
  • Runs the highly efficient “Paper” Minecraft server
  • Raspbian / Ubuntu / Debian distributions supported
  • Installs and configures OpenJDK 18
  • Sets up Minecraft as a system service with option to autostart at boot
  • Automatic backups to minecraft/backups when server restarts
  • Updates automatically to the latest version when server is started
  • Easy control of server with start.sh, stop.sh and restart.sh scripts
  • Optional scheduled daily restart of Pi using cron

Requirements

  • Raspberry Pi model with 1 GB of RAM or higher. Basically a Raspberry Pi 2B or higher. (No Zero unfortunately, 512MB is not enough RAM to do this, I’ve tried!)
  • Headless Linux distribution such as Raspbian Buster Lite, Ubuntu Server 18.04.2, or any Debian based distribution (GUI distros can be used at the expense of available RAM and server performance)
  • Solid state drive highly recommended but not required.
    You can get a SSD setup on a Pi for less than most Micro SD cards cost. See my article here for details
  • If using MicroSD you want to be using a high range card otherwise you will really be hurting on IO when the server is reading/writing chunks of terrain! Click here for MicroSD card benchmarks/recommendations.

Recommended Gear

Minecraft Java for PC
Minecraft Java for PC / Mac / Linux*
Raspberry Pi 4
Raspberry Pi 4

The Raspberry Pi 4 is available in different memory configurations all the way up to 8 GB. It’s about the size of a credit card and uses an extremely low amount of power making it ideal for all sorts of projects and ideas!

Links: Amazon.com*, AliExpress*, Amazon.ca*, Amazon.com.au*, Amazon*.co.jp*, Amazon.co.uk*, Amazon.de*, Amazon.es*, Amazon.fr*, Amazon.it*, Amazon.nl*, Amazon.pl*, Amazon.se*, Amazon.sg*

Raspberry Pi 400 Kit
Raspberry Pi 400 Kit

The Raspberry Pi 400 kit includes everything you need for a full Pi 400 desktop build. The Pi 400 is the fastest Raspberry Pi ever released and comes in the form factor of a keyboard!

Links: Amazon.com*, AliExpress*, Amazon.ca*, Amazon.com.au*, Amazon.co.jp*, Amazon.co.uk*, Amazon.de*, Amazon.es*, Amazon.fr*, Amazon.it*, Amazon.nl*, Amazon.pl*, Amazon.se*, Amazon.sg*

Kingston A400 SSD
Kingston A400 2.5″ SATA SSD

The Kingston A400 has been a great drive to use with the Pi for years. It’s reliable, widely available around the world, has low power requirements and performs very well. It’s also very affordable. This drive has been benchmarked over 1000 times at pibenchmarks.com and is the #1 most popular SSD among the Pi community!

Links: AliExpress*, Amazon.com*, Amazon.ca*, Amazon.com.au*, Amazon.co.jp*, Amazon.co.uk*, Amazon.de*, Amazon.es*, Amazon.fr*, Amazon.it*, Amazon.nl*, Amazon.pl*, Amazon.se*, Amazon.sg*

StarTech 2.5" SATA to USB 3.0/3.1 Adapter
StarTech 2.5″ SATA to USB 3.1 Adapter

The USB 3.1 variant of the StarTech 2.5″ SATA adapter works well with the Pi 4. The USB 3.0 variant doesn’t have firmware updates available and is not recommended.

Links: Amazon.com*, Amazon.ca*, Amazon.com.au*, Amazon.co.jp*, Amazon.co.uk*, Amazon.de*, Amazon.es*, Amazon.fr*, Amazon.it*, Amazon.nl*, Amazon.pl*, Amazon.se*, Amazon.sg*

SD Card Setup:

SanDisk Extreme A1
SanDisk Extreme A1

The SanDisk Extreme A1-A2 SD card has the best scoring SD card on Pi Benchmarks for years and is second in popularity only to the SanDisk Ultra (often included in combo kits). The application class (A1) means random I/O speeds (very important when running an OS) have to meet a higher standard. There’s no benefit on the Pi for A2 right now so get whichever is cheaper/available.

Links: AliExpress*, Amazon.com*, Amazon.ca*, Amazon.com.au*, Amazon.co.jp*, Amazon.co.uk*, Amazon.de*, Amazon.es*, Amazon.fr*, Amazon.it*, Amazon.nl*, Amazon.pl*, Amazon.se*, Amazon.sg*

Choosing a Linux Distribution

The most important consideration when choosing which flavor of Linux to run the server on is simple: available RAM. Headless Linux distributions such as Raspbian Lite that don’t have a built in GUI have

Our biggest obstacle when running a Minecraft server on the Pi is available RAM since 1 GB is extremely low for this type of server. To have a playable experience you should not be running anything else on the Pi so all memory is available to be used.

After testing on many different distros I am finding Raspbian Lite and Ubuntu Server 18.04.4 32-bit to be the best choices. These distributions come with very few background processes and have rock solid support and performance.

64-bit vs 32-bit

There’s a lot of discussion in the Pi world about the up and coming aarch64 64-bit distributions vs. armhf 32-bit distributions. They have been and continue to improve dramatically. There are already use cases where 64-bit is far superior such as video encoding, advanced compression, etc.

So how about for running a Minecraft server? I have been testing extensively with Ubuntu Server 18.04 64-bit and the Debian Buster 64-bit. I have consistently had worse performance and stability than on 32-bit versions of the exact same distros.

But how can that be? It’s certainly true that Minecraft servers benefit in CPU performance from 64-bit versions of Java. The answer is actually incredibly simple: memory. The server running on a 64-bit Java Virtual Machine uses a minimum of about 100 MB more memory. This makes perfect sense because 64 bits > 32 bits by definition!

The Raspberry Pi’s 1 GB of memory has been the biggest obstacle for this project since the very beginning. Back when I first went into the Paper Minecraft developer IRC room and told them what I was trying to do I was practically laughed out of the chat room for even thinking of trying this. Most Minecraft server branches including vanilla can’t even start on the Pi because of the limited memory.

For a dedicated Minecraft server on the Pi I very highly recommend staying 32-bit. You will have more available memory which means it will be much faster and more stable. Since memory is our bottleneck the increased CPU throughput does not help us and losing *any* of our memory is disastrous!

If the Raspberry Pi 4 has more memory like we all expect it to this recommendation will change completely. Even 2 GB of memory would make the extra memory that 64-bit uses a non-issue and the CPU throughput performance gains very desirable. For now though stay 32-bit for a Minecraft server!

Tested Distributions

Raspberry Pi OS – It’s Raspbian. It has very low memory usage and is the official distribution of the Raspberry Pi. The server runs very well on this. It’s overall the best choice. The Buster release has made OpenJDK 11 available on it so it’s no longer behind the rest of the distros.

Ubuntu Server 18.04 / 20.04 – Ubuntu Server is my favorite Linux distro. I use it for nearly all of my projects. The performance of the 32-bit armhf version is on par with Raspbian. It’s a great choice! Click here for my Ubuntu setup guide for Raspberry Pi. The 64-bit version is not a fantastic choice and not recommended because of the higher memory usage. Stick with 32-bit and you’ll be a happy camper with Ubuntu Server.

Debian Buster 64-bit – Debian is the distribution Raspbian is based on. This version is a preview of Debian “Buster” which is the successor to Stretch and will be the next version of Raspbian when it is released. I like this distribution but it is currently still unofficial and unsupported. Performance and stability was less than Ubuntu and Raspbian.

Minecraft Server Installation

SSH into your Raspberry Pi and paste the following commands:

curl https://raw.githubusercontent.com/TheRemote/RaspberryPiMinecraft/master/SetupMinecraft.sh | bash

The script will setup the Minecraft sever and ask you some questions on how to configure it. I’ll explain here what they mean.

“Enter amount of memory in megabytes to dedicate to the Minecraft server” – The amount of memory that will be dedicated to the Minecraft server. The more the better, but you must leave some room for the operating system background processes.

If you exceed the total available memory either the server will crash or the Pi will get incredibly slow to the point where your SSH session will start timing out. The setup script will make a recommendation to you which is your available memory – 10% for headroom. If you aren’t sure what to put just go with the recommended amount.

Note for Raspberry Pi 4: Currently on 32-bit Raspbian 2700 MB is the maximum that Linux will let us allocate in a 32 bit environment. The script has been updated to check for this as the server will not start if it is set over 2700M on a 32 bit server. 64 bit operating systems will be able to allocate all available memory as Pi 4 support rolls out for them.

“Start Minecraft server at startup automatically (y/n)?” – This will set the Minecraft service to start automatically when your Pi boots. This is great because whenever you want to play you can just plug it in and go without having to SSH in.

“Automatically reboot Pi and update server at 4am daily (y/n)?” – This will add a cron job to the server that reboots the Pi every day at 4am. This is great because every time the server restarts it backs up the server and updates to the latest version. See the “Scheduled Daily Reboots” section below for information on how to customize the time or remove the reboot.

That is it for the setup script. The server will finish configuring and start!

Check Java Version

Sometimes if you have multiple versions of Java installed the wrong version of Java will be selected as the default. If the server didn’t start check that the right version of Java is selected with this command:

sudo update-alternatives --config java

If you get the message “update-alternatives: error: no alternatives for java” then you only have one version of Java installed and can skip to the next section.

If you are presented with a list of choices then your machine has multiple versions of Java installed. It will look like this:

update-alternatives: warning: /etc/alternatives/java has been changed (manually or by a script); switching to manual updates only
There are 2 choices for the alternative java (providing /usr/bin/java).

  Selection    Path                                            Priority   Status
------------------------------------------------------------
  0            /usr/lib/jvm/java-11-openjdk-amd64/bin/java      1101      auto mode
  1            /usr/lib/jvm/java-11-openjdk-amd64/bin/java      1101      manual mode
  2            /usr/lib/jvm/java-8-openjdk-amd64/jre/bin/java   1081      manual mode

You will usually want to just select the newest version of OpenJDK that is listed so you would type 0 and press enter. In some cases on some platforms you may want to switch to the official Oracle JDK although I strongly recommend sticking with OpenJDK!

First Run

The first time you run the server it will take a little longer to start since it is generating all the server data. If you try to log in before it fully starts you will get a connection timeout error. Watch for the line: “Timings Reset”. This is the last line that prints when the server is ready to rock and roll. At this point you will be able to connect successfully.

The very first time you log into the server it will be slow for about 1-2 minutes. This is because since nobody has logged in before the server has to scramble to generate all the chunks within your view distance (10 by default) and send them to you/store them. During this time you may not be able to see very far and if you try to destroy blocks there will be noticeable lag from when they break to when they actually disappear.

Don’t panic! This will go away within a couple of minutes as the Pi catches up with all the first time login stuff it needs to do. Performance stabilizes and it will feel very much like the offline experience after that.

If you are hosting for a few friends I’d recommend logging in for the first time right after you set up the server instead of having several people nail a blank server at first startup. This gets it out of the way and when everyone is ready to log in the starting area chunks will be fully fleshed out and the Pi just has to read them. It’s an order of magnitude faster for the Pi to read chunks than to generate and store chunks.

In my experience after the initial login exploring new parts of the server doesn’t cause any lag even though new chunks are being generated. The reason for this is that when you’re walking it’s really only having to generate a new chunk as you get close to the border instead of a huge square area of chunks in all directions and all at the same time like during the first login.

Benchmarking / Testing Storage

If you’re getting poor performance or just want to verify everything is working correctly you may want to run my storage benchmark with:

sudo curl https://raw.githubusercontent.com/TheRemote/PiBenchmarks/master/Storage.sh | sudo bash

If you search for the model of your drive on pibenchmarks.com you can compare your score with others and make sure the drive is performing correctly!

Changing Minecraft Server Version

To override the default version let’s grab a copy of the script locally:

wget https://raw.githubusercontent.com/TheRemote/RaspberryPiMinecraft/master/SetupMinecraft.sh 
nano SetupMinecraft.sh

Now make these changes from inside nano:

Version="1.16.5" 
AllowLocalCopy="1"

Now press Ctrl+X to exit nano and answer “y” to save. Now let’s run the script:

chmod +x SetupMinecraft.sh
./SetupMinecraft.sh

And the setup will run and install the version of Minecraft you set at the top of the file!

Changing Minecraft Client Version

If you are wisely running the “stable” branch instead of the “development” branch there will be times where you need to select the version of Minecraft to run otherwise you will get an error message that your client is outdated when you try to log in.

Fortunately this is very easy. Open up the Minecraft launcher and instead of hitting “Play” choose “Launch Options” in the menu at the top of the window. It will look like this:

Minecraft launch options
Minecraft Launcher “Launch Options” Tab

Click the “Add new” button and pick which version you want to add. You can optionally gave it a name or just click save.

Now when you go back to the “News” tab you will see a dropdown arrow where you can select which version of Minecraft you want to play!

Start, Stop and Restart Server

The server can be started, stopped and restarted two different ways. You can use the provided scripts in the Minecraft folder or you can use systemctl. Here are the commands:

cd ~/minecraft
./start.sh
./stop.sh
./restart.sh

-OR-

sudo systemctl start minecraft
sudo systemctl stop minecraft
sudo systemctl restart minecraft

Automatic Backups

The server backs up each time it starts. This helps you recover easily if something goes wrong. This system works best if you configured the server to restart daily since it means you will have a backup every day.

To access these backups type:

cd ~/minecraft/backups
ls

When a backup is made the filename will be the date and time the backup was taken. If you need to restore a backup it’s very easy. Substitute the timestamp in my example to the backup you want to roll back to. Type:

cd ~/minecraft
./stop.sh
rm -rf world world_nether world_the_end
tar -xf backups/2019.02.15.22.06.30.tar.gz
./start.sh

Your world has now been restored! It’s a good idea to download these backups off the Pi periodically just in case the Pi’s storage fails.

Scheduled Daily Reboots

The daily reboots are scheduled using cron. It’s very easy to customize the time your server restarts.

To change the time that the server restarts type: crontab -e

This will open a window that will ask you to select a text editor (I find nano to be the easiest) and will show the cronjobs scheduled on the Pi. The Minecraft one will look like the following:

0 4 * * * /home/ubuntu/minecraft/restart.sh
cron options

There are 5 fields here. The default restart time is set to reboot at 0 minutes of the 4th hour of the day (4 AM). The other 3 fields are left as * to represent every day of every month. Make any desired changes here and press Ctrl+X to exit nano and update the cronjob.

To remove the daily reboot simply delete the line and save.

Installing Mods / Plugins

The server supports plugins that are compatible with Bukkit / Spigot / Paper. A popular place that you can get plugins is at dev.bukkit.org where there are thousands of them!

To install a plugin you simply download the .jar to the minecraft/plugins folder and restart the server. For example, WorldGuard is a very popular plugin that lets you add protection to different areas of your server.

To install this plugin on our Minecraft server we would use the following commands:

cd ~/minecraft/plugins
curl -H "Accept-Encoding: identity" -H "Accept-Language: en" -L -A "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.12.212 Safari/537.36" -o worldguard.jar https://dev.bukkit.org/projects/worldguard/files/latest
sudo systemctl restart minecraft

The reason the middle line is so long is that “robots” (roughly anything that isn’t a web browser being used by a user in this context) including scripts and utilities are blocked by the Bukkit server. The extra parameters we’re including in this line will add the location (-L) flag as well as a user agent and an identity / language header which will allow us to fetch the files without getting a 403 forbidden error.

Make sure to change “-o worldguard.jar” (second to last parameter) and the URL (very last parameter) to match the project you want to download.

The server will restart and the plugin will be installed. It’s that simple! To use the plugin refer to the documentation on the plugin download page to find out which commands you use to configure/interact with it.

Warning: be advised that plugins are the #1 issue for performance degradation on Minecraft servers. This isn’t because all plugins are bad. Some plugins are coded very inefficiently or perform features that require a lot of hooks in the code.

You should be careful about what plugins you install on the server and if you start having bad performance disable your plugins one by one until you find the culprit!

Reconfigure / Update Scripts

The scripts can always be reconfigured and updated by downloading the latest SetupMinecraft.sh and running the installer again. It will update all of the scripts in the Minecraft directory and reinstall the startup service for you.

Running SetupMinecraft.sh again will also give you a chance to reconfigure options such as the memory dedicated to the server, daily reboots, starting the server on boot, etc.

This will not overwrite your world or any other data so it is safe to run!

Port Forwarding

If everyone on your server is on the same LAN or WiFi network as you then you don’t need to do this. If you want people to connect from outside your local network then you need to set up port forwarding on your router.

The process for this is different for every router so the best thing to do is just look at your router and find the model # and put that in google with port forwarding for easy instructions on how to do it for your specific router.

You want to forward port 25565. The type of connection is TCP if your router asks. Once you do this people will be able to connect to your Minecraft server through your public IP address. This is different than your local IP which is usually a 192.x.x.x or 10.x.x.x. If you don’t know what that is just go to google and type “what’s my ip” and Google will kindly tell you!

Wired vs. Wireless

Going with an ethernet (wired) connection is going to be faster and more reliable. There’s so much wireless traffic and other interference in the air that running your server on WiFi is not recommended.

Even if it is working great 99% of the time it can ruin your experience very quickly if the WiFi drops for a couple of seconds and you get blown up by a creeper!

All that being said, the server works fine on wireless. The script will work fine as is with a wireless connection.

Upgrading

PLEASE BACK UP YOUR SERVER FIRST! The server makes automated backups by default for you in the backups folder but I recommend you back up the entire server folder yourself (basically the entire minecraft folder) any time you attempt to upgrade or downgrade. If you need to roll back to older versions it won’t work without a backup from that version or older!

The easiest way to upgrade an installation is to download the latest SetupMinecraft.sh and run it. This will automatically upgrade you to the latest version.

Upgrading and downgrading to versions that aren’t the default the script chooses is pretty simple. Simply change the Version line at the top in the SetupMinecraft.sh script:

#!/bin/bash
# Minecraft Server Installation Script - James A. Chambers - https://jamesachambers.com
# More information at https://jamesachambers.com/raspberry-pi-minecraft-server-script-with-startup-service/
# GitHub Repository: https://github.com/TheRemote/RaspberryPiMinecraft

# Minecraft server version
Version="1.16.1"

Edit this file in your favorite text editor (you can use nano or vi on the Pi like nano SetupMinecraft.sh) and change the Minecraft version to what you want.

Downgrading

PLEASE RESTORE USING A BACK UP FROM THE VERSION YOU ARE DOWNGRADING TO

If you are having problems on a newer version of Minecraft and want to downgrade you can do so using a complete backup of your server before you ran it on a newer version.

The reason you can’t take server data that has been touched by a version such as 1.17 and go back to 1.16 is that the new version adds all sorts of new data types/structures for the new content into your server data files. If you try to roll back the old versions of the Minecraft server will not understand these data types since they didn’t exist in that version and will crash.

As long as you use a backup for your server files from that version (or older) it’s as simple as changing the version in SetupMinecraft.sh just like I show in the “Upgrading” section.

You can upgrade any old version of Minecraft to any version, but again make sure you have a backup first as it is a one way street and you will need that backup if you want to roll back!

Troubleshooting Note – Oracle Virtual Machines

A very common problem people have with the Oracle Virtual Machine tutorials out there that typically show you how to use a free VM is that the VM is much more difficult to configure than just about any other product / offering out there.

It is because there are several steps you need to take to open the ports on the Oracle VM. You need to both:

  • Set the ingress ports (TCP/UDP) in the Virtual Cloud Network (VCN) security list
  • *and* set the ingress ports in a Network Security Group assigned to your instance

Both of these settings are typically required before you will be able to connect to your VM instance. This is purely configuration related and has nothing to do with the script or the Minecraft server itself.

I do not recommend this platform due to the configuration difficulty but the people who have gone through the pain of configuring an Oracle VM have had good experiences with it after that point. Just keep in mind it’s going to be a rough ride through the configuration for most people.

Troubleshooting Note – Hyper-V

There is a weird bug in Hyper-V that breaks UDP connections on the Minecraft server. The fix for this is that you have to use a Generation 1 VM with the Legacy LAN network driver.

Version History

To view the version history check out the GitHub README here:

Update History – RaspberryPiMinecraft – Official GitHub Page

Other Resources

If you’re trying to set up SSD / USB storage booting check out my Raspberry Pi USB booting setup guide

For benchmarks and recommendations on the fastest storage drives/adapters for the Raspberry Pi check out my 2021 Storage Roundup

If you’re having firmware issues and need to update/restore your firmware check out my Raspberry Pi firmware guide here

Subscribe
Notify of
guest

1.1K Comments
Inline Feedbacks
View all comments
CardinalFang36
CardinalFang36
2 years ago

James,

My server has been running fine for several days but when I went to use it this morning, it was not running. When I investigated, there seems to be an error with sudo and “pam_unix”. I don’t think this is related to your script (other than the 4am reboot) but was hoping you might know what is happening here.

Thanks

—-

Mar 23 11:44:55 paynecraft systemd[1]: Starting Minecraft Server Service...
Mar 23 11:44:55 paynecraft bash[948]: sudo: a terminal is required to read the password; either use the -S option to read from standard input or confi>
Mar 23 11:44:55 paynecraft bash[948]: sudo: a password is required
Mar 23 11:44:55 paynecraft sudo[948]: pam_unix(sudo:auth): conversation failed
Mar 23 11:44:55 paynecraft sudo[948]: pam_unix(sudo:auth): auth could not identify password for [mcadmin]
Mar 23 11:44:55 paynecraft bash[956]: sudo: a terminal is required to read the password; either use the -S option to read from standard input or confi>
Mar 23 11:44:55 paynecraft sudo[956]: pam_unix(sudo:auth): conversation failed
Mar 23 11:44:55 paynecraft sudo[956]: pam_unix(sudo:auth): auth could not identify password for [mcadmin]
Mar 23 11:44:55 paynecraft bash[956]: sudo: a password is required
Mar 23 11:44:55 paynecraft bash[957]: sudo: a terminal is required to read the password; either use the -S option to read from standard input or confi>
Mar 23 11:44:55 paynecraft bash[957]: sudo: a password is required
Mar 23 11:44:55 paynecraft sudo[957]: pam_unix(sudo:auth): conversation failed
Mar 23 11:44:55 paynecraft sudo[957]: pam_unix(sudo:auth): auth could not identify password for [mcadmin]
Mar 23 11:44:55 paynecraft bash[946]: Backing up server (to cd minecraft/backups folder)

CardinalFang36
CardinalFang36
2 years ago

This is my sudoers file:

cat /etc/sudoers.d/minecraft
mcadmin ALL=(ALL) NOPASSWD: /bin/bash /home/mcadmin/minecraft/fixpermissions.sh, /bin/systemctl start minecraft, /bin/bash /home/mcadmin/minecraft/start.sh, /sbin/reboot

I reran SetupMinecraft.sh (seemed fine except this: OpenJDK installation failed. Java version is still reporting as less or greater than OpenJDK 16!)

after, my sudoers looks like:

cat /etc/sudoers.d/minecraft
mcadmin ALL=(ALL) NOPASSWD: /bin/bash /home/mcadmin/minecraft/fixpermissions.sh, /bin/systemctl start minecraft, /bin/bash /home/mcadmin/minecraft/start.sh, /sbin/reboot

Looks to be the same,

CardinalFang36
CardinalFang36
2 years ago

It does appear that a new paperclip.jar appeared last night

CardinalFang36
CardinalFang36
2 years ago

I applied the fix from StackOverflow

Now see this:

Mar 23 23:27:14 paynecraft sudo[5588]: mcadmin : PWD=/home/mcadmin/minecraft ; USER=root ; COMMAND=/usr/bin/sh -c echo 1 > /proc/sys/vm/drop_caches
Mar 23 23:27:14 paynecraft sudo[5588]: pam_unix(sudo:session): session opened for user root(uid=0) by (uid=1001)
Mar 23 23:27:15 paynecraft sudo[5588]: pam_unix(sudo:session): session closed for user root
Mar 23 23:27:15 paynecraft sudo[5597]: mcadmin : PWD=/home/mcadmin/minecraft ; USER=root ; COMMAND=/usr/bin/chown -Rv mcadmin /home/mcadmin/minecraft
Mar 23 23:27:15 paynecraft sudo[5597]: pam_unix(sudo:session): session opened for user root(uid=0) by (uid=1001)
Mar 23 23:27:16 paynecraft sudo[5597]: pam_unix(sudo:session): session closed for user root
Mar 23 23:27:16 paynecraft sudo[5599]: mcadmin : PWD=/home/mcadmin/minecraft ; USER=root ; COMMAND=/usr/bin/chmod -Rv 755 /home/mcadmin/minecraft/fix>
Mar 23 23:27:16 paynecraft sudo[5599]: pam_unix(sudo:session): session opened for user root(uid=0) by (uid=1001)
Mar 23 23:27:16 paynecraft sudo[5599]: pam_unix(sudo:session): session closed for user root
Mar 23 23:27:16 paynecraft bash[5586]: Backing up server (to cd minecraft/backups folder)

But the server still will not start. When I run “screen -r” I see Bukkit starting for a second and then the screen exits.

I guess the next step is rebuild and restore.

CardinalFang36
CardinalFang36
2 years ago

When I try to run manually, I am now getting:

Starting org.bukkit.craftbukkit.Main
Unsupported Java detected (62.0). Only up to Java 17 is supported.

FYI: Running on Raspberry OS
Linux paynecraft 5.10.103-v8+ #1530 SMP PREEMPT Tue Mar 8 13:06:35 GMT 2022 aarch64 GNU/Linux

CardinalFang36
CardinalFang36
2 years ago

James,

My “snap” syntax appears to be different than Markus’:

snap list openjdk --all
sudo snap revert openjdk --revision=818

But after applying that, my server is back up and running.

Who would have guessed that a guy who sells QA software for a living could actually help debug an issue. Thanks for your help…and your wonderful script.

Tom Cardinal Fang

David Artiss
David Artiss
2 years ago

I’m having the same issue. Pretty newbie question (which I am), but what’s the easiest way to perform the update of SetupMinecraft, when you have an existing installation?

David Artiss
David Artiss
2 years ago

Thanks James. In that case, I’m not sure what I’ve done. Should SetupMinecraft.sh still be present from the original install or do I need to re-download it? I only ask, as I can’t see it installed currently.

David Artiss
David Artiss
2 years ago

You meant this, right? 😉

curl https://raw.githubusercontent.com/TheRemote/RaspberryPiMinecraft/master/SetupMinecraft.sh | bash

Thanks for the help here – that’s worked. I’m such a noob with all this, I keep considering giving up but, you know, there’s only one way to learn!

Funkyl
Funkyl
1 year ago
Reply to  CardinalFang36

I’ve been struggling with this error too – server works fine, but those log messages are annoying, particularly as I’m also adding a notification on minecraft join/leave via a comobination of tail (the log file) and ssmtp – so given the mailbad statement means I get emails telling me about these failures. #

The fixes noted in the original thread (editing PAM modules) looked a bit dangerous to me (basically making sudo passwordless throughout) as highlighted in the linked StackOverflow thread.
Looking at the code I wonder if it is an issue with fixpermissions.sh and some of the calls? Two potential areas to look at (and apologies for formatting – first post here so this will be garbled, no idea how to quote etc):

1. in fixPermissions.sh there is this segment when testing the options for flags (starts line 20)…
——————
while getopts ":a:" opt; do
case $opt in
t)
case $OPTARG in
case $OPTARG in
''|*[!0-9]*)
Automated=1
;;
*)
Automated=1
;;
esac

—————–
That case statement looks a little funny? Shouldn’t it be a) rather than t)? (the case statement goes on to note countdown etc rather than automation). Similarly, we are not after an actual value are we, so we could just have getopts “:a” (i.e. no second colon), and simplify the case statement? The upshot of this is that when fixPermissions,sh is called from start.sh, it is not setting the Automated flag and therefore not using the sudo -n statement further on down. However, even if you make those changes, so still get similar sudo errors requiring passwords, even if sudoers.d/minecraft is all OK

2. The second problem then is looking in sudoers.d/minecraft. That gives the local user passwordless permission to run fixpermissions.sh, start.sh etc. However, the actual sudo commands (e.g. chown in fixpermissions.sh, sh in start.sh) will only inherit that status, if those scripts are called via sudo. The minecraft service definition however (under /etc/systemd/ssytem/minecraft.service) includes this:
———————-
[Service]
User=[user]
WorkingDirectory=/home/[user]/minecraft
Type=forking
ExecStart=/bin/bash /home/charon/minecraft/start.sh

———————-
Note the User= command. The default for systemd on startup is to run as root, however as I understand it, when User is set in the service that is no longer the case. Therefore, that ExecStart will not be called via su, and therefore that elevated status not passed onto calls, so when the script eventually hits the sudo commands, the owning script has not been invoked by sudo and therefore scripts are required. Two solutions, either add chown and sh to sudoers.d (not a good idea possibly), or force a call via sudo in the service i.e. change the ExecStart line to:
————————-
ExecStart=/usr/bin/sudo /bin/bash /home/charon/minecraft/start.sh
————————–

I made all the above changes and rebooted and those errors have now gone away (no idea if it makes any difference at all).

As noted, well beyond my comfort zone with a lot of this, so apologies if foolish errors (and lack of formatting)

Funkyl
Funkyl
1 year ago
Reply to  Funkyl

Except that now checking it I see that the server is not running on reboot – start.sh traps out root calls at the start (sensibly). So above a broken solution (sorry) but hopefully helpful in some way.

FunkyL
FunkyL
1 year ago

Hi…. I had been going round and round in circles re the sudoers.d file… more on that in a mo.

In terms of my environment – this is on an Odroid N2+ running their flavour of Ubuntu Mate (22.04) . I’m doing all this headless via ssh.

In terms of sudoers.d/minecraft, this is what it looks like:

charon ALL=(ALL) NOPASSWD: /bin/bash /home/charon/minecraft/fixpermissions.sh, /bin/systemctl start minecraft, /bin/bash /home/charon/minecraft/start.sh, /sbin/reboot

Been looking at this for a few hours or so on the internet, and a common issue apparently is overwrites in /etc/sudoers, but the @includedir /etc/sudoers.d is at the bottom of that file so can’t be that.

For confirmation, sudo -ll gives the following:
——————————————-
Matching Defaults entries for charon on pluto:
env_reset, mail_badpass, secure_path=/usr/local/sbin\:/usr/local/bin\:/usr/sbin\:/usr/bin\:/sbin\:/bin\:/snap/bin, use_pty

User charon may run the following commands on pluto:

Sudoers entry:
RunAsUsers: ALL
RunAsGroups: ALL
Commands:
ALL

Sudoers entry:
RunAsUsers: ALL
Options: !authenticate
Commands:
/bin/bash /home/charon/minecraft/fixpermissions.sh
/bin/systemctl start minecraft
/bin/bash /home/charon/minecraft/start.sh
/sbin/reboot

———————————–
… so assuming that !authenticate means not authenticate, then sudoers.d looks to have bedded in as intended.

Have tried rerunning the original script a couple of times to reset my tweaks to scripts back to default entries … and no change to those log entries. Just spied your update to fixpermissions.sh on github though so will retry that.

Hope something useful in there.

Re your message above, this is my ignorance I’m afraid. The way I was figuring it was that that the systemctl service is *not* running as root (as User is defined in the service definition), therefore fixpermissions will not be called as root/su and therefore the sudoers.d settings will not be invoked when called and so the embedded “sudo” in that script will want interactive authentication. Similarly to the sudo call in start.sh. Probably some garbled logic in there.

Thanks by the way – great script and very easy to set up. Best by far I found on the internet (and as noted on an N2+ as well). As noted the server is running fine, it is just those sudo calls and log entries, which it appears do not hamper the default functionality too much (noting what you highlight re permissions in the top of the fixpermissions script)

FunkyL
FunkyL
1 year ago

Thanks James – I did upgrade from an older version (20 or 21 can’t remember) to 22 so that may be it, so I’ll try a download and clean reinstall and report back here (wont be tonight)

FunkyL
FunkyL
1 year ago

Just to close this out, I reinstalled from the ground up tonight, moving to an SSD while I did. I used a totally fresh install of 22.04 (using netboot_install ubuntu mate minimal 22.04 from Petitboot), and beyond installing e.g. wifi drivers, ssh servers, xrdp installed this script. Alas the same warnings appear in journalctl, so not sure what is going on. To be honest it is a nice to have, and I’ll live with it. The Docker solution is one option, but I slightly prefer having the server not in a virtual environment as it facliattes integration with other things going on on the machine.

Thanks for all your help and your great sight – looking through all your old posts now and some really valuable stuff in here

One aside… I was following your guide for booting N2+ from SSD (I’m using a USB one), and interesting the boot arguments in Petitboot was already set as you highlight to sda, it seemed to have autodetected it.

Patrick
Patrick
2 years ago

Not sure what happened, my server suddenly rebooted tonight and stopped working afterwards. I attempted to backup the world folders and deleted the minecraft folder in an attempt to start from scratch again after trying the restart script with no luck. When running the setup script now, I keep getting stuck at the openjdk version is less or greater than 16 message.

Checked and can see that openjdk 18 was released today and that is showing as the current version when I run java -version from the command line. Tried several methods to uninstall version 18 and reinstall the openjdk version 16 but all attempts have failed so far.

Open to any other suggestions I could try out here. Awesome blog James, even if I can’t get this to work, you’ve already provided hours of fun for myself and kids with our previous server world. 🙂

Patrick
Patrick
2 years ago

I used the curl https://raw.githubusercontent.com/TheRemote/RaspberryPiMinecraft/master/SetupMinecraft.sh | bash command and ended up with the message:

Correct OpenJDK (16) was not found in apt repositories and needs to be installed via snapd.
Checking for snapd...
Installing OpenJDK....
"snap "core" already installed snap "openjdk" is already installed and snap "openjdk" has no updates available

then the OpenJDK failed in red text

Patrick
Patrick
2 years ago
Reply to  Patrick

sorry there were no quotation marks around the curl address

Patrick
Patrick
2 years ago

That has done the trick James! Thank you for getting back so quickly and for continuing to update this

Jeff
Jeff
2 years ago

Hi James,
Thank you so much for the scripts, I ran a 1.17 server on my Pi for a while with no issues! I just upgraded to 1.18.2 and for some reason, the automatic startup is giving me issues. When the Pi reboots automatically or manually it seems like the start.sh begins (the backup successfully completes) however the server does not actually start. When I run start.sh manually, it begins no problem. Any idea what might be happening? Thanks for your help and useful page!

Jeff
Jeff
2 years ago

Hi Jeff, there’s nothing in the logs folder unless I manually start the server, so I don’t think it’s relevant. Pasted below is the results of checking the status of minecraft service. Thanks again for your help!

● minecraft.service - Minecraft Server Service
Loaded: loaded (/etc/systemd/system/minecraft.service; enabled; vendor preset: enabled)
Active: failed (Result: exit-code) since Thu 2022-03-17 01:35:46 CDT; 6s ago
Process: 903 ExecStart=/bin/bash /home/pi/minecraft/start.sh (code=exited, status=0/SUCCESS)
Process: 961 ExecStop=/bin/bash /home/pi/minecraft/stop.sh (code=exited, status=1/FAILURE)

Mar 17 01:35:43 raspberrypi bash[903]: ./world/region/r.5.2.mca
Mar 17 01:35:44 raspberrypi bash[903]: ./world/region/r.3.-5.mca
Mar 17 01:35:44 raspberrypi bash[903]: ./world/session.lock
Mar 17 01:35:44 raspberrypi bash[903]: Starting Minecraft server. To view window type screen -r minecraft.
Mar 17 01:35:44 raspberrypi bash[903]: To minimize the window and let the server run in the background, press Ctrl+A then Ctrl+D
Mar 17 01:35:44 raspberrypi systemd[1]: Started Minecraft Server Service.
Mar 17 01:35:46 raspberrypi bash[961]: Unable to set path variable. You likely need an updated version of SetupMinecraft.sh from GitHub!
Mar 17 01:35:46 raspberrypi bash[961]: Server is not currently running!
Mar 17 01:35:46 raspberrypi systemd[1]: minecraft.service: Control process exited, code=exited, status=1/FAILURE
Mar 17 01:35:46 raspberrypi systemd[1]: minecraft.service: Failed with result 'exit-code'.

CardinalFang36
CardinalFang36
2 years ago

James.

Every time I try to “search” the extensive comments on this page, after entering 2-3 characters in the search box, I get a popup that wants me to sign in. Is this the expected behavior? I don’t see any way to create an account.

Ultimately, I was searching to see if you had any experience running “Multiverse” or similar mods on the RasPI. Do you know if they would overwhelm the server if I only have a couple of occasional users on a RPI 4 w/8GB?

Tom

Paul
Paul
2 years ago

Hi James,

I only stumbled across your blog while doing some extra searches on performance in relation to me trying to document my own Pi setup experimentation – so I won’t forget how to, if my nephew asks again :). My experimentation after setting him up with a server on laptop moved onto me using vannila Minecraft, Raspian aarch64 version, MS Java 17.0.2 on a RPi4 2GB @2146Mhz (actively cooling) and using UHS-I sandisk micro-sd.

From finding your blog I am very appreciative of the information in this – and your previous version of this article – about papermc and the pre-generating of the worlds info.

From your excellent info I downloaded the jar for papermc and chunky to pre-generate my map – allowing me to compare paper to vanilla minecraft performance – with my config using draw-distance of 16 and simulation of 10 – my start flags don’t use nogui and I still run the vncserver on the Pi4, but still find my linux OS is still only showing about 250MB-300MB for the OS when running “top” in a terminal and checking the buff/cache memory usage at first boot.

Sadly, I haven’t got a spare sd card or portable ssd, or the option to image my working Pi3 or Pi4’s cards to free one up currently, to try your blogs amazingly cool solution just yet, so I was wondering if you could give any indication of what type of server performance you are seeing on paper’s gui: avg tick time? or what ticks per second is paper on the Pi4 giving you – after an initial 10mins of uptime with one user logged in and when logged out after 10mins?

vannila Minecraft sadly doesn’t track the 1min, 5min, 20min TPS info AFAIK, and doesn’t have the amazing “timings report” detail that I’ve only just discovered indirectly with paper from your blog, but the “/perf start” on my vannila config – after pre-generation and user logged in – now reports ~20.04 TPS and in normal activities even with 10 TNT explosions – but not flying, not teleporting, not using fill. And now my typical avg tick is around the 10-20ms, occasionally stressing at around the 35ms mark, and after logging out returns to 1-2ms, which is what it eventually reaches after the initial 5-10min server start up load – until “htop –tree” in a terminal is no longer showing 4 core utilisation, or my CPU-voltage-throttling script shows temperatures have dropped back to mid-40degs from mid-70degs. Which is a bit of a quandary because the idle and load tick ms numbers I get running paper – even with some small tweaks to paper.yml and bukkit.yml to lower tick frequency of items and using further tweaks to GC flags still seems to indicate vannila performs marginally better than paper – for me -with its lowest idle tick in ms of about 4.5ms (from initial 10-15ms after different GC start flags) – which I assume is wrong, and I’m leaving performance untapped in paper somehow, either not allocating enough memory with the xms/xmx flags using 1450M, or too big a swap file at 512MB or something.

From anecdotal observation, using chunky on paper and moving the map back to vannila seemed to eliminate performance inconsistency on my vannila setup. Watching “htop –tree” early on with default settings for paper’s startup, it seemed to stress the CPUs cores all the time, but at half load and somehow seemed to load the server and world faster than vannila.

Using my CPU monitoring script through startup it also seemed to keep the temperatures lower, which is interesting because on my Pi3, that isn’t actively cooled, vannila MC server isn’t reliable when I tried, because the initial startup load would frequently cause thermal throttling – dropping the core frequencies down to 800Mhz – when allocating 750MB to the server, and would then cause the server to exceed the “max-tick-time=60000” and shutdown automatically. So on passively cooled Pis paper seems more robust and maybe smoother at handling lag all round on any setup compared to vannila, so naturally I want to beat vannila on my RPI4 setup to justify the switch to paper. Any ideas of things to try would be most welcome.

Paul
Paul
2 years ago

Thanks for the great reply. I probably should have elaborated more than “sandisk uhs-I” and fully said it was a SanDisk Extreme v30 U3 A1 32GB card in my Pi4(and 3) in my first post – which I think is fine, going by the raspian benchmark (rpdiag.txt) file I generated today, gave:

Test : SD Card Speed Test
Run 1
prepare-file;0;0;38258;74
seq-write;0;0;37816;73
rand-4k-write;0;0;2951;737
rand-4k-read;11049;2762;0;0
Sequential write speed 37816 KB/sec (target 10000) - PASS
Random write speed 737 IOPS (target 500) - PASS
Random read speed 2762 IOPS (target 1500) - PASS
Test PASS

I took your good advice and installed iostat on my Pi4 and ran: “iostat -d -h 2” throughout the startup and stabilization time of both paper and vanilla on my server setup and after graphing one of them in scalc, the graph looked similar to the server monitoring graph of memory use, massive activity through setup and then stable with virtual nothing other than small megabyte or kilobyte blips. So it doesn’t appear that the I/O is having either config waiting.

I tried some different things like reducing the number of threads for netty-io down to 2 then 1, but saw no real difference to the idle avg tick time in ms – going no lower than 4ms – and watching htop it looks like paper never gets as much utilisation of all cores as vanilla – whether startup or when handling load it never sustains 4 full cores for more than second for me – but never fully settles either, unlike vanilla that will drop to almost nothing – on all 4 cores – when the server is fully stable after 10mins – under no load – when it has a constant tick time between 1.6ms and 2ms and has dropped to a low 40 deg temp, whereas when running paper, the Pi4 never really drops fully back below 45deg and stays there.

My gut feeling is that the vanilla performance number advantage at idle on my setup is a placebo effect that wouldn’t translate into a better experience than paper in actual use. Sadly, AFAIK there isn’t a free way to simulate a 2 to 4 player additional load on a personal server – without real players, which seems like a massive oversight for Majong and now Microsoft for such an important aspect of a game with self serving.

From the adjustments I tried I think the numbers now show paper to be faster, as it seems like the change in avg tick time with an active player versus idle is less (only 12ms per player if it scales linearly) with paper, where as it seems more like 15-20ms per player with vannila in my tests..

I’m now intrigued enough to move some hardware around to try out your setup script on a Micro-SD or a usb ssd with my Pi4, as I’m sure if you’ve had older server versions running on the 512MB, there’s more performance I missing.

If there is any aspect of my vanilla setup with an advantage to paper, I think it could be because I’m using a Java SDK (installed through sdkman) that Microsoft probably use and profile against vannila, but the paper team probably use the oracle openjdk which is maybe a better fit for it. I selected the Microsoft Java 17.0.2 release because it seemed to be smaller in size than openjdk and oracle, etcs efforts and seemed to give better performance numbers for me. Alternatively if the higher CPU utilisation I’m seeing is a cause, I wonder if there is heavy sorting taking place in the minecraft servers, as a sort algorithm with data supplied in a way that provided superior balancing might give better multithreading performance, and as paper’s adaption of vannila could upset such an algorithm I wonder if that is the performance in idle I can’t seem to get back.

To answer your other question, I did previously have situations where I was running out of memory and crashing the server program because I was experimenting with a ramfs – that needs everything manually accounted for. I was using it for combinations of the location for the world data, the java sdk and the jar file and the path using flag“-DbundlerRepoDir=” for the extracted MainClass, with a 4 or 8GB Pi I think all in ramfs would be really good. But I eventually lowered the vm.swappiness value in the “/etc/sysctl.conf” file, and now only keep the jar and extracted class in a ramfs – to eliminate storage IO as a bottleneck – it seems like linux gives back more of the buffer/cache memory (100MB) by swapping itself into the file with a very low swappiness value, rather than Minecraft’s time sensitive data, and seemingly stopped lag-crashing the server program after idles, where I assume it moved some of the server program data out to swap and then couldn’t access it all quick enough after idle to avoid having a tick longer than maximum allowed.

Thanks again, and will hopefully report back when I get a chance to try your setup script.

Paul
Paul
2 years ago

Great reply, James!

That’s the info I was missing from my newbie knowledge of actually playing MC, so not knowing the main virtues of papermc, like its world persistence for ticking crops etc – beyond plug-ins, and performance that I was struggling to prove to myself, numerically – and me just being the IT person getting a laptop server functional for my nephew, with no background in MC serving specifics or awareness of bukkit/spigot/paper then, and then hobby-ing with a RPi4 replacement as a potential solution, or future server for my kids.

Changing the “keep-spawn-loaded” to “false” as you suggested improved the synthetic(& real) performance numbers massively. Producing a significantly lower avg time in ms per tick, and stabilized as low as 0.2ms, 5-10x less time than 1-2ms of my attempts to optimise Vanilla – even with Vanilla not ticking crops.

The server also has a lower avg tick time most of the time, but the range being much bigger tells me I need to either revert the setting and take the inferior but stable numbers, or look again at maybe reducing memory use in the start flags – as you’ve suggested the server can work well with the pi3’s lesser gigabyte too – and look again at the ramfs, for the java sdk, world files, maybe even revert to a tiny 100MB swapfile too, and then alter some other settings in my yml files to get the better performance numbers along with more stable numbers.

Changing the “chunk-tasks-per-tick” down from 1000 to 500 helped a bit, but one of the problems seems to be the Salmon tick-time for me – using more resources than zombies on lag ticks – but being unable to see a setting that matches in my yml files, and my lack of papermc knowledge means I’m not sure how to handle that best, or the occasional Server.Oversleep adding 40ms when “keep-spawn-loaded“ is set to “false”.

I suspect on balance “keep-spawn-loaded” set to “true” is going to be the better option, but I am still very appreciative that you were able to point me in the right direction to validate that paper is vastly more efficient than Vanilla on my setup. With “keep-spawn-loaded“ set to “false” for the time being on my setup running “/perf start” on a papermc server (not needed obviously with timgsV2 being the definitive tool) now works without throwing errors.

I’ve also freed up a card with a new Bulleyes install, so my next task is to try your script out which I assume has custom yml settings you feel work best, yes?

Paul
Paul
2 years ago

Thanks for the in-depth response.

I got your script installed on my other card using my RPI4 2GB using the raspian bulleyes aarch64 os and can see why you’ve had lots of people using your setup successfully over the years. It seems to work really well by default with very little user input, other than needing to pick wisely with the memory allocation.

Even without the other optimisations I use, like the swappiness change and use of the ramfs for staging files/symlinks, etc. It is a day and night comparison to just running Vannila as is on an overclocked RPi4 from the performance I was noting using my testworld from my other card seup.

After lots of timings with different OS tweaks from my other setup and trying with and without a GUI – using your scripts “switch” console setup – and various java garbage collection flags, with different memory -Xmx allocations, numerically the idling wasn’t as low as my other setup and edge cases where lag really hits, it seemed higher – but by default I think your script still uses “keep-spawn-loaded: true” and the range for the loaded area set to 10 chunks IIRC, which made sense, so I was largely seeing better normal server performance with your paper.yml settings, but better idling and peak lag handling with my paper.yml. Using screen gave back more memory, but didn’t improve the performance on TimingsV2, versus using the Raspian desktop remotely with papermc’s GUI through realvncserver, so I can only assume the ssh and screen programs consume more CPU time on the main core – by redirecting – than GPU accelerated GUI with the java awt gui for the paper server do.

Eventually I downloaded diffuse(a Gui diff) and sorting the two files so your flags order matched the ordering of my recently generated paper.yml – and merged in any missing flags from each other that are still used, and use a copy of the variables with the default value behind a # # in the paper.yml file, for any variable changed from normal – except for the long list of soft:hard:, where I just note it at the top of the section once, as their defaults are all the same.

Some of the entries in the file are left as is, but have a copy with “# #” at the start,because these were entries I was changing at some point, but gave inconclusive results.

This is a link to my last timings run without the initial server startup in the timings. The server.properties file uses a “view-distance=16”,and “network-compression-threshold=512” too.

I this is as good as I’ll get other than me getting a RPI400 or 8GB Pi4 with more ramfs options for the world data, and/or maybe using an SSD to gain a little extra performance from the OS itself, hobbling the game features too much.

Aikar Timings Results

And this is the java flags I use, I think 768k being better IMHO than 1MB jvm would override a bigger value with – and better than 512K I tried – because half of the 768K is a better alignment to the CPU caches on the ARM chip IIRC and seems to yield better performance. I also allocate a large 2048MB swapfile, so the OS doesn’t react to the server consuming all the memory at once and can hopefully not crash the RPI4 if the paper server crashes. I also change the vm.swappiness value down to 5, from the default of 60 in the OS

980M seems to be the maximum I could allocated with a large 200MB world, without more than 30MB of swap being used – working on the basis that storage on a RPi4 has a read limit probably around 30MB/s, so 40ticks stall at most for any minor swapping.

java -Xmx980M -Xms980M -XX:+UseG1GC -XX:+ParallelRefProcEnabled -XX:MaxGCPauseMillis=200 -XX:+UnlockExperimentalVMOptions -XX:+DisableExplicitGC -XX:+AlwaysPreTouch -XX:G1NewSizePercent=5 -XX:G1MaxNewSizePercent=5 -XX:G1HeapRegionSize=768K -XX:G1ReservePercent=20 -XX:G1HeapWastePercent=1 -XX:G1MixedGCCountTarget=4 -XX:InitiatingHeapOccupancyPercent=10 -XX:SurvivorRatio=10 -DbundlerRepoDir=/media/pi/ramdrive -DbundlerMainClass=org.bukkit.craftbukkit.Main -jar ~/Minecraft_files/minecraft/paperclip.jar --server-name RP4B --universe /media/pi/ramdrive/

And here is the paper.yml file settings with all your improvements, and one or two adjustments I made

# #max-joins-per-tick: 3
max-joins-per-tick: 1
track-plugin-scoreboards: false
fix-entity-position-desync: true
use-display-name-in-quit-message: false
load-permissions-yml-before-plugins: true
region-file-cache-size: 256
enable-player-collisions: true
save-empty-scoreboard-teams: false
bungee-online-mode: false
incoming-packet-spam-threshold: 300
use-alternative-luck-formula: false
velocity-support:
enabled: false
online-mode: false
secret: ''
console-has-all-permissions: false
player-auto-save-rate: -1
# #player-auto-save-rate: 60000
# #max-player-auto-save-per-tick: -1
max-player-auto-save-per-tick: 1
fix-target-selector-tag-completion: true
lag-compensate-block-breaking: true
send-full-pos-for-hard-colliding-entities: true
time-command-affects-all-worlds: false
use-dimension-type-for-custom-spawners: false
log-player-ip-addresses: true
console:
enable-brigadier-highlighting: true
enable-brigadier-completions: true
suggest-player-names-when-null-tab-completions: true
watchdog:
early-warning-every: 5000
early-warning-delay: 10000
spam-limiter:
tab-spam-increment: 1
tab-spam-limit: 500
recipe-spam-increment: 1
recipe-spam-limit: 20
book-size:
page-max: 2560
total-multiplier: 0.98
loggers:
deobfuscate-stacktraces: true
item-validation:
display-name: 8192
loc-name: 8192
lore-line: 8192
book:
title: 8192
author: 8192
page: 16384
chunk-loading:
global-max-concurrent-loads: 500.0
min-load-radius: 1
# #min-load-radius: 2
# #max-concurrent-sends: 2
max-concurrent-sends: 32
autoconfig-send-distance: true
target-player-chunk-send-rate: 100.0
# #target-player-chunk-send-rate: 6.0
global-max-chunk-send-rate: -1.0
# #global-max-chunk-send-rate: 50.0
# #enable-frustum-priority: false
enable-frustum-priority: true
# #global-max-chunk-load-rate: -1.0
global-max-chunk-load-rate: = -1.0
# #player-max-concurrent-loads: 20.0
player-max-concurrent-loads: 20.0
# #global-max-concurrent-loads: 20.0

async-chunks:
threads: -1
# #threads: -1
unsupported-settings:
allow-permanent-block-break-exploits: false
allow-piston-duplication: false
perform-username-validation: true
allow-headless-pistons: false
allow-permanent-block-break-exploits-readme: This setting controls if players
should be able to break bedrock, end portals and other intended to be permanent
blocks.
allow-piston-duplication-readme: This setting controls if player should be able
to use TNT duplication, but this also allows duplicating carpet, rails and potentially
other items
allow-headless-pistons-readme: This setting controls if players should be able
to create headless pistons.
packet-limiter:
kick-message: '&cSent too many packets'
limits:
all:
interval: 7.0
max-packet-rate: 500.0
PacketPlayInAutoRecipe:
interval: 4.0
max-packet-rate: 5.0
action: DROP
world-settings:
default:
prevent-moving-into-unloaded-chunks: false
disable-teleportation-suffocation-check: false
generator-settings:
flat-bedrock: false
# #chunk-tasks-per-tick: 1000
delay-chunk-unloads-by: 10s
# #delay-chunk-unloads-by: 10s
piglins-guard-chests: true
should-remove-dragon: false
max-auto-save-chunks-per-tick: 8
# #max-auto-save-chunks-per-tick: 24
baby-zombie-movement-modifier: 0.5
optimize-explosions: true
use-vanilla-world-scoreboard-name-coloring: false
game-mechanics:
scan-for-legacy-ender-dragon: true
fix-curing-zombie-villager-discount-exploit: true
disable-pillager-patrols: false
pillager-patrols:
spawn-chance: 0.2
spawn-delay:
per-player: false
ticks: 12000
start:
per-player: false
day: 5
disable-chest-cat-detection: true
nerf-pigmen-from-nether-portals: false
disable-end-credits: false
disable-player-crits: false
disable-sprint-interruption-on-attack: false
shield-blocking-delay: 5
disable-unloaded-chunk-enderpearl-exploit: true
disable-relative-projectile-velocity: false
disable-mob-spawner-spawn-egg-transformation: false
# #prevent-moving-into-unloaded-chunks: false
prevent-moving-into-unloaded-chunks: true
count-all-mobs-for-spawning: false
spawn-limits:
monster: -1
creature: -1
ambient: -1
axolotls: -1
underground_water_creature: -1
water_creature: -1
water_ambient: -1
experience-merge-max-value: -1
allow-using-signs-inside-spawn-protection: false
wandering-trader:
spawn-minute-length: 1200
spawn-day-length: 24000
spawn-chance-failure-increment: 25
spawn-chance-min: 25
spawn-chance-max: 75
door-breaking-difficulty:
zombie:
- HARD
vindicator:
- NORMAL
- HARD
max-growth-height:
cactus: 3
reeds: 3
bamboo:
max: 16
min: 11
despawn-ranges:
# # defaults #soft: 32
# # defaults #hard: 128
monster:
soft: 28
hard: 96
creature:
soft: 28
hard: 96
ambient:
soft: 28
hard: 96
axolotls:
soft: 28
hard: 96
underground_water_creature:
soft: 28
hard: 96
water_creature:
soft: 28
hard: 96
water_ambient:
soft: 28
hard: 64
misc:
soft: 28
hard: 96
ender-dragons-death-always-places-dragon-egg: false
falling-block-height-nerf: 0
tnt-entity-height-nerf: 0
slime-spawn-height:
swamp-biome:
maximum: 70.0
minimum: 50.0
slime-chunk:
maximum: 40.0
frosted-ice:
enabled: true
delay:
min: 20
max: 40
lootables:
auto-replenish: false
restrict-player-reloot: true
reset-seed-on-fill: true
max-refills: -1
refresh-min: 12h
refresh-max: 2d
filter-nbt-data-from-spawn-eggs-and-related: true
max-entity-collisions: 8
# #max-entity-collisions: 8
disable-creeper-lingering-effect: false
duplicate-uuid-resolver: saferegen
duplicate-uuid-saferegen-delete-range: 32
hopper:
cooldown-when-full: true
disable-move-event: false
ignore-occluding-blocks: false
mob-effects:
undead-immune-to-certain-effects: true
spiders-immune-to-poison-effect: true
immune-to-wither-effect:
wither: true
wither-skeleton: true
# #update-pathfinding-on-block-update: true
update-pathfinding-on-block-update: true
phantoms-do-not-spawn-on-creative-players: true
phantoms-only-attack-insomniacs: true
mobs-can-always-pick-up-loot:
zombies: false
skeletons: false
map-item-frame-cursor-update-interval: 10
allow-player-cramming-damage: false
anticheat:
obfuscation:
items:
hide-itemmeta: false
hide-durability: false
monster-spawn-max-light-level: -1
light-queue-size: 20
auto-save-interval: -1
# #auto-save-interval: -1
mob-spawner-tick-rate: 1
# #mob-spawner-tick-rate: 3
zombies-target-turtle-eggs: true
all-chunks-are-slime-chunks: false
container-update-tick-rate: 1
water-over-lava-flow-speed: 5
grass-spread-tick-rate: 1
use-faster-eigencraft-redstone: true
# #use-faster-eigencraft-redstone: false
armor-stands-do-collision-entity-lookups: true
keep-spawn-loaded: true
# #keep-spawn-loaded: false
anti-xray:
enabled: false
engine-mode: 1
max-block-height: 64
update-radius: 2
lava-obscures: false
use-permission: false
hidden-blocks:
- copper_ore
- deepslate_copper_ore
- gold_ore
- deepslate_gold_ore
- iron_ore
- deepslate_iron_ore
- coal_ore
- deepslate_coal_ore
- lapis_ore
- deepslate_lapis_ore
- mossy_cobblestone
- obsidian
- chest
- diamond_ore
- deepslate_diamond_ore
- redstone_ore
- deepslate_redstone_ore
- clay
- emerald_ore
- deepslate_emerald_ore
- ender_chest
replacement-blocks:
- stone
- oak_planks
- deepslate

disable-thunder: false
skeleton-horse-thunder-spawn-chance: 0.01
disable-ice-and-snow: false
# #keep-spawn-loaded-range: 10
keep-spawn-loaded-range: 6
nether-ceiling-void-damage-height: 0
only-players-collide: false
allow-vehicle-collisions: true
allow-non-player-entities-on-scoreboards: false
portal-search-radius: 128
portal-create-radius: 16
portal-search-vanilla-dimension-scaling: true
fix-items-merging-through-walls: false
parrots-are-unaffected-by-player-movement: false
disable-explosion-knockback: false
fix-climbing-bypassing-cramming-rule: false
fixed-chunk-inhabited-time: -1
remove-corrupt-tile-entities: false
prevent-tnt-from-moving-in-water: false
show-sign-click-command-failure-msgs-to-player: false
iron-golems-can-spawn-in-air: false
max-leash-distance: 10.0
# # #generator-settings:
# # #flat-bedrock: false
per-player-mob-spawns: true
map-item-frame-cursor-limit: 128
armor-stands-tick: true
non-player-arrow-despawn-rate: 60
# #non-player-arrow-despawn-rate: -1
creative-arrow-despawn-rate: 60
# #creative-arrow-despawn-rate: -1
spawner-nerfed-mobs-should-jump: false
entities-target-with-follow-range: false
wateranimal-spawn-height:
maximum: default
minimum: default
zombie-villager-infection-chance: -1.0
unsupported-settings:
fix-invulnerable-end-crystal-exploit: true
enable-treasure-maps: true
treasure-maps-return-already-discovered: false
split-overstacked-loot: true
fishing-time-range:
MinimumTicks: 100
MaximumTicks: 600
entity-per-chunk-save-limit:
experience_orb: -1
snowball: -1
ender_pearl: -1
arrow: -1
fireball: -1
small_fireball: -1
alt-item-despawn-rate:
enabled: false
items:
COBBLESTONE: 300
tick-rates:
sensor:
villager:
secondarypoisensor: 40
behavior:
villager:
validatenearbypoi: -1
feature-seeds:
generate-random-seeds-for-all: false

Paul
Paul
2 years ago

Oh. sorry I think my aggressive reduction in Xmx value – to below 1GB and mentioning me taking the card from my RPi3, has made you think it wasn’t the 2GB RPi4 I ‘ve been using when it was.

Between 980MB for the server, another 200MB-ish in the ramfs, 250MB-ish overhead for Java’s JVM, and another 300-350MB for the linux OS buffer/cache and needing to leave a small margin free of another 100MB or so for the buffer/cache to extend you actually get back to the 1900MB available.

As for the lag numbers, I was under the impression from a video I watch on timingsV2 that it is near impossible to eliminate the lag ticks entirely, but the importance was to keep the avg TPS at 20 and have the lag frames with a combination of minimal over-spend – by time taking more than 50ms – and to have a low percentage of them – and spaced out – over the range.

I was surprised you hadn’t interpreted the timings the way I had – as being improved for a RPi4 – and so I ran your excellent script freshly, again with the same world data and workload as I’d done for my own setup and did seem to get better performance, than my previous runs, and then from that, I reconfigured my own setup to use screen -dmS minecraft with the nogui option, and saw better performance in both setups, so I can only assume either something in the overnight update for Raspian aarch64 bulleyes fixed a bug in screen or ramfs, or my laziness to duplicate the world data, rather than share them with aliased symbolic links between setups, could be a discrepancy in an area of the micro-sd card that hampered my first timings comparison.

After doing a new comparison, and looking at the timings, both setups allocating 1240MB seemed very similar, and only on trying both with the view-distance – in the server.properties file – set to 16, did I then notice that the line trends, although very similar actually were resulting in more chunks being stored in memory on my config (10 versus 4, typically0 and when the orange loss of TPS sections happened, the green line didn’t ever drop from its 20 TPS average, whereas on the script setup the TPS loss was showing a dip in the green TPS line around these moments – like logging in, a “/save-all” or respawning from death – and then when I looked at the lag frame over-spends and the % number of laggy frames, that data reflected that observation of the lines, and those numbers are getting a 2 or more fold improvement in my comparison timings – unless I’m reading them wrong.

I whole heartedly agree, it is nimbling at the edges and even if the numbers implied more than a small improvement, again it could all be placebo benefits – or a regression – when tried in actual use with multiple client load.

Either way I’m pretty satisfied any more tinkering by me will be me, going in circles.

I’m very thankful for all your great input and producing your superb script that gave me great insight into how you optimised your paper.yml settings, along with the script clawing back about 250MB of RPi memory by using screen from linux in CLI mode.

I probably will get round to trying with an SSD – although seemed to remember my 2146Mhz overclock gets unstable with HDD and SSD storage last time I tried, so might go the RPi400 route as it has 4GB of ram for a 1GB ramfs allocation, and it is actually available in the UK, unlike the 4GB and 8GB RPi4 out of stock at MSRP. Normally I’d have spares of SSDs laying around for no-budget hobby projects, but a computer for each of nephews, and niece in recent months has wiped me out for now.

CardinalFang36
CardinalFang36
2 years ago

Do you know if v1.17 has the needed fixes to protect against the log4j security flaw? I was under the impression that 1.18 was required. Any thoughts on this?

CardinalFang36
CardinalFang36
2 years ago

James –

Thanks for your quick response….but I remain confused. It is my understanding that your script uses v1.17 of Minecraft yet the only “safe’ version we should be running these days (because of the log4j exploit) is v1.18. Is this correct, or do I not understand the details of Minecraft versioning?

CardinalFang36
CardinalFang36
2 years ago

My confusion was around the fact that this page starts with “Minecraft 1.17 (Caves and Cliffs Update) is here! ” so I thought the latest version your script would support was currently 1.17. I see now that it is using the latest “1.18.2”. I just did a clean install on my Raspberry Pi 4 (8GB) as the prior setup was on Ubuntu and I seem to be having “apt get update” issues with that…so used this as an opportunity to start with a fresh install overall. I was also concerned that if someone had exploited the log4j issue there is no way I would ever know.

I actually had thought that I had been hacked. I had not used the server for a while and found out it was down. When I investigated, I found the server was out of disk space. I panicked but upon investigation found that the daily backups of the server data was the cause of the disk space issue.

Andre
Andre
2 years ago

is there any way to install a snapshot version, for instance the new deep dark snapshot thats not in the launcher yet?

Andre
Andre
2 years ago

I tried using winscp to move the file for the server.jar file into the minecraft folder on the server for the newest deep dark snapshot and ran it like a normal server without your script and it worked

1 38 39 40 41 42 48