Where’d the Timer Go?

So. System.Threading.Timer. Right.

I’m really starting to miss the old System.Timers.Timer. Built like a tank. System.Threading.Timer is a bit more finicky, but is the only option in .Net Core.

My fun of the day:

It turns out, when the timer goes out of scope, it will be disposed of. Even if you’d told it to, for example, tick every 3 seconds. Though I probably should have known that. 

This will tick exactly once:

private void foo()
Timer t = new Timer(bar, null, 0, 3000);

Instead, you must do:

Timer t = null;
private void foo()
t = new Timer(bar, null, 0, 3000);

Just so you don’t waste a couple of frustrating hours like I did.

Happy coding!

Getting to the (.Net) Core of It

Migrating a .Net 4.x Console Application to .Net Core

I finally got the server side of Winds of Paradise running in .Net Core! I thought I’d share how it did in, in hopes that it might help you do the same. As cool as Mono is, I’m totally psyched to have all my C# code running on Microsoft’s .Net under Centos Linux!

If you haven’t watched it yet, I highly recommend Microsoft’s .Net Core lesson at the Microsoft Virtual Academy:

1st thing I did was update Visual Studio 2015 Community to Update 3 and install all of the prerequisites. These can be found at: http://getdotnet.azurewebsites.net/target-dotnet-platforms.html

You can also find instructions there on how to install .Net Core onto wherever your code will be hosted.

Once everything is installed (block out a good hour for this), I opened my existing solution in Visual Studio.

To the solution, I then added another project and chose the type: Console Application (.Net Core)


Next, open that project and use the NuGet Manager to install any packages that you are using in your .Net 4.x project. For me, this was npgsql and Newtonsoft.JSON.

Once the new project is created, copy over all of your .cs files from your original project to the new .Net Core version.

Hit build, and start working on replacing any .Net 4.x functionality that is not available in .Net Core.

What I did was make corrections in the .Net Core version and then replicate those changes in the .Net 4.5 version. This way, I could build and run the old version with minor changes to prove the changes worked, rather than changing *everything* and trying to debug the .Net Core version. This worked, since the .Net 4.x encompasses everything .Net Core does.

Once you’ve worked out all of the bugs, copy all of your code over to whatever box your running on .Net Core on (Windows, Linux, MacOS, etc.).
Open a shell, cd in the folder with project.json and run:

dotnet restore
dotnet run

That’s it! .Net will download necessary packages from nuget, compile, and run.

Here’s some of the classes I had to find workarounds for:

System.Net.HttpWebRequest, System.IO.Stream.GetReqestStream:
The .Net Core version of this object only has async methods for GetRequestStream and GetResponse. You’ll have to move to GetRequestStreamAsync and GetResponseAsync, which also means having your methods return Task instead of void
Also, the .Net Core version does not have HttpWebRequest.ContentLength when doing a POST. So far, simply removing it seems to work fine in both  .Net 4.5 and .Net Core.

I’m guessing this could probably be made to work with .Net Core fairly easily, but moving NpgsqlDataAdpater usage to NpgsqlDataReader for better database efficiency has been on my TODO list for quite a while anyway.

I found a great resource for setting up json configuration files at:
A couple notes:
1) I had previously been targeting .Net 4.5. I needed to target 4.5.1 in order to install Microsoft.Extensions.Configuration
2) If you create appsetttings.json in your .Net 4.5 project 1st, make sure to create appsettings.json in your new .Net Core project, DON’T COPY it from from the .Net 4.5.1 one. Creating it new sets it as a “Content File”

This was a tricky one. System.Timers.Timer allows easily add/subtracting events from occurring on the timer with Elapsed += [function].  This allowed me to have a couple of static timers that any other object could add events to.
The only alternative in .Net Core is the System.Threading.Timer. This timer is much less sophisticated. It can only accept one function to run at each tick, and this function cannot be changed. My workaround was to implement a separate timer for each object that needed one. I’m hoping this does not increase resource consumption. Hopefully a better timer alternative will work its way int nuget, I didn’t see anything that looked promising at the moment.

Happy coding!

Lync 2011 Mac Keychain Error

Today Lync 2011 decided it was not going to log in. Each time I tried I got an error about the oc_keycontainer and a request for my password.

I tried just deleting all the oc_keycontainer entries from Keychain Access, but still no luck.

It turns out it’s necessary to also delete the OC_KeyContainer_[username] file from ~/Library/Keychains

Re-launch Lync, and all should be good.

Fixing OpenVPN in pfSense After Static IP Change

I recently moved (yay me) and with the move came a new static IP address.

Unfortunately, changing the IP address in pfSense did not change it in the OpenVPN configuration as well.

If this happens to you, here’s the fix:

Log into pfSense, go to Status->Services and stop the OpenVPN service.

Next, SSH into the pfSense router with something like:

ssh root@[your router]

Once you are in, press 8 to get a shell

Enter the following command:

vi /var/etc/openvpn/server1.conf

Go to the line that starts with “local” followed by your external IP address

Change your current IP address to your new external address, then save and exit vi.

Go back to the pfSense web interface, go to Status->Services and start the OpenVPN service.

You should now be able to connect! (You’ll need to change your client configs as well if they are pointed to your IP rather than a DNS address)

Mysterious Blue Box

I was helping someone set up their brand new (and stunningly beautiful) Dell XPS 15. When, lo and behold, a mysterious blue box appeared every time I moved a Window.

Mysterious Blue BoxI Binged, and Binged, and Binged, but could not come up with what this was.

Finally, as I watched a coworker drag a window, I noticed a program briefly appear as the window as being dragged, then close itself once I stopped.

It turns out the XPS 15 came with a program called “Dell PremierColor” which has an ancillary function of making it “easier” to snap windows.

To disable this, first open the Dell PremierColor app (yes, PremierColor is one word…)

Dell PremierColor 1Once it’s open, click the Advanced button

Dell PremierColor 2On the left click Display Splitter

Dell PremierColor 3Uncheck the box next to “Display Splitter on”

Dell PremierColor 4The change will take effect immediately. Now close Dell PremierColor and the mysterious blue box should be gone!

Dell PremierColor 5-Adam

WordPress Auto Update Soup-to-Nuts

This took a couple days of Binging and hacking, but I finally got WordPress to auto-update on Centos 7 with SSL and without disabling SELinux.

Update 1: I should note, this is for self-hosted WordPress users.

(Anything in brackets [] is up to you to choose)

WordPress 4.4 requires FTP access to the server in order to update its self.

vsFTPd with SSL

To keep things secure, I’ve setup vsftpd with chroots (to prevent ftp accounts from going outside of where they should be) and SSL.

Install vsfptd

sudo yum install vsftpd

Edit the configuration file

sudo nano /etc/vsftpd/vsftpd.conf

The following options should already be in your config file and can just be changed:


The rest should be added to the bottom of the config file.
I’m assuming you already have an SSL cert you are using for your website. You can use this cert for vsftpd as well.

# Keep non-chroot listed users jailed

rsa_cert_file=/etc/pki/tls/certs/[your ssl cert].crt
rsa_private_key_file=/etc/pki/tls/private/[your ssl cert key].key

Now you can enable and start the FTP server

sudo systemctl enable vsftp
sudo systemctl start vsftp

Next, create a user that will be used for FTP.
It’s important to set the home directory with the “-d” option to where your website files are. I’m assuming the default /var/www/html.

sudo adduser -d /var/www/html [ftp-user]

Set a password for the user. Make sure to choose something secure!

sudo passwd [ftp-user]

Add the user to the apache group, so that it will have write access to /var/www/html/*

sudo gpasswd -a [ftp-user] apache

Make sure that apache has read/write to the WordPress files

sudo chown apache:apache /var/www/html/*
sudo chmod -R g+w /var/www/html/*


To the best of my knowledge, these are the SELinux commands necessary for both the vsftpd as well as for Apache to FTP into the server and update itself.

SELinux booleans to enable the functionality we need

setsebool -P ftp_home_dir=on
setsebool -P ftpd_full_access=on
setsebool -P httpd_can_network_connect=on
setsebool -P httpd_can_connect_ftp=on

SELinux needs to be told that Apache has permission to write the files in /var/www/html and its subfolders

sudo chcon -R -v -t httpd_sys_rw_content_t /var/www/html

Let’s test the FTP server to make sure you can connect

First, install the lftp client

sudo yum install lftp

Connect to the FTP server

lftp -d -u [ftp-user] -e 'set ftp:ssl-force true'



and make sure you get a directory listing. If not, you’ll need to use the debug data printed to troubleshoot further (I sure did, I hope you won’t).

Assuming that works, the last step is to set edit wp-config.php with the FTP server settings

sudo nano /var/www/wp-config.php

Under the database settings, add a section:

/*** FTP login settings ***/
define("FTP_HOST", "");
define("FTP_USER", "[ftp-user]");
define("FTP_PASS", "[ftp-user-password]");

It may not be necessary, but I like to restart Apache just to be sure

sudo systemctl restart httpd

Finally, log into WordPress and try to update something simple, like a theme or plugin. It should work!

SELinux ACLs with Apache

A quick reminder to myself (and you if you’ve come across my little site) to change SELinux file ACLs when uploading new files to be served by Apache (httpd) on Centos.

Yesterday I linked to some Radeon drivers in my http://www.shernet.com/windows/ati-radeon-mobility-x1400-on-windows-10/ post.

However, the linked zip file was showing ‘Access Denied’ errors, despite the correct filesystem permissions.

I had forgotten to also mark the file as something httpd should have access to on Centos as far as SELinux was concerned.

Without further ado, it simply took:

sudo chcon -v -t httpd_sys_content_t uploaded_file.ext


ATI Radeon Mobility X1400 on Windows 10

I’m getting an old Dell Inspiron E1505 upgraded to Windows 10.

Most things are going well, but there are definitely some driver difficulties, the 1st of which are the graphics.

This comes via GreenReaper on the Microsoft forums, but I wanted to replicate it here just in case the post goes away: http://answers.microsoft.com/en-us/windows/forum/windows_10-win_upgrade/no-windows-10-driver-for-amd-radeon-x1400/9e0afae5-e571-483d-b0e0-841ae6ae20c1?auth=1

(If you trust me, you can skip this whole part and simply download the  zipped Windows 10 Radeon X1400 Win 10 driver)

First, download the driver from the Microsoft Update catalog:

If the link fails, search http://catalog.update.microsoft.com
For: ATI Technologies Inc. – Display – ATI Mobility Radeon X1400

Open the downloaded cab file, and copy the contents to a new folder.
Create *another* new folder within that folder called: B_72960
Copy all of the files into that folder as well (or it will error)

Reboot into Safe Mode
Click Start->Power
Hold down the Shift key and click Reboot
Click Troubleshoot->Advanced Options->Startup Settings->RebootChoose “Safe Mode” on reboot

When you’ve booted into safe mode, open Windows Explorer

Right click “This PC” and click “Manage”
Click Device Manager
Click the arrow next to “Display Adapters”
Right Click “Basic Display Adapter” (or whatever it says)
Click Update Driver Software
Click Browser my computer for driver software
Choose the folder with the downloaded driver
After the installation, reboot.

Then voi la! Enjoy your accelerated graphics and the beauty of Windows 10! 🙂

Some Fun With NFS and Windows

I have some Linux servers that I’d like to talk to my Windows Server 2012R2 file server.

Since I’d like daemons, rather than users, to be able to communicate with the server, I thought this would be a good candidate for NFS.

Linux Side (1st round)

(I’m using Centos, but the general concept will apply to Fedora, Ubuntu, etc.)

Install the daemons that will access the file server. Most of these will create their own users.

Create any additional users you would like to be able to access the file server. You can always add more later.

To save some complexity (and not assume you pay for Active Directory), I’m not going to have my file server look up Linux IDs via Active Directory. Instead, I’m going to use flat passwd and group files, just like Linux.

Copy (via SSH, USB, copy/paste, whatever) the passwd and group files from /etc/ over to your Windows server.

You can delete all of the entries for users/groups that will not be accessing the share.

Window Side

Copy the the passwd and group files to:

Create users (and groups) on your server with the same user name / group name as you created on your Linux server.

UPDATE: Make sure you set the Windows users to never have their passwords expire if they are service accounts. If they do, the users will lose access to the shares via NFS when the password expires.

The passwd and group files serve as a map between the user/group IDs in Linux and the user/group names in Windows.

Install Server for NFS on the Windows server.

Server Manager->Manage->Add Roles and Features

server-for-nfsNext->Next->etc. until installed.

Browse to the folder on your file server you are looking to share.

Right click on it and choose Properties

Go to the NFS Sharing tab

Click the “Manage NFS Sharing” button


Check the “Share this folder” check box.

The only other change I make here is to uncheck the “Enable unmapped user access” option so that only users in the passwd file we copied over will have access to the server.

Next, click on the Permissions button at the bottom


I like to set “All Machines” to be no access, that way only the servers I specify will be able to mount the share.

Click the “Add…” button.

add-nfs-clientIn the “Add Names:” box, enter the IP address of your Linux server.

Make sure Type of Access is set to the type you are looking for.

I prefer to leave “Allow root access” unchecked for a bit more security.

Press OK, OK, Close

If everything worked, the folder icon should now look like this:


Using the security tab, assign NTFS permission to the folder for the users you would like to be able to read/write to that folder, just as you would if it were an SMB share.

Linux Side (2nd Round)

Install the NFS client and enable (make start on boot) and start the services.

sudo yum -y install nfs-utils

sudo systemctl enable rpcbind
sudo systemctl enable nfs-server
sudo systemctl enable nfs-lock
sudo systemctl enable nfs-idmap

sudo systemctl start rpcbind
sudo systemctl start nfs-server
sudo systemctl start nfs-lock
sudo systemctl start nfs-idmap

Create a folder that will be used as the mount point for the file server, aka: Where do I go to get to the files on the file server.

I was really hoping to find a definitive “this is where to mount nfs shares” article, but some Binging around came up with nothing.

I will therefore advise you create a folder under /mnt, as that feels right to me.

sudo mkdir -p /mnt/[server name]/[share name]

It’s finally time to give the share a test.


sudo mount -t nfs [server name or ip]:/[nfs share name] /mnt/[server name]/[share name]

Make sure you are logged in as a user with permission to that folder and cd into it:

cd /mnt/[server name]/[share name]

You should now be able to create files and folders! (which will of course be visible on the file server as well)

The final step is to have the server automatically mount the share on boot.

sudo nano /etc/fstab

Add a line similar to:

[server dns name or ip]:/[share name]    /mnt/[file server name]/[share]  nfs     defaults        0 0

Give the server a reboot to test automatic mounting

sudo shutdown -r now

When you reboot, the share should be mounted and all is good in the world!

PS: If you are using this for transmission-daemon (which I’m assuming you’re using for legitimate purposes), make sure you edit your settings.json file and set umask=0, otherwise transmission will create folders that it cannot create files in.