OpenSUSE 15.1 → 15.2 upgrade; with nVidia it’s a disaster due to nouveau

Upshot is, the installer has two different options depending on if you are in graphical mode (init 5) versus text mode (init 3). Graphical mode (which was not recommended) at least had the possibility of working.

Back story: at work more than a decade ago, the whole team got new computers, but one of my co-workers preferred his MacBook laptop. After his PC sat unused for a couple years, I got the idea to ask him if he minded me having his dual monitors. He was okay with that. Of course, to drive those two monitors, one needs a dual monitor video card, so I took that too.

Now my machine had two identical video cards and four identical monitors. It was pretty sweet. The nVidia drivers had handled that just fine. Well, until ….

Then some upgrade happened (in 2017), and suddenly the nVidia driver could only light up one of the two video cards. I really liked having four screens, so I went and bought a single nVidia card with four outputs – NVIDIA Quadro P600. Life was good.

However, with this configuration, all the upgrades to OpenSUSE since then are just miserable. This weekend, I tried again. Awful, as usual.

The problem is that the install wants to replace the nVidia (proprietary) driver with the nouveau (open source) driver, but that never works right.

The other, bigger, problem is that if (in text mode) you don’t agree to let nouveau foul over your machine, you don’t get to upgrade at all.

I’ll try to illustrate the steps:

In text only mode: zypper dup, and at the end I was warned that the nouveau driver was going to be used. The prompt says “do you agree? yes/no: “

If you type “no”, the upgrade stops.

If you type “yes”, the upgrade continues and then trashes the graphical mode configuration. It installs the nouveau driver which doesn’t work with a single card and four monitors.

After banging my head against the problem for too long, it gets time to give up, download the ISO, burn a DVD, boot off the DVD, and choose “install” – completely wiping out all sorts of needed stuff. 🙁

But doing that (a fresh install), I get a graphical install. I get to the point where one of the prompts warned that the nouveau driver was going to be used. The prompt says “do you agree?” There are two buttons: “I agree” and “I disagree”. But most importantly, there is a checkbox for “Install using software emulation only”

That checkbox disables nouveau from breaking the system. Well, it disables nouveau completely, which prevents the system from being broken by nouveau. During the install, I saw a log line that nouveau was being locked from zypper updates, and that a blacklist entry was being added for nouveau to prevent start up.

Finally, I had a system that would boot. It wasn’t particularly stable, but at least it could boot and present the graphical login prompt. The graphical session wasn’t stable or working well, but at least it wasn’t booting to a single blinking text cursor in the corner of one monitor.

It turned out it was easiest to ssh in from a different machine, run the zypper command to add the nVidia repository, and install the nVidia proprietary drivers.

One more reboot later, and I’ve got a stable, four monitor, graphical environment once again. Hooray! 😀

One thing a person should always to with Linux: use a separate hard drive for /home

This way, installing a new operating system (whether it is Mint, OpenSUSE, Kubuntu) does not mess with your files. The new install sticks to the Operating System disk, and doesn’t mess with your /home disk.

So, all my VM guests are fine, my Perl scripts are fine, my login environment (KDE) is fine. That’s all good.

What’s bad about replacing the OS because the upgrade trashed the system is that my personal crontab file is not stored under /home.

I didn’t remember to go find and back up that file, so now it’s gone. I’m going to have to re-invent it from memory. All the scripts I write output log files; but, those get written to /var/tmp – which also gets wiped out when a fresh install happens.

Although I had printed the names of all the repositories I use (and put that file on /home) I was in a hurry and didn’t realize that the screen didn’t list the URLs. Whoops.

And of course, since the way out of the broken system was a fresh install, all the Perl modules I’ve installed in the last few years need to be discovered and installed again.

But, I’m running OpenSUSE Leap 15.2 now. Leap 15.1 is planned to go end-of-life next month, so I thought it about time to get to 15.2. That’s done, but man was it painful.

Lightsail + Bitnami has changed the underlying image – I get to learn debian now :-)

So far, it’s been easy. I have a post about How to make Ubuntu have a nice bash shell like OpenSuSE and it barely needs any update.

But it does, a little.

sudo update-alternatives --config editor

In the menu that was presented to me, Option 2: 2 /usr/bin/vim.basic was the right one. There’s nothing there to tell me the difference between vim.basic versus vim.tiny (I wanted whatever vim.fullsuperduperthrowinallthebellsandwhistles is) – but vim.tiny was not it.

touch ~/.bash_aliases
vim ~/.bash_aliases
(insert mode)
alias ll="ls -la"
alias ..="cd .."
(escape)
:wq

and lastly, the step that is the same:

sudo vim /etc/inputrc

Find my way down to where the comments say alternate mappings for “page up” and “page down” to search the history and then hit the x key a few times to delete the characters which comment out the functionality I want.

Log out, and log back in. It’s good. 🙂

Wow Perl PAR::Packer sucks

I presented a problem to my boss, where I need to let about 30 desktop technicians run some code I’ve written. My boss said when he is in that position, he writes it in PowerShell, and uses PS2EXE. This is good idea. I found that in the Perl world, the same idea is in PAR::Packer.

A super simple script, running on my Linux box, takes less than one second to run. Open up an SQLite database, fetch all 20 records, sort them, print them. Simple. Less than one second.

The Windows .exe version takes 19 seconds.

Every. single. run.

There is no way that the on-call technicians who have to run the scripts I’m writing are going to be happy with that. And it would make me feel bad, inflicting that sort of this-is-time-of-my-life-that-I-am-not-getting-back on some poor soul who got a call at two in the morning, to deal with whomever for whatever.

Normally, on Windows, I used WinBatch. Did so for 20 years. But alas, WinBatch was always a for-pay product, and eventually hobbyists wrote AutoHotKey (or was it Auto-It?) (for free) to do everything WinBatch does. Also, the real goal was to take my Perl scripts that use REST to get and put JSON or XML at a web service. WinBatch has lots of old extenders, but rarely any new ones. I don’t know of a REST extender for WinBatch. I don’t know of anything in WinBatch that does what DBI does in the Perl world. The WinBatch answer is to install MS Access (or whatever) and use COM to drive the actual database client. Avoiding installing software is part of the goal here. I need something That Just Works.

And preferably works in a second or two; not twenty.

I’ve got REST modules written in Perl. I’ve gotten far enough in my Perl skills to put standardized code in modules, and then use those modules. But that meant putting modifying the search environment for finding modules. Guess what doesn’t work with PAR::Packer?

Okay, crap, I can move all my modules into the root directory where my scripts are. This is stupid, but I’ll do it.

And then I find that the execution speed of even a simple script is terrible.

Searching for a solution, of course the answer is “You’re doing Perl wrong, if you don’t want to install an entire development environment on every workstation”.

Well, thanks for nothing. Apparently I need to give up Perl and start learning PowerShell. PowerShell does rather look like Perl, so maybe it won’t be too terrible of a transition.

Bitnami phpmyadmin

Just a quick note for me to easily find and remember how to access PHP My Admin on a Bitnami WordPress instance

From the command line on my local machine:

ssh -4 -N -L 8888:www.gerisch.org:443 -i $insertpathtopemfilehere nottheadmin@gerisch.org

And then in a browser:

https://www.gerisch.org:8888/phpmyadmin

Lastly, remember that the login name to phpmyadmin is root (not the Bitnami application password, or any other user name).

Because public Internet access to PHP My Admin would be a Very Bad Idea, the Bitnami WordPress image is configured such that PHP My Admin refuses to run, if the requests don’t come through www.gerisch.org

This is a good idea.

But what that also means is that I need something listening on my www.gerisch.org address, that can forward the network traffic to the remote web server.

ssh -4 says use IP v4 addresses only (suppresses IP v6 errors if your machine doesn’t have that).

ssh -N says do not execute remote commands (all we’re going to be doing here is port forwarding).

ssh -L says local to remote port forwarding will be done.

8888:www.gerisch.org:443 says the local port to listen on is port 8888, the local address to listen on is the home address of www.gerisch.org, and when listening on the “server” www.gerisch.org, know that it will be listening for port 443 traffic (https instead of http). Another way of thinking about this is that your web browser that is throwing HTTP GETs and PUTs will be throwing them at port 8888, since that is the port the service is listening on. But when the traffic is thrown across the Internet, ssh is going to throw the traffic to www.gerisch.org port 443. Yet, www.gerisch.org:443 is really just a front for gerisch.org:443

ssh -i says to use a public/private key pair for logging in (instead of a password). $insertpathtopemfilehere is the variable that holds the path to the .pem file.

ssh nottheadmin@gerisch.org is the actual remote login name and server name.

More power sleep Linux stuff – or how to set permissions to make a keystroke out of it

This command does successfully put the computer to sleep (and thus the screens eventually go dark and no longer light up the room like stadium lighting):

echo freeze > /sys/power/state

But mere mortals don’t have permission to do that.

I added a script in /etc/init.d which does a chmod 666 /sys/power/state on startup (see the previous post about editing /etc/init.d/after.local)

Credit where credit is due: a gentleman named Aaron Ball posted this at his web site oper.io – clever logo, too, to combine the power switch icon as “.io” – but I digress.

Then another tiny script that simply does the echo command for me:

#!/bin/sh
/usr/bin/echo freeze > /sys/power/state

I had started to go down the road of a sudoers file entry, which would give anyone permission to run this script; but the problem isn’t who runs the command. The problem is that the target of the echo command, /sys/power/state, isn’t going to allow writing by a script (even if run by sudo).

Last step was to add a keystroke to my KDE shortcuts. System Settings –> Custom Shortcuts –> Edit –> New –> Global Shortcuts

Name the action, assign the keystrokes to invoke it, and make the action the tiny script above. Works like a charm. 🙂

AMD Ryzen 1700 and power sleep failure

I had bought all the parts for a new system at the end of 2017, and was mostly happy with it. The motherboard was an AS Rock Taichi and the CPU was an AMD Ryzen 1700. I bought the highest MHz AMD Ryzen I could get except I avoided the 220 Watts TDP; power draw on this chip is about 65 Watts TDP.

Certainly, I was thrilled with system performance, and very reasonable price. But sleep states were a problem. The system would go so deep into sleep, it would never wake up. I would have to press and hold the power switch to get it back: not good. Once in a while, the box would freeze hard too; usually while scrolling a Facebook page. So I had this sense of unease that I’d made a mistake buying the AS Rock Taichi X370 and trying to run Linux on it.

This last birthday, I bought myself a replacement motherboard: an MSI X470 Gaming Plus. I spent my birthday pulling out the Taichi motherboard and putting in the 470GP.

And my ACPI sleep problems did not go away. Rats!

I’ve taken some vacation time, and looking through the log files, I did find an error message that lead me to some vital information. The AMD Ryzen 1700 has an ACPI sleep state – C6 – which Linux doesn’t play nice with. A patch was offered to the Linux maintainers, but not accepted. I don’t know why, and I’m not sure it matters, either.

But what someone did, is make a Python script that pokes and prods the correct bits in the Ryzen 1700 to have it declare that ACPI sleep state C6 is not available / should not be used.

I haven’t had a sleep state problem with this rig since. 😀

First, I needed this: Github ZenStates. I saved this script as /home/myhomelocation/zenstates.py

Then I needed two bash scripts to run it after system startup:

/etc/init.d/after.local

which contains (and is executable):

#!/bin/sh
/etc/init.d/set_c6_acpi_state_disabled.sh

/etc/init.d/set_c6_acpi_state_disabled.sh

which contains (and is executable):

#!/bin/sh
# ScriptName=set_c6_acpi_state_disabled
/usr/bin/python /home/myhomelocation/zenstates.py --c6-disable

In theory, this could be a single script: after.local could be the script to run the Python script zenstates.py. But what if I find I want more than one script to run after system startup? This way, I just add another line to after.local

This week I talked with my brother, who found a relevant piece of information (while researching something else). Apparently AMD will give me a new CPU that doesn’t have this problem, as a warranty repair. So I guess this is AMD being honorable enough to admit they made a mistake here; that is nice. The caveat is, they cannot trust people to not fry their CPU and use this as an excuse to get a replacement under warranty. So the drill becomes: get an RMA from AMD, remove the Ryzen 1700, ship it (at my cost) to them, they test the CPU to make sure it’s not fried (is otherwise good except for the C6 power state problem), and then they ship a replacement. Total turnaround time is probably one month.

Do I want this, my main system, to be down for a month until the AMD CPU RMA SOP EOP FTW? The warranty on the CPU is three years, and I bought it two and a quarter ago.

I think I’m good, with just a software patch. I’m just happy that r4m0n found and supplied a patch.

Thank you r4m0n. 🙂

New OpenSuSE installation – Facebook videos / GIFs don't play

This is just a reminder to myself that when I install fresh OpenSuSE, that when Facebook videos don’t play (but Youtube does), the solution is to go into software management, and to add libxmp4 and MP4Tools. I think that was it. It was important to allow vendor change, and I had to do a lot of acknowledgments for that.

I see that I changed:

  • libxmp4
  • libwx lots of stuff
  • bento4
  • MP4Tools
  • ffmpeg-4

Previously, I had added the Adobe Flash stuff, and that had fixed some of the trouble, but not all of it.

New motherboard

For my birthday, I bought myself a new motherboard. The previous motherboard was speedy; but, not stable. I pulled out an ASRock X370 Taichi and put in an MSI X470 Gaming Plus.

I kept everything else the same: RAM, video card, storage. So far, the MSI motherboard is performing admirably.

Three little snags I ran into:

  • Backups were a pain.
  • Sound card appeared to not work (but probably did).
  • Btrfs is not reconfiguration friendly.

I never did get Clonezilla to work as a backup. I’d bought an external USB hard drive from Costco last year I think. No matter how many times I tried to put a partition on it, it would err out. I think this was because the drive had an MBR (Master Boot Record) config on it instead of GPT (GUID Partition Table). Ultimately, I booted off of a GParted live DVD, and wiped the external USB that way. Then created an ext4 partition for the whole 5 terabytes. From there, rebooted back into OpenSuSE and used rsync. Specifically:

su -
mount /dev/sdc1 /mnt
rsync -aAXv /home /mnt

That took a while. But after I got a backup of my home directory, I was free to start taking apart hardware. 🙂

But yeah, I started around 9:00 AM, and only got the good backup going by 11:30 AM. Cryptic error messages are cryptic.

The Taichi motherboard removal actually went reasonably easy.

What did delay me a little bit was that when I first installed the Noctua NF-S12A PWM system fan, I installed it 90° off; the cable from the fan was about a finger’s width too far away from the motherboard connector. Although it was super easy to remove the Noctua – it has rubber posts and grommets instead of screws (which make it super quiet) – putting it back in to the case was slightly difficult. During the initial build, the fan went in first, so using the needle nose pliers to pull on the stretchy polymer posts was easy. But this time, the power supply and motherboard are already in there, and I don’t really want to have to pull all that out for one corner of the fan mounting. Eventually I got it, but it wasn’t easy.

Boot the machine up, and things are looking pretty good. But I have this fear that sound and Linux are enemies, so I go in to YaST and test the sound. The sound tests fail. Following instructions though, SDB:Audio troubleshooting specifically this test:

speaker-test -c2 -l5 -twav

did produce sound! So sound is working after all. It’s just something in YaST the fails to to produce the test sound. Apparently.

All I really know is that I got to the point where I disabled the second sound card (it’s built into the video card), rebooted, and decided to just try Youtube. Youtube worked. I had sound and everything. I’ll call that a win.

HOWEVER, now it’s time to bring in my files for my home directory, from my backup. And I had forgotten to do some manual partition work during the initial install. I had wanted to wipe both /dev/sda and /dev/sdb so that during the initial install, hardware detection would find what is in the MSI X470, with no previous crud from the Taichi motherboard be hanging around.

But I had not bothered to manually change the partitioner to make /dev/sdb the /home directory. I figured I could do that later. I figured wrong.

Under previous systems, it was pretty easy to delete /home on /dev/sda3 and then configure Linux to mount /home on /dev/sdb1 instead.

Btrfs was having none of that. And if I thought the gparted errors about the external USB partitions were cryptic – this took obfuscation a whole new level.

The good news is that I’d already done all the copies to /dev/sdb1 (from the external USB backup on /dev/sdc1 ), so that work wasn’t wasted.

And indeed, it was easier to just wipe /dev/sda and install all over again. This time, during partitioning, I specified the existing /dev/sdb1 to be mounted as /home and Btrfs left it’s grubby mitts off my home directory disk.

Finished the reinstall, deleted the second audio, and et voila – my machine seems almost exactly like it was this morning when I woke up. I almost can’t tell I did a whole motherboard swap out underneath; except so far no spontaneous reboots. 🙂

mech-dump (part of Perl WWW::Mechanize) is incredibly stupid about it's input file name

If the file name it is dumping does not end in:

.html

the mech-dump will spit out an error that the file content is not text/html it is text/plain. And of course, it immediately quits without doing anything helpful.

And then you go and look inside the file, and this is right at the top:

content="text/html"

You ask yourself What the Hell?

It’s a terrible error message; that’s the hell of it. The error message should say “Input file name does not terminate with the string .html”

I use Linux a lot, and in Linux, files do not have to have file extensions in their names. Over in the Windows side, it is expected that a file name has an extension. Windows uses that file name extension to figure out which program should be associated to the file type. But in Linux, the program association data is written inside the file itself.

This has two effects. First, files in Linux don’t need file extensions in their name. Second, you can name a file in Linux to not have the file extension, and the file works anyway.

So, if I’m writing a Perl script on Linux and I want to dump out something I’ve just pulled down from a web server, using WWW::Mechanize, I might be inclined to name the file where I’m dumping this web form to www_mechanize_web_form_dump

And this would be a mistake, because when I later run

mech-dump www_mechanize_web_form_dump

I’m going to get spit at with the message that the file does not contain HTML, it contains only plain text.

It would have saved me a bunch of time, if the error message would have been “mech-dump does not interpret files with names that do not end in .html”

That might seem kind of a silly input file name constraint, but at least the error message wouldn’t be misleading.

Bitnami WordPress Multisite – DNS spoofing

In an earlier post, I said I hope you have pointed your domain name at your static IP address. Well, what if you don’t want to?

The point being that the DNS entry for the domain name currently points to the production WordPress site, and really, I would like to set up this multisite WordPress installation without having to change the public DNS entry.

Also, setting up this, my personal blog, I was using No-IP DNS services. I could update the DNS entry for gerisch.org, and the DNS replicated out almost instantly. It was great. But the other web site I’m working on (the one that got me into WordPress at all), is using Network Solutions for their DNS. They take their good sweet time replicating DNS entries out to the world. I don’t really want to post an update to DNS, wait, dink around with the new site while the production site is down, decide to revert to production, post an update to DNS, wait again while Network Solutions gets around to pointing everyone back to the production web site.

It would just be better if the new web server machine never got away from it’s own self when doing lookups for the domain name it will eventually be.

So I can start the WordPress install from the IP address of the server out on the public Internet. However, WordPress during it’s install, is going to do a DNS lookup, and try to invoke code on the server where the DNS really does resolve. Which isn’t where I am. So I’m going to try to install a fake DNS server on the new server, and have it redirect all calls to the old domain to the new server.

Step the first: install dnsmasq

sudo apt-get install dnsmasq

Next, set up listening on the local host address:

sudo vim /etc/dnsmasq.conf

Find your way to the line #listen-address= and edit it thus:

listen-address=www.gerisch.org

And save and exit

sudo vim /etc/dhcp/dhclient.conf

Find your way to #prepend domain-name-servers www.gerisch.org; and uncomment this line. Save and exit.

And now it gets weird.

The Bitnami / AWS Lightsail images use something called cloud-init : https://cloudinit.readthedocs.io/en/latest/topics/modules.html

So if you were going to try to edit /etc/hosts or /etc/resolv.conf you get warned to not edit them by hand, because they will be replaced on next boot. But they sure as heck don’t tell you where to implement edits. Just don’t do it here.

Turns out there are template files in /etc/cloud/templates that hold the magic.

cd /etc/cloud/templates
sudo cp hosts.debian.tmpl hosts.debian.tmpl.original
sudo vim hosts.debian.tmpl

Now I’m going add a line below www.gerisch.org localhost which will be the IP address I want this machine to go to whenever it tries to resolve the domain name of the production web site

And indeed, if I use dig from an ssh session in the machine, dig reports back the local machine’s address, not the one out on the public Internet