Skip to content

My $4K EV Code Signing Adventure: Windows & HSM Chaos

When you download a file on Windows, both the browser and the system check it for viruses and its reputation.

If you want to be trusted, you’ll need to purchase an Extended Validation (EV) Code Signing Certificate—which costs a lot. But simply buying it isn’t enough; there are plenty of complications, and I’ll talk about those and how I ended up spending over $4K!

We’re developing a Flutter app to manage iOS, macOS, and integrate with App Store Connect (aso.dev), and as it turns out, many ASO specialists use only Windows…

We use MacBooks with M1 chips, so building an app for Windows x86 in virtualization is nearly impossible (trust me, I tried).

First, I turned to Microsoft’s startup program, Founders Hub, which easily got me $5K in Azure credits.

I spent two weeks setting up CI/CD. The basics are simple: setting variables and PATH. I was reminded why I don’t like Windows—everything works locally, but in CI/CD, it’s magic…

After building the .exe installer, I realized that downloading and installing it from the site was a huge problem…

Windows Smart Screen

Windows Smart Screen

Google led me to Extended Validation (EV) Code Signing Certificates and Code Signing Certificates. The difference? EV costs 2-3 times more. After digging into the details, I found that EV helps with Windows SmartScreen, while a regular certificate fails about 95% of the time.

EV Code Signing Certificates can’t be saved as a file. They require an HSM or a token, and tokens don’t work over RDP (I tested this), plus my build is in the cloud. So, I found Azure Dedicated HSM, and here’s the cost breakdown:

Pricing for HSM

Pricing for HSM

Certificates for the cloud must support the cloud (or so it seems).

Careful readers will notice the cost is per hour! I didn’t catch that, and I ended up spending over $3K! I don’t know what I would’ve done if this had been personal money and not part of the grant!

Azure bill for the month

Azure bill for the month

I deleted everything I could from Key Vaults and started checking the accounts daily. But even after another day, I realized the money was still leaking out. Finally, I deleted the key blocks from the deleted ones. That was the end of my cloud certificate adventures.

Ordering the Certificate and More Problems

We ordered a certificate from IdenTrust. During the order, we entered different addresses for delivery and payment, and they didn’t match the bank’s billing address. The money was frozen for a week, and support couldn’t help. After the refund, we ordered the certificate again, this time without a physical token, and the payment went through. But we were denied, as the company had existed for less than three years, and the money was frozen for another week.

Finally, we found a certificate on SSL.com for $349 (what a nightmare). They provided decent instructions on how to work with YubiKey, though they required YubiKey FIPS.

In theory, you can sign a .exe on a Mac, but I wasn’t ready for that. And since the grant is only for a year, I’d need a Windows machine eventually. After researching, I bought an HP Pro Mini 400 G9 DM/DOS/i5-12500T/8GB/512GB for 58,644 RSD (about $540), and a YubiKey 5C for $50.

Fun fact: you can only create a bootable Windows flash drive on Windows! (Wasted a day on this).

Projector saved the day while the monitor was being repaired under warranty

Projector saved the day while the monitor was being repaired under warranty

The Google Maps Validation Adventure

To verify the business, you need an address on Google Maps (among other things, but this is the simplest case). It turns out, it’s much easier to add a new business to the map than to update information about an existing one, even if you’re the owner. Our address was listed but hidden, and when we tried to show it, they requested a video confirmation, which no one seems to watch.

Google called us six times (three times we managed to talk), but it didn’t help update the data, even after we sent documents showing the address in our company’s legal papers. Clearly, something is broken in Google’s processes. In the end, we added a new location to the map with the correct address and deleted the old one after passing SSL.com validation.

Signing the App: The Final Challenge

Once we passed all the checks and calls, updated the Google Maps data, and received the certificate for ASO.DEV LLP, I began trying to sign the application.

The main issue? SSL.com really wants to sell you their e-codeSign cloud service (expensive). So, I had to dig around to find instructions on how to run it locally with my own key.

I won’t rehash the instructions here—just check out these links:

Tips

  • Code Signing won’t work over RDP!
  • Don’t send installation files through messengers—use a CDN instead, or the OS may block installation.
  • Verify the Attestation Certificate with SSL.com and attach it to your order. If you get a signature error, wait for the files to update or contact support.

I bought FIPS after running into a signature error. After a few days of agony, an email to support fixed everything (they updated the Verify Attestation Certificate, as I understand). I couldn’t connect a second token for signing due to the lack of a private key, and I didn’t have the energy to experiment further.

Had to take a photo since screenshots were blocked

Had to take a photo since screenshots were blocked

One more important point: the reason we started looking into certificates in the first place was that auto-updating the app on Windows wasn’t working. After signing the certificate, it still didn’t work, but after updating the config from sparkle:edSignature to sparkle:dsaSignature, everything started working.