From 734cd69206352cb6a66cfbe5d14ebbb491f57748 Mon Sep 17 00:00:00 2001 From: Tait Hoyem Date: Mon, 14 Dec 2020 11:23:32 -0700 Subject: [PATCH] Use permalink and update links to posts --- _posts/2020-02-19-rsa2.md | 2 +- _posts/2020-04-02-rsa3.md | 4 ++-- _site/2020/02/19/rsa2/index.html | 2 +- _site/2020/04/02/rsa3/index.html | 2 +- _site/blog/index.html | 2 +- _site/feed.xml | 2 +- 6 files changed, 7 insertions(+), 7 deletions(-) diff --git a/_posts/2020-02-19-rsa2.md b/_posts/2020-02-19-rsa2.md index 5270453..9e9fcd4 100644 --- a/_posts/2020-02-19-rsa2.md +++ b/_posts/2020-02-19-rsa2.md @@ -5,7 +5,7 @@ title: "How Does Encryption Work, in Theory?" --- -There are many kinds of encryption used in our everyday communication. Online and offline, over the internet and in person. In this article, I will explain the basics of how encryption should work in theory. I explain in [this article](/2020/01/26/rsa1.html) why encryption is important, and why *you* should care about it. +There are many kinds of encryption used in our everyday communication. Online and offline, over the internet and in person. In this article, I will explain the basics of how encryption should work in theory. I explain in [this article]({% post_url 2020-01-26-rsa1 %}) why encryption is important, and why *you* should care about it. We will start by looking at in-person, offline encryption. diff --git a/_posts/2020-04-02-rsa3.md b/_posts/2020-04-02-rsa3.md index 4dd28ce..eed7d85 100644 --- a/_posts/2020-04-02-rsa3.md +++ b/_posts/2020-04-02-rsa3.md @@ -3,7 +3,7 @@ title: "How Asymetric Encryption Works" layout: post author: tait --- -In a few previous articles I have explained [why encryption may be important to you](/2020/01/26/rsa1.html) and [how the theory behind encryption works](/2020/02/19/rsa2.html). I did not yet explain the system of asymetric cryptography, however. That is what this article is for. +In a few previous articles I have explained [why encryption may be important to you]({% post_url 2020-01-26-rsa1 %}) and [how the theory behind encryption works]({% post_url 2020-02-19-rsa2 %}). I did not yet explain the system of asymetric cryptography, however. That is what this article is for. Previously, we talked about how *symetric* encryption works. This is by having a shared key that both parties use to simultaniously encrypt, and decrypt the data. (See Ceasar Cipher for example). @@ -142,5 +142,5 @@ In this article we went over some basic points: 2. RSA is considered the standard for extra-seure communication. 3. EC is a newer, faster, more transient encryption method. -To learn how to use RSA keys to encrypt your own communications, check out [this other aritcle I wrote](/2020/04/06/rsa4.html). +To learn how to use RSA keys to encrypt your own communications, check out [this other aritcle I wrote]({% post_url 2020-04-06-rsa4 %}). diff --git a/_site/2020/02/19/rsa2/index.html b/_site/2020/02/19/rsa2/index.html index 8aa77f1..f6ff29d 100644 --- a/_site/2020/02/19/rsa2/index.html +++ b/_site/2020/02/19/rsa2/index.html @@ -1 +1 @@ - How Does Encryption Work, in Theory? | tait.tech

How Does Encryption Work, in Theory?


There are many kinds of encryption used in our everyday communication. Online and offline, over the internet and in person. In this article, I will explain the basics of how encryption should work in theory. I explain in this article why encryption is important, and why you should care about it.

We will start by looking at in-person, offline encryption.

Cryptography We Do Everyday

We encrypt things all the time without even thinking about it. If you spend a significant amount of time with the same group of friends, you will tend to develop common codes that may not make sense to others outside the group. For example: for years, my family called sombody falling from a sitting position “doing a Don”. There is a story of course—We knew a guy named Don who fell from his plastic beach chair in a rather hilarious way; “doing a Don” was born.

These types of minor dialects in speech are cryptographic in their own way. The truth is though, that we use cryptography much more than that!

“Is cryptography any different than talking? We say something other than what we mean, and then expect everyone is able to decipher the true meaning behind the words. Only, I never do…” — Adapted from a scene in The Imitation Game (p. 39-40)

How many times have you hinted, flirted, and innuendoed to try to say “I find you very physically attractive”? Have you told your friend that always stinks to wear more deodorant? Have you ever had someone say the words “I’m fine” when you know for certain that they are indeed not okay?

Words Said Meaning
What can you do? I don’t want to talk about this anymore.
I don’t want to overstay my welcome. I want to go home now.
I don’t like them and don’t know why. They threaten my ego.
Creepy Unattractive and friendly

All of these scenarios are perfect examples of lies encryption! If we have the key to these codes, we can start to understand what people really mean. Hopefully I have convinced you that you use deceit cryptography on a regular basis in your life, so let us consider what a basic encryption method might be:

Grade-School Encryption

Back when I was in middle school I used to pass notes like these:

A message I would have sent in middle school. ROT5: Xfwfm hx hzy
The kind of message I would have sent in middle school. A ROT5 Ceasar cipher.

This is a message encrypted using the Caesar cipher. This encryption technique was used by Julius Caesar during the reign of the Roman Empire to “encrypt messages of military significance.”[1] This is one of the oldest and simplest methods of encryption known to us today.

A diagram of a Ceasar Shift algorithm. A <-> N, B <-> O, et cetera.
A diagram of a ROT13 Ceasar shift algorithm. A <-> N, B <-> O, et cetera.

You can try this out yourself by moving some letters forward in the alphabet. An ‘A’ turns into a ‘B’, ‘B’ into ‘C’, ‘C’ into ‘D’, et cetera. In this case, “Hello!” would become “Ifmmp!” That is just using a shift of one. You can use a shift of seven, for example, and then you would shift letters like so:

  • A -> +7 -> H
  • Q -> +7 -> X
  • T -> +7 -> A

When you reach the end of the alphabet, wrap around to the beginning to find the encrypted letter.

Example of a Caesar Cipher

Let’s setup a little story to illustrate the problems of encryption. We will have three characters:

  • Alice, young lady with feelings for Bob
  • Bob, a young lad with an addiction to pancakes
  • Eve, a wee jealous girl scout who sits between Bob and Alice

Alice really likes Bob and wants to tell Bob her feelings, so she writes “I love you, Bob! Please eat healthier!” on a sticky note. She passes it to Eve, so Eve can pass it to Alice’s love interest. However, in an unfortunate turn of events Eve reads the note herself, and decides not to give it to Bob.

Oh the horror! Alice is without young love! How could she remedy this so that Bob can read her message, but evil Eve can not? Let’s use the Caesar cipher to fix this problem.

Let us assume that Alice and Bob already have a shared key, 7 for example. To encrypt this message, she should shift her letters seven letters forward in the alphabet—just like the example above.

A longer Ceasar cipher encrypted message: ROT2: Wpeng Vgf ku dqqogt ogog]
A longer Ceasar cipher encrypted message using ROT2.

Now Alice’s message reads “P svcl fvb, Ivi! Wslhzl lha olhsaoply!”

Now, when Alice sends her Romeo a little note, all he has to do is decrypt the text by shifting the letters down by 7. Here is a site which can do longer pieces of text for you instead of doing it manually.

Problems

Before the two love-birds start smooching on the branch of a big pine tree in the schoolyard, perhaps we should consider some problems with the Ceasar cipher.

It is Very Easy to Break

Even Eve with her measly grade 4 math skills could easily start going through this message with pen and paper and figure out any combination in a couple hours at maximum. Imagine how easy this is for a computer? This could be broken in a few microseconds even on an older processor like the Intel Core 2 Duo.

No Secure Way of Sharing Keys

We assumed in our previous example that Bob and Alice already have a shared key (seven) to encrypt and decrypt all of their messages. If Bob and Alice did not have a previous friendship and time to share secrets of this sort, there is no way to share their key with eachother without Eve also knowing. This would defeat the entire purpose of obscuring the message in the first place.

Universal Vulnerability of Messages

Every message sent between the two parties uses the same code to encrypt and decrypt. If someone finds out the code once, all previous communications are comprimised.

Better Encryption Methods

To combat the issues with easily breakable, shared-key cryptography, we can turn to the beautiful beast that is Asymetric Cryptography. I will discuss this more in another article, but for the technically inclined:

  1. RSA/EC provides very large cryptographic keys. It would be impossible for a human to encrypt or decrypt a message manually.
  2. Asymetric cryptography provides four keys, instead of just one; stopping evesdroppers from listening in on your secret conversations—even if you do not have the chance to exchange keys in advance.

\ No newline at end of file + How Does Encryption Work, in Theory? | tait.tech

How Does Encryption Work, in Theory?


There are many kinds of encryption used in our everyday communication. Online and offline, over the internet and in person. In this article, I will explain the basics of how encryption should work in theory. I explain in this article why encryption is important, and why you should care about it.

We will start by looking at in-person, offline encryption.

Cryptography We Do Everyday

We encrypt things all the time without even thinking about it. If you spend a significant amount of time with the same group of friends, you will tend to develop common codes that may not make sense to others outside the group. For example: for years, my family called sombody falling from a sitting position “doing a Don”. There is a story of course—We knew a guy named Don who fell from his plastic beach chair in a rather hilarious way; “doing a Don” was born.

These types of minor dialects in speech are cryptographic in their own way. The truth is though, that we use cryptography much more than that!

“Is cryptography any different than talking? We say something other than what we mean, and then expect everyone is able to decipher the true meaning behind the words. Only, I never do…” — Adapted from a scene in The Imitation Game (p. 39-40)

How many times have you hinted, flirted, and innuendoed to try to say “I find you very physically attractive”? Have you told your friend that always stinks to wear more deodorant? Have you ever had someone say the words “I’m fine” when you know for certain that they are indeed not okay?

Words Said Meaning
What can you do? I don’t want to talk about this anymore.
I don’t want to overstay my welcome. I want to go home now.
I don’t like them and don’t know why. They threaten my ego.
Creepy Unattractive and friendly

All of these scenarios are perfect examples of lies encryption! If we have the key to these codes, we can start to understand what people really mean. Hopefully I have convinced you that you use deceit cryptography on a regular basis in your life, so let us consider what a basic encryption method might be:

Grade-School Encryption

Back when I was in middle school I used to pass notes like these:

A message I would have sent in middle school. ROT5: Xfwfm hx hzy
The kind of message I would have sent in middle school. A ROT5 Ceasar cipher.

This is a message encrypted using the Caesar cipher. This encryption technique was used by Julius Caesar during the reign of the Roman Empire to “encrypt messages of military significance.”[1] This is one of the oldest and simplest methods of encryption known to us today.

A diagram of a Ceasar Shift algorithm. A <-> N, B <-> O, et cetera.
A diagram of a ROT13 Ceasar shift algorithm. A <-> N, B <-> O, et cetera.

You can try this out yourself by moving some letters forward in the alphabet. An ‘A’ turns into a ‘B’, ‘B’ into ‘C’, ‘C’ into ‘D’, et cetera. In this case, “Hello!” would become “Ifmmp!” That is just using a shift of one. You can use a shift of seven, for example, and then you would shift letters like so:

  • A -> +7 -> H
  • Q -> +7 -> X
  • T -> +7 -> A

When you reach the end of the alphabet, wrap around to the beginning to find the encrypted letter.

Example of a Caesar Cipher

Let’s setup a little story to illustrate the problems of encryption. We will have three characters:

  • Alice, young lady with feelings for Bob
  • Bob, a young lad with an addiction to pancakes
  • Eve, a wee jealous girl scout who sits between Bob and Alice

Alice really likes Bob and wants to tell Bob her feelings, so she writes “I love you, Bob! Please eat healthier!” on a sticky note. She passes it to Eve, so Eve can pass it to Alice’s love interest. However, in an unfortunate turn of events Eve reads the note herself, and decides not to give it to Bob.

Oh the horror! Alice is without young love! How could she remedy this so that Bob can read her message, but evil Eve can not? Let’s use the Caesar cipher to fix this problem.

Let us assume that Alice and Bob already have a shared key, 7 for example. To encrypt this message, she should shift her letters seven letters forward in the alphabet—just like the example above.

A longer Ceasar cipher encrypted message: ROT2: Wpeng Vgf ku dqqogt ogog]
A longer Ceasar cipher encrypted message using ROT2.

Now Alice’s message reads “P svcl fvb, Ivi! Wslhzl lha olhsaoply!”

Now, when Alice sends her Romeo a little note, all he has to do is decrypt the text by shifting the letters down by 7. Here is a site which can do longer pieces of text for you instead of doing it manually.

Problems

Before the two love-birds start smooching on the branch of a big pine tree in the schoolyard, perhaps we should consider some problems with the Ceasar cipher.

It is Very Easy to Break

Even Eve with her measly grade 4 math skills could easily start going through this message with pen and paper and figure out any combination in a couple hours at maximum. Imagine how easy this is for a computer? This could be broken in a few microseconds even on an older processor like the Intel Core 2 Duo.

No Secure Way of Sharing Keys

We assumed in our previous example that Bob and Alice already have a shared key (seven) to encrypt and decrypt all of their messages. If Bob and Alice did not have a previous friendship and time to share secrets of this sort, there is no way to share their key with eachother without Eve also knowing. This would defeat the entire purpose of obscuring the message in the first place.

Universal Vulnerability of Messages

Every message sent between the two parties uses the same code to encrypt and decrypt. If someone finds out the code once, all previous communications are comprimised.

Better Encryption Methods

To combat the issues with easily breakable, shared-key cryptography, we can turn to the beautiful beast that is Asymetric Cryptography. I will discuss this more in another article, but for the technically inclined:

  1. RSA/EC provides very large cryptographic keys. It would be impossible for a human to encrypt or decrypt a message manually.
  2. Asymetric cryptography provides four keys, instead of just one; stopping evesdroppers from listening in on your secret conversations—even if you do not have the chance to exchange keys in advance.

\ No newline at end of file diff --git a/_site/2020/04/02/rsa3/index.html b/_site/2020/04/02/rsa3/index.html index e67fd10..18f0d3b 100644 --- a/_site/2020/04/02/rsa3/index.html +++ b/_site/2020/04/02/rsa3/index.html @@ -1 +1 @@ - How Asymetric Encryption Works | tait.tech

How Asymetric Encryption Works


In a few previous articles I have explained why encryption may be important to you and how the theory behind encryption works. I did not yet explain the system of asymetric cryptography, however. That is what this article is for.

Previously, we talked about how symetric encryption works. This is by having a shared key that both parties use to simultaniously encrypt, and decrypt the data. (See Ceasar Cipher for example).

Public-key, or Asymetric Encryption

Asymetric encryption is based on the idea of having multiple keys instead of only one shared key. For example: instead of encrypting with one key, and decrypting with that same key (like our ROT ciphers we talked about previously), we can use one key to encrypt the information, and a different key to decrypt the information.

Alice sending her message to Bob using Bob's public key. Bob decrypts the message with his private key.
Alice sending her message to Bob using Bob's public key. Bob decrypts the message with his private key.

In the picture above, see how Alice uses Bob’s public key to encrypt some data, then sends it to Bob for him to decrypt with his private key? That is the essense of public-key encryption.

The great thing about public-key encryption is that your public key is public! There is no need to be afraid of sending this everywhere! You can attach it at the end of all your emails, the end of your forum posts, a link to it on your low-power webserver (wink). There are even things called keyservers that will save your public key on them for retrival in case somebody wants to verify your public key.

Anything encrypted with your public key can only be decrypted with your private key. Provided you never, NEVER share your private key with anyone ever, we can assume that all messages sent to you encrypted with your public key will never be read by anyone else.

Asymetric encryption, however, often contains four keys instead of two. Why is this?

Verification of Author

One interesting thing about keys pairs is that not only can the private key decrypt anything the public key encrypts, but the public key can decrypt anything the private key encrypts.

Now why would one want to encrypt a message that can be decrypted by anyone?

Alice sending a message to bob which is 'signed' with her private key. This allows Bob to know only Alice could have sent it!
Alice sending a message to bob which is 'signed' with her private key. This allows Bob to know only Alice could have sent it!

Note: Although the picture shows otherwise, the text is not sent in the plain. It is encrypted with Alice's private key.

This is how you can verify that the person who says they wrote the message really did indeed write the message! If their private key was never shared with anyone else, then the message must have come from them!

For maximum security, these methods are often layered. First, signing with the sender’s private key, ensuring only they could have sent it— then encrypted with the recipient’s pulbic key, making sure only the reciever can read it.

Note that both sides must first have eachother’s public keys to do this. This is easy if they communicate often, but when first contacting somebody, people will generally send their encrypted message along with the their own pulbic key attached in a seperate file.

What This Means

Notice neither Alice nor Bob had to share any comprimsing information over the network? This is why public-key encryption is so powerful!

Alice and Bob can both safely send their public keys in the open. They can even send them over the insecure HTTP, or FTP protocols.

Whilst not sending any encryption-breaking messages, Alice and Bob now have a way to communicate securely. If you trust nothing and no one, this is your perfered method of security.

Check out this Computerphile video if you want the simplified explaination.

The Algorithms

The two biggest “implementations” of public-key cryptography vary only in the mathamatical equations used to generate the numbers, and how the numbers are “trapdoored” to decrypt if you have the correct key.

I will discuss the differences in approach here. If you want to skip to the next article where I show you how to encrypt your own documents using RSA, see this link.

RSA

The mathamatic center of the RSA system was developed over the course of a year or so. Three men were involved. Ron Rivest, Adi Shamir, and Leonard Aldeman. They worked as a kind of “team”: Each idea by Rivest and Shamir were critisized by the mathamatician on their team: Mr. Aldeman.

One night, after consuming “liberal quantities of Manischewitz wine” Rivest had trouble sleeping. After taking long gazes into the abyss of his math textbook, he came up with an idea which would change cryptography forever. By the next morning, an academic mathamatical paper was nearly finished. He named it after himself and the two others that had been helping him along this whole time. Rivest, Shamir, Aldeman.

Key sizes of RSA range from 1024-bit to 4096-bit. 1024-bit keys are considered somewhat insecure. However, it should be noted that every bit doubles the complexity of the key, so 2048 is 2^1024 times more complex than 1024.

Eliptic-Curve (EC)

Eliptic-Curve (EC) is a family of algorithms that use the Eliptic curve mathamatical structure to generate the numbers for the keys. EC can effectivly provide the security of an RSA key one order of magnitude larger than an RSA key.

A picture of an eliptic curve.
An eliptic curve structure.

It’s fast; it’s secure! Perfect right?

Of course not!

One problem is that due to the smaller key size, it can more easily be broken by brute-force. This is why EC is mostly used for temporary communication (like HTTPS), not permenant communication (like having an encrypted email conversation with a journalist).

The other problem is that a certain EC algrorithm called P-256 is suspected to be introduced with malice to National Institute of Standards and Technology (NIST) by the NSA. Supposedly, the NSA is able to crack anything encrypted with this algorithm. I will let the experts argure about that.

Other well-known EC algorithms that are more-or-less trusted as secure do exist though. The premeire one being Curve25519. The reference implementation of this algrorithm is also public-domain, so it is easy for devlopers to work into their own applications without worrying about copywrite.

Conslusion

In this article we went over some basic points:

  1. Public-key encryption enables secure communication over insecure networks.
  2. RSA is considered the standard for extra-seure communication.
  3. EC is a newer, faster, more transient encryption method.

To learn how to use RSA keys to encrypt your own communications, check out this other aritcle I wrote.


\ No newline at end of file + How Asymetric Encryption Works | tait.tech

How Asymetric Encryption Works


In a few previous articles I have explained why encryption may be important to you and how the theory behind encryption works. I did not yet explain the system of asymetric cryptography, however. That is what this article is for.

Previously, we talked about how symetric encryption works. This is by having a shared key that both parties use to simultaniously encrypt, and decrypt the data. (See Ceasar Cipher for example).

Public-key, or Asymetric Encryption

Asymetric encryption is based on the idea of having multiple keys instead of only one shared key. For example: instead of encrypting with one key, and decrypting with that same key (like our ROT ciphers we talked about previously), we can use one key to encrypt the information, and a different key to decrypt the information.

Alice sending her message to Bob using Bob's public key. Bob decrypts the message with his private key.
Alice sending her message to Bob using Bob's public key. Bob decrypts the message with his private key.

In the picture above, see how Alice uses Bob’s public key to encrypt some data, then sends it to Bob for him to decrypt with his private key? That is the essense of public-key encryption.

The great thing about public-key encryption is that your public key is public! There is no need to be afraid of sending this everywhere! You can attach it at the end of all your emails, the end of your forum posts, a link to it on your low-power webserver (wink). There are even things called keyservers that will save your public key on them for retrival in case somebody wants to verify your public key.

Anything encrypted with your public key can only be decrypted with your private key. Provided you never, NEVER share your private key with anyone ever, we can assume that all messages sent to you encrypted with your public key will never be read by anyone else.

Asymetric encryption, however, often contains four keys instead of two. Why is this?

Verification of Author

One interesting thing about keys pairs is that not only can the private key decrypt anything the public key encrypts, but the public key can decrypt anything the private key encrypts.

Now why would one want to encrypt a message that can be decrypted by anyone?

Alice sending a message to bob which is 'signed' with her private key. This allows Bob to know only Alice could have sent it!
Alice sending a message to bob which is 'signed' with her private key. This allows Bob to know only Alice could have sent it!

Note: Although the picture shows otherwise, the text is not sent in the plain. It is encrypted with Alice's private key.

This is how you can verify that the person who says they wrote the message really did indeed write the message! If their private key was never shared with anyone else, then the message must have come from them!

For maximum security, these methods are often layered. First, signing with the sender’s private key, ensuring only they could have sent it— then encrypted with the recipient’s pulbic key, making sure only the reciever can read it.

Note that both sides must first have eachother’s public keys to do this. This is easy if they communicate often, but when first contacting somebody, people will generally send their encrypted message along with the their own pulbic key attached in a seperate file.

What This Means

Notice neither Alice nor Bob had to share any comprimsing information over the network? This is why public-key encryption is so powerful!

Alice and Bob can both safely send their public keys in the open. They can even send them over the insecure HTTP, or FTP protocols.

Whilst not sending any encryption-breaking messages, Alice and Bob now have a way to communicate securely. If you trust nothing and no one, this is your perfered method of security.

Check out this Computerphile video if you want the simplified explaination.

The Algorithms

The two biggest “implementations” of public-key cryptography vary only in the mathamatical equations used to generate the numbers, and how the numbers are “trapdoored” to decrypt if you have the correct key.

I will discuss the differences in approach here. If you want to skip to the next article where I show you how to encrypt your own documents using RSA, see this link.

RSA

The mathamatic center of the RSA system was developed over the course of a year or so. Three men were involved. Ron Rivest, Adi Shamir, and Leonard Aldeman. They worked as a kind of “team”: Each idea by Rivest and Shamir were critisized by the mathamatician on their team: Mr. Aldeman.

One night, after consuming “liberal quantities of Manischewitz wine” Rivest had trouble sleeping. After taking long gazes into the abyss of his math textbook, he came up with an idea which would change cryptography forever. By the next morning, an academic mathamatical paper was nearly finished. He named it after himself and the two others that had been helping him along this whole time. Rivest, Shamir, Aldeman.

Key sizes of RSA range from 1024-bit to 4096-bit. 1024-bit keys are considered somewhat insecure. However, it should be noted that every bit doubles the complexity of the key, so 2048 is 2^1024 times more complex than 1024.

Eliptic-Curve (EC)

Eliptic-Curve (EC) is a family of algorithms that use the Eliptic curve mathamatical structure to generate the numbers for the keys. EC can effectivly provide the security of an RSA key one order of magnitude larger than an RSA key.

A picture of an eliptic curve.
An eliptic curve structure.

It’s fast; it’s secure! Perfect right?

Of course not!

One problem is that due to the smaller key size, it can more easily be broken by brute-force. This is why EC is mostly used for temporary communication (like HTTPS), not permenant communication (like having an encrypted email conversation with a journalist).

The other problem is that a certain EC algrorithm called P-256 is suspected to be introduced with malice to National Institute of Standards and Technology (NIST) by the NSA. Supposedly, the NSA is able to crack anything encrypted with this algorithm. I will let the experts argure about that.

Other well-known EC algorithms that are more-or-less trusted as secure do exist though. The premeire one being Curve25519. The reference implementation of this algrorithm is also public-domain, so it is easy for devlopers to work into their own applications without worrying about copywrite.

Conslusion

In this article we went over some basic points:

  1. Public-key encryption enables secure communication over insecure networks.
  2. RSA is considered the standard for extra-seure communication.
  3. EC is a newer, faster, more transient encryption method.

To learn how to use RSA keys to encrypt your own communications, check out this other aritcle I wrote.


\ No newline at end of file diff --git a/_site/blog/index.html b/_site/blog/index.html index 95c7b5e..34346fb 100644 --- a/_site/blog/index.html +++ b/_site/blog/index.html @@ -1 +1 @@ - Blog | tait.tech

Blog

Orca, Emacspeak and Chromium Accessibility on A Raspberry Pi Running Manjaro ARM

I wanted to get a gift for my blind friend who has been interested in learning Linux for a while now. Just when I was about to start looking for something I decided to take a look at Brian Lunduke’s newest video featuring the Raspberry Pi 400. The Raspberry Pi 400 has come full circle in terms of computing. It is a keyboard. All the computing is done from within the keyboard. Much like the Comodore64, this computer comes without a screen but is still technically fully functional without one. I had my ‘Aha!’ moment, and decided that the Raspberry Pi 400 would be a very cool present.

Curiosity

Curiosity is fundamental to a deep understanding of any subject. Masters, Ph.Ds, and other fancy name suffixes will never help you if you don’t have the spirit of curiosity burning inside of you.

Minesweeper Bomb Generation And Tile Revealing

When I was creating a little Minesweeper game, I got confused at some points. My bomb generation didn’t look quite right, and I for sure didn’t quite get the whole cascading tile reveal thing. With a bit of internet research, I found what I was looking for. I’ll explain it all in one place for my own research purposes.

How to Solve The Django Deployment Puzzle

A few days ago I had a Django project I wanted to put on a real server. This project is still in its infancy, but I thought it would be nice to put it on my resume and show my friends. Little did I know the headache coming my way. Here are some tips to help you not make the same mistakes as me.

BSD Journey, Part 1

As Linux becomes controlled by corporate sponsors and becomes more full of proprietary blobs, drivers, and even closed-source software like Steam, One may wonder if there are other options out there. For me, somebody that is intensely interested in security, there is one option: OpenBSD.

Know How Your Representative Votes In Parliament

As an advocate for openness, I had an idea to make a project out of the government of Canada’s Open Data initiative to take a look at how my local MP voted on various pieces of legislation. It turns out though that this was not necessary due to how easy it was to find this information on the government’s own website. In this article, I will explain how you can do the same.

Installing MultiCraft on Gentoo Linux

In a very odd combination of requirements, I needed to install MultiCraft on a Gentoo Linux system. The PHP USE flags are important so you don’t have to recompile it three times like I did.

Independence

“When given a choice between independence and dependence, always choose independence; you will never regret that choice!”—Luke Smith

How to use tmux to send and receive things from your Minecraft server

So recently I had problem. I run a Minecraft server on a big Linux computer I have running in my room. Now, as a system administrator it is very helpful to be able to run some simple commands without needing to login with my key, password, TFA, etc. It is, frankly, a lot of work. Especially when I really just want to be playing games but I just need to check something quickly.

Site Update

I updated the site with some easier to identify information about me and my projects :)

New Game: Clue (coming soon)

Ooo! Exciting! Today I want to announce a new project I’ll be working on which should be live within the month of May: Clue.

What is XSS?

I found a cross-site scripting (XSS) attack in a well-known quiz hosting website. I disclosed the vulnerability to them years ago, so I thought now might be a good time to write about it.

How To Encrypt Your Own Documents Using gpg

If you have ever wanted to garuntee the utmost security of your emails and documents, then this is the guide for you! It should be noted that in some circles the tools used are more common than in others. These are the everyday tools of many privacy advocates and computer nerds.

How Does Encryption Work, in Theory?

There are many kinds of encryption used in our everyday communication. Online and offline, over the internet and in person. In this article, I will explain the basics of how encryption should work in theory. I explain in this article why encryption is important, and why you should care about it.

Is Encryption Worth It?

What is the most embarassing thing you have typed into Google search? What is the most personal secret you told a friend in confidence? What is your bank password? What is your business’s secret to stay ahead of the competition?

Padding And Margin

Many people have expressed confusion over how padding and margins work in HTML/CSS. I have been one of those people. In this short article I will explain what the differences are between the two, and how it may affect the functionality of your site.


\ No newline at end of file + Blog | tait.tech

Blog

Orca, Emacspeak and Chromium Accessibility on A Raspberry Pi Running Manjaro ARM

I wanted to get a gift for my blind friend who has been interested in learning Linux for a while now. Just when I was about to start looking for something I decided to take a look at Brian Lunduke’s newest video featuring the Raspberry Pi 400. The Raspberry Pi 400 has come full circle in terms of computing. It is a keyboard. All the computing is done from within the keyboard. Much like the Comodore64, this computer comes without a screen but is still technically fully functional without one. I had my ‘Aha!’ moment, and decided that the Raspberry Pi 400 would be a very cool present.

Curiosity

Curiosity is fundamental to a deep understanding of any subject. Masters, Ph.Ds, and other fancy name suffixes will never help you if you don’t have the spirit of curiosity burning inside of you.

Minesweeper Bomb Generation And Tile Revealing

When I was creating a little Minesweeper game, I got confused at some points. My bomb generation didn’t look quite right, and I for sure didn’t quite get the whole cascading tile reveal thing. With a bit of internet research, I found what I was looking for. I’ll explain it all in one place for my own research purposes.

How to Solve The Django Deployment Puzzle

A few days ago I had a Django project I wanted to put on a real server. This project is still in its infancy, but I thought it would be nice to put it on my resume and show my friends. Little did I know the headache coming my way. Here are some tips to help you not make the same mistakes as me.

BSD Journey, Part 1

As Linux becomes controlled by corporate sponsors and becomes more full of proprietary blobs, drivers, and even closed-source software like Steam, One may wonder if there are other options out there. For me, somebody that is intensely interested in security, there is one option: OpenBSD.

Know How Your Representative Votes In Parliament

As an advocate for openness, I had an idea to make a project out of the government of Canada’s Open Data initiative to take a look at how my local MP voted on various pieces of legislation. It turns out though that this was not necessary due to how easy it was to find this information on the government’s own website. In this article, I will explain how you can do the same.

Installing MultiCraft on Gentoo Linux

In a very odd combination of requirements, I needed to install MultiCraft on a Gentoo Linux system. The PHP USE flags are important so you don’t have to recompile it three times like I did.

Independence

“When given a choice between independence and dependence, always choose independence; you will never regret that choice!”—Luke Smith

How to use tmux to send and receive things from your Minecraft server

So recently I had problem. I run a Minecraft server on a big Linux computer I have running in my room. Now, as a system administrator it is very helpful to be able to run some simple commands without needing to login with my key, password, TFA, etc. It is, frankly, a lot of work. Especially when I really just want to be playing games but I just need to check something quickly.

Site Update

I updated the site with some easier to identify information about me and my projects :)

New Game: Clue (coming soon)

Ooo! Exciting! Today I want to announce a new project I’ll be working on which should be live within the month of May: Clue.

What is XSS?

I found a cross-site scripting (XSS) attack in a well-known quiz hosting website. I disclosed the vulnerability to them years ago, so I thought now might be a good time to write about it.

How To Encrypt Your Own Documents Using gpg

If you have ever wanted to garuntee the utmost security of your emails and documents, then this is the guide for you! It should be noted that in some circles the tools used are more common than in others. These are the everyday tools of many privacy advocates and computer nerds.

How Does Encryption Work, in Theory?

There are many kinds of encryption used in our everyday communication. Online and offline, over the internet and in person. In this article, I will explain the basics of how encryption should work in theory. I explain in this article why encryption is important, and why you should care about it.

Is Encryption Worth It?

What is the most embarassing thing you have typed into Google search? What is the most personal secret you told a friend in confidence? What is your bank password? What is your business’s secret to stay ahead of the competition?

Padding And Margin

Many people have expressed confusion over how padding and margins work in HTML/CSS. I have been one of those people. In this short article I will explain what the differences are between the two, and how it may affect the functionality of your site.


\ No newline at end of file diff --git a/_site/feed.xml b/_site/feed.xml index e33e9d1..06d894a 100644 --- a/_site/feed.xml +++ b/_site/feed.xml @@ -1 +1 @@ -Jekyll2020-12-14T11:09:32-07:00/feed.xmlGetting Pacaur Working on a Raspberry Pi 4 with Manjaro ARM or Arch Linux2020-12-01T00:00:00-07:002020-12-01T00:00:00-07:00/2020/12/01/pacaur-rpi<p>I recently installed Manjaro ARM (based on Arch Linux ARM) on a Raspberry Pi 4. I used some standard commands to start to add the <code class="language-plaintext highlighter-rouge">pacaur</code> package so I can easily retrieve <a href="https://wiki.archlinux.org/index.php/Arch_User_Repository">AUR packages</a> without needing to do it manually. Unfortunately, there is a small problem with compiling this on ARM.</p> <h2 id="always_inline">always_inline</h2> <p>To setup the install for <code class="language-plaintext highlighter-rouge">pacaur</code>, I first needed to download <a href="https://aur.archlinux.org/packages/auracle-git">auracle-git</a> AUR package manually. I ran into an error when compiling this package.</p> <p>But first, my setup:</p> <pre class="terminal"> $ git clone https://aur.archlinux.org/auracle-git $ cd auracle-git $ makepkg -sri </pre> <p>Around half way through compiling this project, I got this cryptic message telling me there was a “target specific option mismatch”…Whatever that means. The full error is below, hopefully that helps my chances on the search engines.</p> <pre class="terminal"> In file included from ../subprojects/abseil-cpp-20200225.2/absl/random/internal/randen_hwaes.cc:225: /usr/lib/gcc/aarch64-unknown-linux-gnu/9.3.0/include/arm_neon.h: In function 'Vector128 {anonymous}::AesRound(const Vector128&amp;, const Vector128&amp;)': /usr/lib/gcc/aarch64-unknown-linux-gnu/9.3.0/include/arm_neon.h:12452:1: error: inlining failed in call to always_inline 'uint8x16_t vaesmcq_u8(uint8x16_t)': target specific option mismatch 12452 | vaesmcq_u8 (uint8x16_t data) </pre> <p>Luckily, there is a very easy fix for this. The user redfish <a href="https://aur.archlinux.org/packages/auracle-git#comment-762117">helpfully pointed out</a> on the <code class="language-plaintext highlighter-rouge">auracle-git</code> package page that you need to add a special make option to your <code class="language-plaintext highlighter-rouge">/etc/make.conf</code> file to make this work.</p> <p>His solution, as commented is like so:</p> <blockquote> <p>If you get this error when building for ARM aarch64:</p> <p>(insert error message from before)</p> <p>Then check that in /etc/makepkg.conf CFLAGS and CXXFLAGS have the +crypto suffix in -march flag, like -march=armv8-a+crypto (the base identifier may very depending on your hardware)</p> </blockquote> <p>Basically, there is a file on Linux: <code class="language-plaintext highlighter-rouge">/etc/makepkg.conf</code> which tells your computer how to compile <em>all</em> programs on the system. By default the Manjaro ARM (RPi4) edition has the following relevant lines in <code class="language-plaintext highlighter-rouge">makepkg.conf</code>.</p> <pre class="file"> CFLAGS="-march=armv8-a -O2 -pipe -fstack-protector-strong -fno-plt" CXXFLAGS="-march=armv8-a -O2 -pipe -fstack-protector-strong -fno-plt" </pre> <p>What Mr. redfish is telling us is that we must add ‘+crypto’ to the end of the -march compiler flag so that our compiler will know how to inline that pesky vaesmcq_u8 function.</p> <p>So in the end, your <code class="language-plaintext highlighter-rouge">makepkg.conf</code>’s relevant lines will look like so:</p> <pre class="file"> CFLAGS="-march=armv8-a+crypto -O2 -pipe -fstack-protector-strong -fno-plt" CXXFLAGS="-march=armv8-a+crypto -O2 -pipe -fstack-protector-strong -fno-plt" </pre> <h2 id="why">Why?</h2> <p>Redfish continues:</p> <blockquote> <p>Build of abseil-cpp package works because it uses CMake which adds the correct -march flag regardless of makepkg.conf, whereas when abseil-cpp is build as a subproject within this package, it uses meson, which does not add the flag and thus fails with the above error.</p> </blockquote> <p>In other words, one of the dependencies pulled in with auracle is not compiling without this special compiler flag enabled.</p> <h2 id="conclusion">Conclusion</h2> <p>Thanks to redfish for posting this solution to the forums! Would’ve been quite the rabbit hole for me to figure out how to do that. In fact, it is very likely I would have never figured that one out.</p> <p>After this issue is resolved, the installation of <code class="language-plaintext highlighter-rouge">pacaur</code> goes as expected. Nice and easy! Pacuar will compile on any architecture so it’s smooth sailing from here.</p> <p>Happy hacking!</p>I recently installed Manjaro ARM (based on Arch Linux ARM) on a Raspberry Pi 4. I used some standard commands to start to add the pacaur package so I can easily retrieve AUR packages without needing to do it manually. Unfortunately, there is a small problem with compiling this on ARM.ZFS NAS Box, Part 22020-11-15T00:00:00-07:002020-11-15T00:00:00-07:00/2020/11/15/nas2<p>Back in <a href="/2020/04/12/nas1/">part one of my NAS project</a> I discussed how I wanted to set up my hardware. Today, I set up the NAS (almost).</p> <p>There were some hiccup along the way, like learning that M.2 slots can disable some of your SATA ports or waiting a month for a host bus adapter to come in from China.</p> <h2 id="why-did-it-take-so-long">Why Did It Take So Long</h2> <p>So it turns out I was going to spend a lot more on this project than I originally anticipated. I ended up getting a server machine instead of a sleek NAS box. Here are some of the quick specs:</p> <ul> <li>Standard ATX case by Thermaltake.</li> <li>LSI 9211-8i.</li> <li>The cheapest HDMI graphics card I could find on Kijiji.</li> <li>6x 3TB Segate HDDs.</li> <li>1x 250G Kingston SSD.</li> <li>AMD Ryzen 5 3600.</li> <li>MSI B450 Gaming Plus Max.</li> <li>2x 8GB FlareX 3200Mhz RAM.</li> <li>1x 16GB Kingston 3200Mhz RAM.</li> </ul> <h2 id="zfs">ZFS</h2> <p>This is how I decided to configure my storage pools. In hindsight, this was not the best choice for upgrading. I may change it in the future to a 0+1 setup, but it works for now.</p> <p>I have 5x 3TB in a RAIDZ2 with one drive not attached for redundancy’s sake. How does one setup a ZFS pool. Check this out:</p> <pre class="terminal"> # zpool create poolname raidz2 \ /dev/by-id/blahblahblah1 \ /dev/by-id/blahblahblah2 \ /dev/by-id/blahblahblah3 \ /dev/by-id/blahblahblah4 \ /dev/by-id/blahblahblah5 </pre> <p>And zippidy-doo! We’ve got a ZFS pool! We can check its status with <code class="language-plaintext highlighter-rouge">zpool status</code>.</p> <pre class="terminal"> $ zfs status pool: raid state: ONLINE scan: scrub in progress since Wed Nov 18 18:41:41 2020 1.84T scanned at 8.51G/s, 121G issued at 562M/s, 1.84T total 0B repaired, 6.45% done, 0 days 00:53:25 to go config: NAME STATE READ WRITE CKSUM raid ONLINE 0 0 0 raidz2-0 ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JTNMYY ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JVSXTY ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JXAS8Y ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JXBARY ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JXP77Y ONLINE 0 0 0 errors: No known data errors </pre> <p>I had run a scrub right before this, so there’s some extra detail in that. This is really fun! I will be doing more home storage projects soon. Perhaps Raspberry Pi NAS using all 4 USB ports to load SATA drives on it. Now that would be fun!</p> <h2 id="so-i-kinda-have-a-nas-now">So I Kinda Have A NAS Now…?</h2> <p>So right now I can only copy files with <code class="language-plaintext highlighter-rouge">rsync</code>, <code class="language-plaintext highlighter-rouge">scp</code> and moving data via a physical drive. The one major disadvantage this has is speed.</p> <p>Due to this machine being connected directly outside my network and pulling DHCP like a normal router would, I need to send my data through the WAN connection to get my files to it. This is rather unfortunate as my upload speed is capped at 20 megabits per second, despite my upload being in the 300+ range.</p> <p>Part 3 will involve a LAN card so I can connect both to the DHCP server of my ISP and my local router. This way my transfer speeds should be in the range of 1 gigabit per second. This will make my life much easier, at least on the local network.</p> <h2 id="fun-fact">Fun Fact!</h2> <p>Do not try to use the M.2 slot on a consumer motherboard where you are also using all the SATA ports. On my consumer gaming motherboard, the SATA ports next to the M.2 slot became <em>disabled</em> when I attached the M.2 SSD. I found this out form my motherboard documentation, which I read only after a week of thinking my motherboard itself was defective, and sending it in for repairs that did absolutely nothing.</p> <h2 id="thoughts">Thoughts</h2> <p>I like having all this space. I plan on using it up pretty fast, so I’m already looking at how to expand. Hopefully that gives a decent overview of how I set up my drives.</p> <p>Happy hacking!</p>Back in part one of my NAS project I discussed how I wanted to set up my hardware. Today, I set up the NAS (almost).Curiosity2020-10-26T00:00:00-06:002020-10-26T00:00:00-06:00/2020/10/26/curiosity<p>Curiosity is fundamental to a deep understanding of any subject. Masters, Ph.Ds, and other fancy name suffixes will never help you if you don’t have the spirit of curiosity burning inside of you.</p> <p>I was speaking to someone from a journalism major at my school when the subject of hacking arose. I expected her to know nothing about it, being a journalism student and all, but surprisingly she had something to say about it:</p> <blockquote> <p>“The best hackers are the ones who are curious.”</p> </blockquote> <p>That struck a cord with me. It seems to me she has nailed down the difference between the students who care about grades, and those who want to learn. These are not necessarily mutually exclusive, but in my experience they often are due to the way education is structured.</p> <h2 id="my-anecdote">My Anecdote</h2> <p>In my second semester at SAIT Polytechnic, I took a class entitled <em>Emerging Trends In Technology</em>. This class was probably the best class I have ever taken. We had to combine two things:</p> <ul> <li><strong>Hard skills</strong>: learning a new hard skill like Angular, Django, or GPG encryption.</li> <li><strong>Soft skills</strong>: public speaking and presentation of our ideas.</li> </ul> <p>Soft skills are not usually my area, but I can do public speaking. I grew up quite religious, so public speaking was drilled into me young. I liked to go off script and talk about interesting things I found along the way to the actual point. My creativity was not usually encouraged. That said, going off script is useful when teaching and presenting ideas; it gives a natural air to your breath and an unquestionable confidence in your speech.</p> <p>This is how we learn: in relationships. Try explaining ancient Japanese history to a computer science major, or UNIX sockets to an English major and you’ll see what I mean. If there is nothing for us to connect the knowledge to, it dissipates.</p> <p>So why did I do so well in this class?</p> <p>Our task for the semester was as follows:</p> <ol> <li>Learn a new subject (any <em>emerging trend in technology</em>) which you find fascinating.</li> <li>Give a one minute introduction by week three.</li> <li>Give a 10 minute non-technical overview by week 8.</li> <li>Give a 20 minute technical explaination and demo by week 13.</li> </ol> <p>This is the only course I have ever taken which lets students’ imagination run wild. Their presentation, their rules. They treated the students like adults who know what they are doing. What happened? Everyone stopped coming because “Oh no! Presentations!”?</p> <p>No, exactly the opposite. There was never more than one student missing. Every single presentation was at least moderately interesting, and most students were excited to come to that class. You could see it in their faces, the way they carried themselves. Every student picked something unique to their tastes, leaving every student more educated than before.</p> <p>This class, unlike many others, encouraged the curiosity of the students. It rewarded those who had unique interests and an ability to sell others on their ideas.</p> <p>The curiosity and the grades were one.</p> <h2 id="conclusion">Conclusion</h2> <p>Although it’s nice to have a course where these goals align here and there, anyone who has been to collage or university can tell you that is far from the norm.</p> <p>On the other hand, I never would have started this site if it wasn’t for that class alone. So I thank you, Kitty Wong, for getting me started running my own “research blog” (?)</p>Curiosity is fundamental to a deep understanding of any subject. Masters, Ph.Ds, and other fancy name suffixes will never help you if you don’t have the spirit of curiosity burning inside of you.Minesweeper Bomb Generation And Tile Revealing2020-09-12T00:00:00-06:002020-09-12T00:00:00-06:00/2020/09/12/minesweeper<p>When I was creating a little Minesweeper game, I got confused at some points. My bomb generation didn’t look quite right, and I for sure didn’t quite get the whole cascading tile reveal thing. With a bit of internet research, I found what I was looking for. I’ll explain it all in one place for my own research purposes.</p> <h2 id="bomb-generation">Bomb Generation</h2> <p>When I started this project I attempted to use a random bomb generator. By this I mean on each square, before it gets generated, give it a one in 15 change of being a bomb. Personally, I’m not sure why this never looked right. Something about the layout of the bombs did not mimic the classic Minesweeper game.</p> <p>After looking at some open source Minesweeper examples, I started to get the idea. I wrote some mathematical statements describing the generation of bombs and how to get their x,y position from an appropriate number. For those non-mathy people, don’t leave just yet; there will be code equivalents to the math.</p> <p>W and H are the width and height of the board respectively.</p> <p><span class="katex-display"><span class="katex"><span class="katex-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><mrow><mn mathvariant="italic">0</mn><mo>≤</mo><mi>r</mi><mo>≤</mo><mtext>W</mtext><mo>×</mo><mtext>H</mtext></mrow><annotation encoding="application/x-tex"> \it 0 \leq r \leq \text W \times \text H </annotation></semantics></math></span><span class="katex-html" aria-hidden="true"><span class="base"><span class="strut" style="height:0.8193em;vertical-align:-0.13597em;"></span><span class="mord"><span class="mord mathit">0</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">≤</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mord mathit">r</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">≤</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mord text"><span class="mord">W</span></span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mbin">×</span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mord text"><span class="mord">H</span></span></span></span></span></span></span> <span class="katex-display"><span class="katex"><span class="katex-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><mrow><mi>x</mi><mo>=</mo><mi>r</mi><mtext> </mtext><mo lspace="0.22em" rspace="0.22em"><mrow><mi mathvariant="normal">m</mi><mi mathvariant="normal">o</mi><mi mathvariant="normal">d</mi></mrow></mo><mtext> </mtext><mtext>W</mtext></mrow><annotation encoding="application/x-tex"> \it x = r \bmod \text W </annotation></semantics></math></span><span class="katex-html" aria-hidden="true"><span class="base"><span class="strut" style="height:0.69444em;vertical-align:0em;"></span><span class="mord"><span class="mord mathit">x</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">=</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mord mathit">r</span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mspace" style="margin-right:0.05555555555555555em;"></span><span class="mbin"><span class="mord"><span class="mord mathrm">m</span><span class="mord mathrm">o</span><span class="mord mathrm">d</span></span></span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mspace" style="margin-right:0.05555555555555555em;"></span><span class="mord text"><span class="mord">W</span></span></span></span></span></span></span> <span class="katex-display"><span class="katex"><span class="katex-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><mrow><mi>y</mi><mo>=</mo><mrow><mo fence="true">⌊</mo><mfrac><mi>r</mi><mtext>H</mtext></mfrac><mo fence="true">⌋</mo></mrow></mrow><annotation encoding="application/x-tex"> \it y = \left\lfloor\frac{r}{\text H}\right\rfloor </annotation></semantics></math></span><span class="katex-html" aria-hidden="true"><span class="base"><span class="strut" style="height:1.8359999999999999em;vertical-align:-0.686em;"></span><span class="mord"><span class="mord mathit">y</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">=</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="minner"><span class="mopen delimcenter" style="top:0em;"><span class="delimsizing size2">⌊</span></span><span class="mord"><span class="mopen nulldelimiter"></span><span class="mfrac"><span class="vlist-t vlist-t2"><span class="vlist-r"><span class="vlist" style="height:1.10756em;"><span style="top:-2.314em;"><span class="pstrut" style="height:3em;"></span><span class="mord"><span class="mord text"><span class="mord">H</span></span></span></span><span style="top:-3.23em;"><span class="pstrut" style="height:3em;"></span><span class="frac-line" style="border-bottom-width:0.04em;"></span></span><span style="top:-3.677em;"><span class="pstrut" style="height:3em;"></span><span class="mord"><span class="mord mathit">r</span></span></span></span><span class="vlist-s">​</span></span><span class="vlist-r"><span class="vlist" style="height:0.686em;"><span></span></span></span></span></span><span class="mclose nulldelimiter"></span></span><span class="mclose delimcenter" style="top:0em;"><span class="delimsizing size2">⌋</span></span></span></span></span></span></span></span></p> <p>The code equivalent to this in Python is below:</p> <div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kn">import</span> <span class="nn">random</span> <span class="c1"># r &lt;= 0 &lt;= W*H </span><span class="n">r</span> <span class="o">=</span> <span class="n">random</span><span class="p">.</span><span class="n">randint</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">W</span><span class="o">*</span><span class="n">H</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span> <span class="c1"># x = r mod W </span><span class="n">x</span> <span class="o">=</span> <span class="n">r</span> <span class="o">%</span> <span class="n">W</span> <span class="c1"># y = floor(r/H); note the special syntax python has for this operation </span><span class="n">y</span> <span class="o">=</span> <span class="n">r</span> <span class="o">//</span> <span class="n">H</span> </code></pre></div></div> <p>So that’s that, we can put this in a big ‘ol for loop and generate an arbitrary <em>n</em> number of bombs given a width and height of a Minesweeper board.</p> <h2 id="cascading-tile-revealing">Cascading Tile Revealing</h2> <p>This one is hard to describe; I am adapting this from <a href="https://leetcode.com/problems/minesweeper/">leetcode.com</a>. Whenever a player clicks a tile, the following logic should be used:</p> <ol> <li>If a mine is revealed, the game is over. (obviously)</li> <li>If a tile with <em>no</em> adjacent mines is revealed, recursively reveal all eight adjacent tiles.</li> <li>If a tile with one or more adjacent mines is revealed, display the number of mines next to it.</li> </ol> <p>Here is the code in Python for this algorithm.</p> <div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">def</span> <span class="nf">reveal_square</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">board</span><span class="p">,</span> <span class="n">alread_revealed</span><span class="p">):</span> <span class="c1"># if already checked </span> <span class="k">if</span> <span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">)</span> <span class="ow">in</span> <span class="n">already_revealed</span><span class="p">:</span> <span class="k">return</span> <span class="c1"># if it's a bomb </span> <span class="k">if</span> <span class="n">board</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">]</span> <span class="o">==</span> <span class="s">'B'</span><span class="p">:</span> <span class="n">you_lose</span><span class="p">()</span> <span class="k">return</span> <span class="c1"># if the bomb number is more than 0 </span> <span class="n">already_revealed</span><span class="p">.</span><span class="n">append</span><span class="p">((</span><span class="n">nx</span><span class="p">,</span> <span class="n">ny</span><span class="p">))</span> <span class="c1"># from -1 to 1 </span> <span class="k">for</span> <span class="n">xd</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">):</span> <span class="k">for</span> <span class="n">yd</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">):</span> <span class="c1"># skip if it is this the center tile </span> <span class="k">if</span> <span class="n">x</span><span class="o">+</span><span class="n">xd</span> <span class="o">==</span> <span class="n">x</span> <span class="ow">and</span> <span class="n">y</span><span class="o">+</span><span class="n">yd</span> <span class="o">==</span> <span class="n">y</span><span class="p">:</span> <span class="k">continue</span> <span class="c1"># recursively check the adjacent square </span> <span class="n">reveal</span><span class="p">(</span><span class="n">x</span><span class="o">+</span><span class="n">xd</span><span class="p">,</span> <span class="n">y</span><span class="o">+</span><span class="n">yd</span><span class="p">,</span> <span class="n">board</span><span class="p">,</span> <span class="n">already_revealed</span><span class="p">)</span> <span class="k">return</span> <span class="n">already_revealed</span> </code></pre></div></div> <p>This has no checks for valid squares, but it’s the general idea. This function returns an array of tile coordinates which should be revealed.</p> <h2 id="conclusion">Conclusion</h2> <p>I wrote this because in the first place because I was writing my own Minesweeper game. I hope that this helps you with getting the general idea of a Minesweeper game. The completed version of this game is available on my <a href="https://lamegames.tait.tech/">lamegames</a> site. Let me know what you think!</p> <p>Happy hacking!</p>When I was creating a little Minesweeper game, I got confused at some points. My bomb generation didn’t look quite right, and I for sure didn’t quite get the whole cascading tile reveal thing. With a bit of internet research, I found what I was looking for. I’ll explain it all in one place for my own research purposes.lamegames.tait.tech2020-09-09T00:00:00-06:002020-09-09T00:00:00-06:00/2020/09/09/lamegames<p>This is an announcement for a new project of mine: <a href="https://lamegames.tait.tech">lamegames.tait.tech</a>.</p> <p>This is something I’m really excited to work on!</p> <p>Right now, I’ve just got a rock-paper-scissors game. A chat function, and a few simple card games to come.</p> <p>Check out the repository on my <a href="https://github.com/TTWNO/lamegames.io">Github</a>.</p>This is an announcement for a new project of mine: lamegames.tait.tech.How to Solve The Django Deployment Puzzle2020-08-18T00:00:00-06:002020-08-18T00:00:00-06:00/2020/08/18/django-deployment<p>A few days ago I had a Django project I wanted to put on a real server. This project is still in its infancy, but I thought it would be nice to put it on my resume and show my friends. Little did I know the headache coming my way. Here are some tips to help you not make the same mistakes as me.</p> <h3 id="asgi-servers">ASGI Servers</h3> <p>Because my project used the ASGI (Asynchronous webServer Gateway Interface), I needed to find a good production ASGI server to handle all the incoming requests. The best thing I found was <a href="http://www.uvicorn.org/">uvicorn</a>. It focuses on speed, which is a priority, especially when using the ASGI protocol.</p> <p>To run uvicorn on the command line for testing purposes, use something like the following:</p> <pre class="terminal"> $ uvicorn --reload myapp.asgi:application </pre> <p>The <code class="language-plaintext highlighter-rouge">--reload</code> option says to reload the server if any of the files get updated. This is not recommended in production. Sadly, I thought this meant I would need to do a hard shutdown of the server process every time I wanted to update. This turned out to not be the case.</p> <h3 id="workload-managers">Workload Managers</h3> <p>There is another equine-named program called <a href="https://gunicorn.org/">gunicorn</a> which can hold a number of processes under its control. An interesting feature of <code class="language-plaintext highlighter-rouge">gunicorn</code> is that it will gracefully switch from an old to a new deployment, replacing the subprocesses one-by-one and eventually having only the new deployment active on all subprocesses. The greatest part? Zero down time. The server keeps any old processes open if there is communication with them, then shift and new connections to the new deployment. This was a very cool feature I wanted to take advantage of.</p> <p>“Now hold on!” you might protest. “gunicorn is a WSGI server!” … oh you got me there! Yes, that’s right, <code class="language-plaintext highlighter-rouge">gunicorn</code> is paired with <code class="language-plaintext highlighter-rouge">uvicorn</code> to serve my files.</p> <h3 id="systemd">systemd</h3> <p>Love it or hate it, the majority of Linux distributions use the <code class="language-plaintext highlighter-rouge">systemd</code> init system. I decided it would be very convenient to have a .service file for my Django application to run automatically at boot. <code class="language-plaintext highlighter-rouge">Systemd</code> allows me to do this with a file like the following one I stored in <code class="language-plaintext highlighter-rouge">/lib/systemd/system/lamegames.service</code>.</p> <pre class="file"> [Unit] Description=Gunicorn/Uvicorn (lamegames.io) [Service] WorkingDirectory=/home/lame/lamegames.io Type=simple RemainAfterExit=yes ExecStart=/home/lame/lamegames.io/env/bin/gunicorn lamegames.asgi:application -w 2 -k uvicorn.workers.UvicornWorker ExecStop=/bin/kill -HUP $MAINPID Restart=always [Install] WantedBy=multi-user.target </pre> <h3 id="nginx">nginx</h3> <p>NGINX (pronounced engine-X) is a performance web server designed for speed and simplicity. For the front facing side of the site, I do need a production web server like nginx. Gunicorn simply doesn’t need all the features that nginx provides, but I do. To configure my nginx installation, I used the following few directives to:</p> <ol> <li>Redirect most traffic towards the gunicorn server.</li> <li>Redirect statically served files (CSS, JS, images) to the directory specified in the STATIC_ROOT variable of my <code class="language-plaintext highlighter-rouge">settings.py</code> file.</li> <li>Use TLS to enable https://</li> </ol> <p>Serving the static files from nginx as opposed to the <code class="language-plaintext highlighter-rouge">gunicorn</code> server is necessary. Gunicorn and other production A/WSGI web server will not set the proper MIME type over TLS. This will cause your browser to not load the Javascript/CSS.</p> <p>This is the important part of my nginx config.</p> <pre class="file"> server { location / { proxy_set_header Host $http_host; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; # these two lines ensure that WebSocket, and HTTP2 connection are forwarded correctly proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "Upgrade"; proxy_redirect off; proxy_buffering off; # this forwards all traffic to the local server on port 8000 proxy_pass http://localhost:8000; } # This forwards all static requests to Django's STATIC_ROOT set in settings.py; it is generated using the collectstatic command. location /static { autoindex on; alias /home/lame/lamegames.io/static_generated; } } </pre> <h3 id="setup">Setup</h3> <p>After all that, I was able to do the following:</p> <pre class="terminal"> # systemctl enable lamegames </pre> <p>This enabled my <code class="language-plaintext highlighter-rouge">gunicorn</code> server to run once the server started. NGINX is that way be default.</p> <p>And tada! You now have a working Django project on a production server!</p> <h4 id="notes">Notes</h4> <ul> <li>If using ws:// websockets, change them to wss:// for secure web sockets.</li> <li>Make sure to use channels.routing.get_default_application() instead of django.get_asgi_application() if your’re wanting to use channels/redis WebSockets.</li> </ul>A few days ago I had a Django project I wanted to put on a real server. This project is still in its infancy, but I thought it would be nice to put it on my resume and show my friends. Little did I know the headache coming my way. Here are some tips to help you not make the same mistakes as me.BSD Journey, Part 12020-08-15T00:00:00-06:002020-08-15T00:00:00-06:00/2020/08/15/openbsd1<p>As Linux becomes controlled by corporate sponsors and becomes more full of proprietary blobs, drivers, and even closed-source software like Steam, One may wonder if there are other options out there. For me, somebody that is intensely interested in security, there is one option: OpenBSD.</p> <p>Now, my interest in OpenBSD has been going on for a long time. I started poking around for Linux alternatives way back a few years ago when Linus Torvalds decided to leave after he got in trouble for some <a href="https://arstechnica.com/information-technology/2013/07/linus-torvalds-defends-his-right-to-shame-linux-kernel-developers/">unprofessional behaviour</a>. That said, Linus did come back to Linux development, but I knew that his abrasive style is what brought good code to the Linux kernel. I also knew that his ability to be critical would be hurt by the new <a href="https://itsfoss.com/linux-code-of-conduct/">code of conduct</a>. It would become a tool for the SJW types to hammer on Linus for being a “white male, et al.”; It would become a tool for the easily offended to use to get their dumb code into Linux; It would become a tool for the corporatization, the HR-ification of Linux. Frankly, this does not interest me.</p> <p>Now I’m sure that OpenBSD has its own internal policies that I disagree with. That said, Theo De Raadt is still at least known for calling Firefox an “amorphous peace of garbage” due to its lack of privilege separation. And, in their <a href="https://openbsd.org/goals.html">project goals</a> page, they specifically mention:</p> <blockquote> <p>Be as politics-free as possible; solutions should be decided on the basis of technical merit.</p> </blockquote> <p>Now that’s something I can get behind! Bet you that’s not in the Linux COC?</p> <p>He also went to university in my hometown, so that’s pretty cool! I can support a local madman who thinks he can make a better operating system than all those corporations. Maybe he was right, maybe not. What I know is I am excited to find out!</p> <p>Wish my luck on my OpenBSD journey. I will post updates here along the way.</p> <p>Happy hacking!</p>As Linux becomes controlled by corporate sponsors and becomes more full of proprietary blobs, drivers, and even closed-source software like Steam, One may wonder if there are other options out there. For me, somebody that is intensely interested in security, there is one option: OpenBSD.Know How Your Representative Votes In Parliament2020-07-30T00:00:00-06:002020-07-30T00:00:00-06:00/2020/07/30/canadian-parliament<p>As an advocate for openness, I had an idea to make a project out of the government of Canada’s <a href="https://open.canada.ca/en/open-data">Open Data</a> initiative to take a look at how my local MP voted on various pieces of legislation. It turns out though that this was not necessary due to how easy it was to find this information on the government’s own website. In this article, I will explain how you can do the same.</p> <h3 id="1-find-your-representative">1. Find Your Representative</h3> <p>The first step in this process is to find who your representative is. To do so, go to the government’s own website <a href="https://www.ourcommons.ca/Members/en">ourcommons.ca’s search tool</a>.</p> <p>Simply type in your postal code in the search box to find out who your MP is.</p> <h3 id="2-their-voting-record">2. Their Voting Record</h3> <p>Every MP’s voting record is public knowledge, and it is available nice and simple in a table on that MP’s page. For example, this is a link to <a href="https://www.ourcommons.ca/Members/en/pierre-poilievre(25524)/votes">Pierre Poilievre’s voting record</a>.</p> <p>To find your MP’s voting record, do step one, then: After the <strong>Overview</strong>, and <strong>Seat in The House</strong> sections, there are three tabs, <strong>Roles</strong>, <strong>Work</strong>, and <strong>Contact</strong>. Click on work. At the bottom of that tab is a link which says <strong>Chamber Votes</strong>. This will open a small window with some recent votes by this politician. If you want to see all their votes, there is a button at the bottom named <strong>All Votes by This Member</strong>.</p> <p>Tada! You can now keep your local MP accountable for anything you do or do not support.</p> <h3 id="3-bill-details">3. Bill Details</h3> <p>If you want to get into the nitty gritty, once you open a specific bill, you can actually find out the status of said bill, or read the actual text by clicking the <strong>View this Bill on LEGISinfo</strong> button.</p> <p>Both the status of the bill, and a link to a PDF document containing the bilingual text of the bill are visible in the main body of the page.</p> <h4 id="conclusion">Conclusion</h4> <p>I thought this was pretty cool! It was <em>way</em> simpler than I thought it would be.</p> <p>Thanks, Canada!</p>As an advocate for openness, I had an idea to make a project out of the government of Canada’s Open Data initiative to take a look at how my local MP voted on various pieces of legislation. It turns out though that this was not necessary due to how easy it was to find this information on the government’s own website. In this article, I will explain how you can do the same.Installing MultiCraft on Gentoo Linux2020-07-19T00:00:00-06:002020-07-19T00:00:00-06:00/2020/07/19/multicraft-php-gentoo<p>In a very odd combination of requirements, I needed to install <a href="https://multicraft.org">MultiCraft</a> on a Gentoo Linux system. The PHP <code class="language-plaintext highlighter-rouge">USE</code> flags are important so you don’t have to recompile it three times like I did.</p> <p>Here are some useful tips I came across:</p> <h3 id="php-use-flags">PHP <code class="language-plaintext highlighter-rouge">USE</code> flags</h3> <p>In <code class="language-plaintext highlighter-rouge">/etc/portage/package.use/php</code> I placed the following line:</p> <pre class="terminal"> dev-lang/php cgi mysql mysqli fpm pdo gd truetype </pre> <p>This should give you enough for a mysql backended MultiCraft installation. The <code class="language-plaintext highlighter-rouge">cgi</code> option may not be required as <code class="language-plaintext highlighter-rouge">fpm</code> stands for <em>FastCGI Process Managment</em>. I don’t know for sure though.</p> <h3 id="paper">Paper</h3> <p>This will grab the latest version of the Paper jar file using <a href="https://yivesmirror.com">YivesMirror</a>. I’m not sure how reputable it is, but my buddy who works with this stuff more often than me seemed to recognize it.</p> <pre class="terminal"> ## See the default craftbukkit.jar.conf for a detailed documentation of the ## format of this file. [config] name = Paper 1.16.1 Latest source = https://yivesmirror.com/files/paper/Paper-1.16.1-latest.jar category = Mods [encoding] #encode = system #decode = system #fileEncoding = latin-1 [start] command = "{JAVA}" -Xmx{MAX_MEMORY}M -Xms{START_MEMORY}M -XX:MaxPermSize=128M -Djline.terminal=jline.UnsupportedTerminal -jar "{JAR}" nogui </pre> <h3 id="other-tips">Other Tips</h3> <p>Do not use the option to setup a separate user for each server. This completely stalled any work getting done with a ton of ‘permission denied’ errors.</p> <h4 id="security">Security</h4> <p>If the panel is in the root directory of your NGINX web server, use the following in your server block to deny access to the <code class="language-plaintext highlighter-rouge">/protected</code> directory.</p> <pre class="terminal"> location /protected { deny all; return 404; } </pre> <h5 id="mysql">MySQL</h5> <p>It is always good practice to separate privileges. The MultiCraft daemon should have one SQL login, with one database allocated to it. The MultiCraft panel should have a separate SQL login, with a separate database allocated to it.</p> <p>You can do this with the following commands in your MySQL prompt:</p> <pre class="terminal"> sql&gt; CREATE DATABASE multicraft_daemon_database; Query OK, 0 rows affected (0.01 sec) sql&gt; CREATE DATABASE multicraft_panel_database; Query OK, 0 rows affected (0.01 sec) sql&gt; CREATE USER 'muilticraft_daemon'@'localhost' IDENTIFIED BY 'strong password here'; Query OK, 0 rows affected (0.01 sec) sql&gt; CREATE USER 'multicraft_panel'@'localhost' IDENTIFIED BY 'different strong password here'; Query OK, 0 rows affected (0.01 sec) sql&gt; GRANT ALL PRIVILEGES ON multicraft_daemon_database . * TO 'multicraft_daemon'@'localhost'; Query OK, 0 rows affected (0.01 sec) sql&gt; GRANT ALL PRIVILEGES ON multicraft_panel_database . * TO 'mutlicraft_panel'@'localhost'; Query OK, 0 rows affected (0.01 sec) </pre> <p>During setup, make sure the proper credentials are used for each step. Database 1 is the panel database. Database 2 is the daemon database.</p> <p>Happy hacking :)</p>In a very odd combination of requirements, I needed to install MultiCraft on a Gentoo Linux system. The PHP USE flags are important so you don’t have to recompile it three times like I did.Independence2020-07-12T00:00:00-06:002020-07-12T00:00:00-06:00/2020/07/12/independence<blockquote> <p>“When given a choice between independence and dependence, always choose independence; you will never regret that choice!”—Luke Smith</p> </blockquote> <p>Whatever you may believe about the YouTube personality Luke Smith, the quote above summarizes a core principle of mine. Much like many people have religious principles, I have <em>Independence</em>.</p> <p>My choice to use Linux as my primary operating system, host my own website, own my own domain name—all of these are directly related to this core principle of independence.</p> <p>I never want a man, or a company to have too much power over my life. Just like I would not trust just any person to be able to read my emails, know where I live, where I am going, who are my friends, what do I believe; in the same way, I do not trust a company with that same information.</p> <blockquote> <p>“If you want to find out what a man is to the bottom, give him power. Any man can stand adversity — only a great man can stand prosperity.”—Robert Ingersoll</p> </blockquote> <p>Take control of your own digital life:</p> <ol> <li>Own your own domain.</li> <li>Hookup an email and a website to that.</li> </ol> <p>That’s it!</p> <p>Without this, any of your internet privileges can be revoked at any time by Google, Facebook, YouTube, Twitter, or even an angry Twitter Mob. Maybe because they hate your skin colour, maybe they hate your religious/political views, or maybe you got caught on a technicality.</p> <p>If you own your own domain, however:</p> <p>Your email provider goes down/bans you: change your provider; keep the email.</p> <p>Your website is pulled for controversial views: switch hosts.</p> <p>Protect yourself; give yourself choices. Why give others that power when you could have it for yourself?</p>“When given a choice between independence and dependence, always choose independence; you will never regret that choice!”—Luke Smith \ No newline at end of file +Jekyll2020-12-14T11:19:49-07:00/feed.xmlGetting Pacaur Working on a Raspberry Pi 4 with Manjaro ARM or Arch Linux2020-12-01T00:00:00-07:002020-12-01T00:00:00-07:00/2020/12/01/pacaur-rpi<p>I recently installed Manjaro ARM (based on Arch Linux ARM) on a Raspberry Pi 4. I used some standard commands to start to add the <code class="language-plaintext highlighter-rouge">pacaur</code> package so I can easily retrieve <a href="https://wiki.archlinux.org/index.php/Arch_User_Repository">AUR packages</a> without needing to do it manually. Unfortunately, there is a small problem with compiling this on ARM.</p> <h2 id="always_inline">always_inline</h2> <p>To setup the install for <code class="language-plaintext highlighter-rouge">pacaur</code>, I first needed to download <a href="https://aur.archlinux.org/packages/auracle-git">auracle-git</a> AUR package manually. I ran into an error when compiling this package.</p> <p>But first, my setup:</p> <pre class="terminal"> $ git clone https://aur.archlinux.org/auracle-git $ cd auracle-git $ makepkg -sri </pre> <p>Around half way through compiling this project, I got this cryptic message telling me there was a “target specific option mismatch”…Whatever that means. The full error is below, hopefully that helps my chances on the search engines.</p> <pre class="terminal"> In file included from ../subprojects/abseil-cpp-20200225.2/absl/random/internal/randen_hwaes.cc:225: /usr/lib/gcc/aarch64-unknown-linux-gnu/9.3.0/include/arm_neon.h: In function 'Vector128 {anonymous}::AesRound(const Vector128&amp;, const Vector128&amp;)': /usr/lib/gcc/aarch64-unknown-linux-gnu/9.3.0/include/arm_neon.h:12452:1: error: inlining failed in call to always_inline 'uint8x16_t vaesmcq_u8(uint8x16_t)': target specific option mismatch 12452 | vaesmcq_u8 (uint8x16_t data) </pre> <p>Luckily, there is a very easy fix for this. The user redfish <a href="https://aur.archlinux.org/packages/auracle-git#comment-762117">helpfully pointed out</a> on the <code class="language-plaintext highlighter-rouge">auracle-git</code> package page that you need to add a special make option to your <code class="language-plaintext highlighter-rouge">/etc/make.conf</code> file to make this work.</p> <p>His solution, as commented is like so:</p> <blockquote> <p>If you get this error when building for ARM aarch64:</p> <p>(insert error message from before)</p> <p>Then check that in /etc/makepkg.conf CFLAGS and CXXFLAGS have the +crypto suffix in -march flag, like -march=armv8-a+crypto (the base identifier may very depending on your hardware)</p> </blockquote> <p>Basically, there is a file on Linux: <code class="language-plaintext highlighter-rouge">/etc/makepkg.conf</code> which tells your computer how to compile <em>all</em> programs on the system. By default the Manjaro ARM (RPi4) edition has the following relevant lines in <code class="language-plaintext highlighter-rouge">makepkg.conf</code>.</p> <pre class="file"> CFLAGS="-march=armv8-a -O2 -pipe -fstack-protector-strong -fno-plt" CXXFLAGS="-march=armv8-a -O2 -pipe -fstack-protector-strong -fno-plt" </pre> <p>What Mr. redfish is telling us is that we must add ‘+crypto’ to the end of the -march compiler flag so that our compiler will know how to inline that pesky vaesmcq_u8 function.</p> <p>So in the end, your <code class="language-plaintext highlighter-rouge">makepkg.conf</code>’s relevant lines will look like so:</p> <pre class="file"> CFLAGS="-march=armv8-a+crypto -O2 -pipe -fstack-protector-strong -fno-plt" CXXFLAGS="-march=armv8-a+crypto -O2 -pipe -fstack-protector-strong -fno-plt" </pre> <h2 id="why">Why?</h2> <p>Redfish continues:</p> <blockquote> <p>Build of abseil-cpp package works because it uses CMake which adds the correct -march flag regardless of makepkg.conf, whereas when abseil-cpp is build as a subproject within this package, it uses meson, which does not add the flag and thus fails with the above error.</p> </blockquote> <p>In other words, one of the dependencies pulled in with auracle is not compiling without this special compiler flag enabled.</p> <h2 id="conclusion">Conclusion</h2> <p>Thanks to redfish for posting this solution to the forums! Would’ve been quite the rabbit hole for me to figure out how to do that. In fact, it is very likely I would have never figured that one out.</p> <p>After this issue is resolved, the installation of <code class="language-plaintext highlighter-rouge">pacaur</code> goes as expected. Nice and easy! Pacuar will compile on any architecture so it’s smooth sailing from here.</p> <p>Happy hacking!</p>I recently installed Manjaro ARM (based on Arch Linux ARM) on a Raspberry Pi 4. I used some standard commands to start to add the pacaur package so I can easily retrieve AUR packages without needing to do it manually. Unfortunately, there is a small problem with compiling this on ARM.ZFS NAS Box, Part 22020-11-15T00:00:00-07:002020-11-15T00:00:00-07:00/2020/11/15/nas2<p>Back in <a href="/2020/04/12/nas1/">part one of my NAS project</a> I discussed how I wanted to set up my hardware. Today, I set up the NAS (almost).</p> <p>There were some hiccup along the way, like learning that M.2 slots can disable some of your SATA ports or waiting a month for a host bus adapter to come in from China.</p> <h2 id="why-did-it-take-so-long">Why Did It Take So Long</h2> <p>So it turns out I was going to spend a lot more on this project than I originally anticipated. I ended up getting a server machine instead of a sleek NAS box. Here are some of the quick specs:</p> <ul> <li>Standard ATX case by Thermaltake.</li> <li>LSI 9211-8i.</li> <li>The cheapest HDMI graphics card I could find on Kijiji.</li> <li>6x 3TB Segate HDDs.</li> <li>1x 250G Kingston SSD.</li> <li>AMD Ryzen 5 3600.</li> <li>MSI B450 Gaming Plus Max.</li> <li>2x 8GB FlareX 3200Mhz RAM.</li> <li>1x 16GB Kingston 3200Mhz RAM.</li> </ul> <h2 id="zfs">ZFS</h2> <p>This is how I decided to configure my storage pools. In hindsight, this was not the best choice for upgrading. I may change it in the future to a 0+1 setup, but it works for now.</p> <p>I have 5x 3TB in a RAIDZ2 with one drive not attached for redundancy’s sake. How does one setup a ZFS pool. Check this out:</p> <pre class="terminal"> # zpool create poolname raidz2 \ /dev/by-id/blahblahblah1 \ /dev/by-id/blahblahblah2 \ /dev/by-id/blahblahblah3 \ /dev/by-id/blahblahblah4 \ /dev/by-id/blahblahblah5 </pre> <p>And zippidy-doo! We’ve got a ZFS pool! We can check its status with <code class="language-plaintext highlighter-rouge">zpool status</code>.</p> <pre class="terminal"> $ zfs status pool: raid state: ONLINE scan: scrub in progress since Wed Nov 18 18:41:41 2020 1.84T scanned at 8.51G/s, 121G issued at 562M/s, 1.84T total 0B repaired, 6.45% done, 0 days 00:53:25 to go config: NAME STATE READ WRITE CKSUM raid ONLINE 0 0 0 raidz2-0 ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JTNMYY ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JVSXTY ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JXAS8Y ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JXBARY ONLINE 0 0 0 ata-HGST_HUS724030ALA640_PN2234P8JXP77Y ONLINE 0 0 0 errors: No known data errors </pre> <p>I had run a scrub right before this, so there’s some extra detail in that. This is really fun! I will be doing more home storage projects soon. Perhaps Raspberry Pi NAS using all 4 USB ports to load SATA drives on it. Now that would be fun!</p> <h2 id="so-i-kinda-have-a-nas-now">So I Kinda Have A NAS Now…?</h2> <p>So right now I can only copy files with <code class="language-plaintext highlighter-rouge">rsync</code>, <code class="language-plaintext highlighter-rouge">scp</code> and moving data via a physical drive. The one major disadvantage this has is speed.</p> <p>Due to this machine being connected directly outside my network and pulling DHCP like a normal router would, I need to send my data through the WAN connection to get my files to it. This is rather unfortunate as my upload speed is capped at 20 megabits per second, despite my upload being in the 300+ range.</p> <p>Part 3 will involve a LAN card so I can connect both to the DHCP server of my ISP and my local router. This way my transfer speeds should be in the range of 1 gigabit per second. This will make my life much easier, at least on the local network.</p> <h2 id="fun-fact">Fun Fact!</h2> <p>Do not try to use the M.2 slot on a consumer motherboard where you are also using all the SATA ports. On my consumer gaming motherboard, the SATA ports next to the M.2 slot became <em>disabled</em> when I attached the M.2 SSD. I found this out form my motherboard documentation, which I read only after a week of thinking my motherboard itself was defective, and sending it in for repairs that did absolutely nothing.</p> <h2 id="thoughts">Thoughts</h2> <p>I like having all this space. I plan on using it up pretty fast, so I’m already looking at how to expand. Hopefully that gives a decent overview of how I set up my drives.</p> <p>Happy hacking!</p>Back in part one of my NAS project I discussed how I wanted to set up my hardware. Today, I set up the NAS (almost).Curiosity2020-10-26T00:00:00-06:002020-10-26T00:00:00-06:00/2020/10/26/curiosity<p>Curiosity is fundamental to a deep understanding of any subject. Masters, Ph.Ds, and other fancy name suffixes will never help you if you don’t have the spirit of curiosity burning inside of you.</p> <p>I was speaking to someone from a journalism major at my school when the subject of hacking arose. I expected her to know nothing about it, being a journalism student and all, but surprisingly she had something to say about it:</p> <blockquote> <p>“The best hackers are the ones who are curious.”</p> </blockquote> <p>That struck a cord with me. It seems to me she has nailed down the difference between the students who care about grades, and those who want to learn. These are not necessarily mutually exclusive, but in my experience they often are due to the way education is structured.</p> <h2 id="my-anecdote">My Anecdote</h2> <p>In my second semester at SAIT Polytechnic, I took a class entitled <em>Emerging Trends In Technology</em>. This class was probably the best class I have ever taken. We had to combine two things:</p> <ul> <li><strong>Hard skills</strong>: learning a new hard skill like Angular, Django, or GPG encryption.</li> <li><strong>Soft skills</strong>: public speaking and presentation of our ideas.</li> </ul> <p>Soft skills are not usually my area, but I can do public speaking. I grew up quite religious, so public speaking was drilled into me young. I liked to go off script and talk about interesting things I found along the way to the actual point. My creativity was not usually encouraged. That said, going off script is useful when teaching and presenting ideas; it gives a natural air to your breath and an unquestionable confidence in your speech.</p> <p>This is how we learn: in relationships. Try explaining ancient Japanese history to a computer science major, or UNIX sockets to an English major and you’ll see what I mean. If there is nothing for us to connect the knowledge to, it dissipates.</p> <p>So why did I do so well in this class?</p> <p>Our task for the semester was as follows:</p> <ol> <li>Learn a new subject (any <em>emerging trend in technology</em>) which you find fascinating.</li> <li>Give a one minute introduction by week three.</li> <li>Give a 10 minute non-technical overview by week 8.</li> <li>Give a 20 minute technical explaination and demo by week 13.</li> </ol> <p>This is the only course I have ever taken which lets students’ imagination run wild. Their presentation, their rules. They treated the students like adults who know what they are doing. What happened? Everyone stopped coming because “Oh no! Presentations!”?</p> <p>No, exactly the opposite. There was never more than one student missing. Every single presentation was at least moderately interesting, and most students were excited to come to that class. You could see it in their faces, the way they carried themselves. Every student picked something unique to their tastes, leaving every student more educated than before.</p> <p>This class, unlike many others, encouraged the curiosity of the students. It rewarded those who had unique interests and an ability to sell others on their ideas.</p> <p>The curiosity and the grades were one.</p> <h2 id="conclusion">Conclusion</h2> <p>Although it’s nice to have a course where these goals align here and there, anyone who has been to collage or university can tell you that is far from the norm.</p> <p>On the other hand, I never would have started this site if it wasn’t for that class alone. So I thank you, Kitty Wong, for getting me started running my own “research blog” (?)</p>Curiosity is fundamental to a deep understanding of any subject. Masters, Ph.Ds, and other fancy name suffixes will never help you if you don’t have the spirit of curiosity burning inside of you.Minesweeper Bomb Generation And Tile Revealing2020-09-12T00:00:00-06:002020-09-12T00:00:00-06:00/2020/09/12/minesweeper<p>When I was creating a little Minesweeper game, I got confused at some points. My bomb generation didn’t look quite right, and I for sure didn’t quite get the whole cascading tile reveal thing. With a bit of internet research, I found what I was looking for. I’ll explain it all in one place for my own research purposes.</p> <h2 id="bomb-generation">Bomb Generation</h2> <p>When I started this project I attempted to use a random bomb generator. By this I mean on each square, before it gets generated, give it a one in 15 change of being a bomb. Personally, I’m not sure why this never looked right. Something about the layout of the bombs did not mimic the classic Minesweeper game.</p> <p>After looking at some open source Minesweeper examples, I started to get the idea. I wrote some mathematical statements describing the generation of bombs and how to get their x,y position from an appropriate number. For those non-mathy people, don’t leave just yet; there will be code equivalents to the math.</p> <p>W and H are the width and height of the board respectively.</p> <p><span class="katex-display"><span class="katex"><span class="katex-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><mrow><mn mathvariant="italic">0</mn><mo>≤</mo><mi>r</mi><mo>≤</mo><mtext>W</mtext><mo>×</mo><mtext>H</mtext></mrow><annotation encoding="application/x-tex"> \it 0 \leq r \leq \text W \times \text H </annotation></semantics></math></span><span class="katex-html" aria-hidden="true"><span class="base"><span class="strut" style="height:0.8193em;vertical-align:-0.13597em;"></span><span class="mord"><span class="mord mathit">0</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">≤</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mord mathit">r</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">≤</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mord text"><span class="mord">W</span></span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mbin">×</span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mord text"><span class="mord">H</span></span></span></span></span></span></span> <span class="katex-display"><span class="katex"><span class="katex-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><mrow><mi>x</mi><mo>=</mo><mi>r</mi><mtext> </mtext><mo lspace="0.22em" rspace="0.22em"><mrow><mi mathvariant="normal">m</mi><mi mathvariant="normal">o</mi><mi mathvariant="normal">d</mi></mrow></mo><mtext> </mtext><mtext>W</mtext></mrow><annotation encoding="application/x-tex"> \it x = r \bmod \text W </annotation></semantics></math></span><span class="katex-html" aria-hidden="true"><span class="base"><span class="strut" style="height:0.69444em;vertical-align:0em;"></span><span class="mord"><span class="mord mathit">x</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">=</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mord mathit">r</span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mspace" style="margin-right:0.05555555555555555em;"></span><span class="mbin"><span class="mord"><span class="mord mathrm">m</span><span class="mord mathrm">o</span><span class="mord mathrm">d</span></span></span><span class="mspace" style="margin-right:0.2222222222222222em;"></span><span class="mspace" style="margin-right:0.05555555555555555em;"></span><span class="mord text"><span class="mord">W</span></span></span></span></span></span></span> <span class="katex-display"><span class="katex"><span class="katex-mathml"><math xmlns="http://www.w3.org/1998/Math/MathML"><semantics><mrow><mi>y</mi><mo>=</mo><mrow><mo fence="true">⌊</mo><mfrac><mi>r</mi><mtext>H</mtext></mfrac><mo fence="true">⌋</mo></mrow></mrow><annotation encoding="application/x-tex"> \it y = \left\lfloor\frac{r}{\text H}\right\rfloor </annotation></semantics></math></span><span class="katex-html" aria-hidden="true"><span class="base"><span class="strut" style="height:1.8359999999999999em;vertical-align:-0.686em;"></span><span class="mord"><span class="mord mathit">y</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="mrel">=</span><span class="mspace" style="margin-right:0.2777777777777778em;"></span><span class="minner"><span class="mopen delimcenter" style="top:0em;"><span class="delimsizing size2">⌊</span></span><span class="mord"><span class="mopen nulldelimiter"></span><span class="mfrac"><span class="vlist-t vlist-t2"><span class="vlist-r"><span class="vlist" style="height:1.10756em;"><span style="top:-2.314em;"><span class="pstrut" style="height:3em;"></span><span class="mord"><span class="mord text"><span class="mord">H</span></span></span></span><span style="top:-3.23em;"><span class="pstrut" style="height:3em;"></span><span class="frac-line" style="border-bottom-width:0.04em;"></span></span><span style="top:-3.677em;"><span class="pstrut" style="height:3em;"></span><span class="mord"><span class="mord mathit">r</span></span></span></span><span class="vlist-s">​</span></span><span class="vlist-r"><span class="vlist" style="height:0.686em;"><span></span></span></span></span></span><span class="mclose nulldelimiter"></span></span><span class="mclose delimcenter" style="top:0em;"><span class="delimsizing size2">⌋</span></span></span></span></span></span></span></span></p> <p>The code equivalent to this in Python is below:</p> <div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kn">import</span> <span class="nn">random</span> <span class="c1"># r &lt;= 0 &lt;= W*H </span><span class="n">r</span> <span class="o">=</span> <span class="n">random</span><span class="p">.</span><span class="n">randint</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="n">W</span><span class="o">*</span><span class="n">H</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span> <span class="c1"># x = r mod W </span><span class="n">x</span> <span class="o">=</span> <span class="n">r</span> <span class="o">%</span> <span class="n">W</span> <span class="c1"># y = floor(r/H); note the special syntax python has for this operation </span><span class="n">y</span> <span class="o">=</span> <span class="n">r</span> <span class="o">//</span> <span class="n">H</span> </code></pre></div></div> <p>So that’s that, we can put this in a big ‘ol for loop and generate an arbitrary <em>n</em> number of bombs given a width and height of a Minesweeper board.</p> <h2 id="cascading-tile-revealing">Cascading Tile Revealing</h2> <p>This one is hard to describe; I am adapting this from <a href="https://leetcode.com/problems/minesweeper/">leetcode.com</a>. Whenever a player clicks a tile, the following logic should be used:</p> <ol> <li>If a mine is revealed, the game is over. (obviously)</li> <li>If a tile with <em>no</em> adjacent mines is revealed, recursively reveal all eight adjacent tiles.</li> <li>If a tile with one or more adjacent mines is revealed, display the number of mines next to it.</li> </ol> <p>Here is the code in Python for this algorithm.</p> <div class="language-python highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="k">def</span> <span class="nf">reveal_square</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">board</span><span class="p">,</span> <span class="n">alread_revealed</span><span class="p">):</span> <span class="c1"># if already checked </span> <span class="k">if</span> <span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">)</span> <span class="ow">in</span> <span class="n">already_revealed</span><span class="p">:</span> <span class="k">return</span> <span class="c1"># if it's a bomb </span> <span class="k">if</span> <span class="n">board</span><span class="p">[</span><span class="n">x</span><span class="p">][</span><span class="n">y</span><span class="p">]</span> <span class="o">==</span> <span class="s">'B'</span><span class="p">:</span> <span class="n">you_lose</span><span class="p">()</span> <span class="k">return</span> <span class="c1"># if the bomb number is more than 0 </span> <span class="n">already_revealed</span><span class="p">.</span><span class="n">append</span><span class="p">((</span><span class="n">nx</span><span class="p">,</span> <span class="n">ny</span><span class="p">))</span> <span class="c1"># from -1 to 1 </span> <span class="k">for</span> <span class="n">xd</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">):</span> <span class="k">for</span> <span class="n">yd</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">):</span> <span class="c1"># skip if it is this the center tile </span> <span class="k">if</span> <span class="n">x</span><span class="o">+</span><span class="n">xd</span> <span class="o">==</span> <span class="n">x</span> <span class="ow">and</span> <span class="n">y</span><span class="o">+</span><span class="n">yd</span> <span class="o">==</span> <span class="n">y</span><span class="p">:</span> <span class="k">continue</span> <span class="c1"># recursively check the adjacent square </span> <span class="n">reveal</span><span class="p">(</span><span class="n">x</span><span class="o">+</span><span class="n">xd</span><span class="p">,</span> <span class="n">y</span><span class="o">+</span><span class="n">yd</span><span class="p">,</span> <span class="n">board</span><span class="p">,</span> <span class="n">already_revealed</span><span class="p">)</span> <span class="k">return</span> <span class="n">already_revealed</span> </code></pre></div></div> <p>This has no checks for valid squares, but it’s the general idea. This function returns an array of tile coordinates which should be revealed.</p> <h2 id="conclusion">Conclusion</h2> <p>I wrote this because in the first place because I was writing my own Minesweeper game. I hope that this helps you with getting the general idea of a Minesweeper game. The completed version of this game is available on my <a href="https://lamegames.tait.tech/">lamegames</a> site. Let me know what you think!</p> <p>Happy hacking!</p>When I was creating a little Minesweeper game, I got confused at some points. My bomb generation didn’t look quite right, and I for sure didn’t quite get the whole cascading tile reveal thing. With a bit of internet research, I found what I was looking for. I’ll explain it all in one place for my own research purposes.lamegames.tait.tech2020-09-09T00:00:00-06:002020-09-09T00:00:00-06:00/2020/09/09/lamegames<p>This is an announcement for a new project of mine: <a href="https://lamegames.tait.tech">lamegames.tait.tech</a>.</p> <p>This is something I’m really excited to work on!</p> <p>Right now, I’ve just got a rock-paper-scissors game. A chat function, and a few simple card games to come.</p> <p>Check out the repository on my <a href="https://github.com/TTWNO/lamegames.io">Github</a>.</p>This is an announcement for a new project of mine: lamegames.tait.tech.How to Solve The Django Deployment Puzzle2020-08-18T00:00:00-06:002020-08-18T00:00:00-06:00/2020/08/18/django-deployment<p>A few days ago I had a Django project I wanted to put on a real server. This project is still in its infancy, but I thought it would be nice to put it on my resume and show my friends. Little did I know the headache coming my way. Here are some tips to help you not make the same mistakes as me.</p> <h3 id="asgi-servers">ASGI Servers</h3> <p>Because my project used the ASGI (Asynchronous webServer Gateway Interface), I needed to find a good production ASGI server to handle all the incoming requests. The best thing I found was <a href="http://www.uvicorn.org/">uvicorn</a>. It focuses on speed, which is a priority, especially when using the ASGI protocol.</p> <p>To run uvicorn on the command line for testing purposes, use something like the following:</p> <pre class="terminal"> $ uvicorn --reload myapp.asgi:application </pre> <p>The <code class="language-plaintext highlighter-rouge">--reload</code> option says to reload the server if any of the files get updated. This is not recommended in production. Sadly, I thought this meant I would need to do a hard shutdown of the server process every time I wanted to update. This turned out to not be the case.</p> <h3 id="workload-managers">Workload Managers</h3> <p>There is another equine-named program called <a href="https://gunicorn.org/">gunicorn</a> which can hold a number of processes under its control. An interesting feature of <code class="language-plaintext highlighter-rouge">gunicorn</code> is that it will gracefully switch from an old to a new deployment, replacing the subprocesses one-by-one and eventually having only the new deployment active on all subprocesses. The greatest part? Zero down time. The server keeps any old processes open if there is communication with them, then shift and new connections to the new deployment. This was a very cool feature I wanted to take advantage of.</p> <p>“Now hold on!” you might protest. “gunicorn is a WSGI server!” … oh you got me there! Yes, that’s right, <code class="language-plaintext highlighter-rouge">gunicorn</code> is paired with <code class="language-plaintext highlighter-rouge">uvicorn</code> to serve my files.</p> <h3 id="systemd">systemd</h3> <p>Love it or hate it, the majority of Linux distributions use the <code class="language-plaintext highlighter-rouge">systemd</code> init system. I decided it would be very convenient to have a .service file for my Django application to run automatically at boot. <code class="language-plaintext highlighter-rouge">Systemd</code> allows me to do this with a file like the following one I stored in <code class="language-plaintext highlighter-rouge">/lib/systemd/system/lamegames.service</code>.</p> <pre class="file"> [Unit] Description=Gunicorn/Uvicorn (lamegames.io) [Service] WorkingDirectory=/home/lame/lamegames.io Type=simple RemainAfterExit=yes ExecStart=/home/lame/lamegames.io/env/bin/gunicorn lamegames.asgi:application -w 2 -k uvicorn.workers.UvicornWorker ExecStop=/bin/kill -HUP $MAINPID Restart=always [Install] WantedBy=multi-user.target </pre> <h3 id="nginx">nginx</h3> <p>NGINX (pronounced engine-X) is a performance web server designed for speed and simplicity. For the front facing side of the site, I do need a production web server like nginx. Gunicorn simply doesn’t need all the features that nginx provides, but I do. To configure my nginx installation, I used the following few directives to:</p> <ol> <li>Redirect most traffic towards the gunicorn server.</li> <li>Redirect statically served files (CSS, JS, images) to the directory specified in the STATIC_ROOT variable of my <code class="language-plaintext highlighter-rouge">settings.py</code> file.</li> <li>Use TLS to enable https://</li> </ol> <p>Serving the static files from nginx as opposed to the <code class="language-plaintext highlighter-rouge">gunicorn</code> server is necessary. Gunicorn and other production A/WSGI web server will not set the proper MIME type over TLS. This will cause your browser to not load the Javascript/CSS.</p> <p>This is the important part of my nginx config.</p> <pre class="file"> server { location / { proxy_set_header Host $http_host; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; # these two lines ensure that WebSocket, and HTTP2 connection are forwarded correctly proxy_set_header Upgrade $http_upgrade; proxy_set_header Connection "Upgrade"; proxy_redirect off; proxy_buffering off; # this forwards all traffic to the local server on port 8000 proxy_pass http://localhost:8000; } # This forwards all static requests to Django's STATIC_ROOT set in settings.py; it is generated using the collectstatic command. location /static { autoindex on; alias /home/lame/lamegames.io/static_generated; } } </pre> <h3 id="setup">Setup</h3> <p>After all that, I was able to do the following:</p> <pre class="terminal"> # systemctl enable lamegames </pre> <p>This enabled my <code class="language-plaintext highlighter-rouge">gunicorn</code> server to run once the server started. NGINX is that way be default.</p> <p>And tada! You now have a working Django project on a production server!</p> <h4 id="notes">Notes</h4> <ul> <li>If using ws:// websockets, change them to wss:// for secure web sockets.</li> <li>Make sure to use channels.routing.get_default_application() instead of django.get_asgi_application() if your’re wanting to use channels/redis WebSockets.</li> </ul>A few days ago I had a Django project I wanted to put on a real server. This project is still in its infancy, but I thought it would be nice to put it on my resume and show my friends. Little did I know the headache coming my way. Here are some tips to help you not make the same mistakes as me.BSD Journey, Part 12020-08-15T00:00:00-06:002020-08-15T00:00:00-06:00/2020/08/15/openbsd1<p>As Linux becomes controlled by corporate sponsors and becomes more full of proprietary blobs, drivers, and even closed-source software like Steam, One may wonder if there are other options out there. For me, somebody that is intensely interested in security, there is one option: OpenBSD.</p> <p>Now, my interest in OpenBSD has been going on for a long time. I started poking around for Linux alternatives way back a few years ago when Linus Torvalds decided to leave after he got in trouble for some <a href="https://arstechnica.com/information-technology/2013/07/linus-torvalds-defends-his-right-to-shame-linux-kernel-developers/">unprofessional behaviour</a>. That said, Linus did come back to Linux development, but I knew that his abrasive style is what brought good code to the Linux kernel. I also knew that his ability to be critical would be hurt by the new <a href="https://itsfoss.com/linux-code-of-conduct/">code of conduct</a>. It would become a tool for the SJW types to hammer on Linus for being a “white male, et al.”; It would become a tool for the easily offended to use to get their dumb code into Linux; It would become a tool for the corporatization, the HR-ification of Linux. Frankly, this does not interest me.</p> <p>Now I’m sure that OpenBSD has its own internal policies that I disagree with. That said, Theo De Raadt is still at least known for calling Firefox an “amorphous peace of garbage” due to its lack of privilege separation. And, in their <a href="https://openbsd.org/goals.html">project goals</a> page, they specifically mention:</p> <blockquote> <p>Be as politics-free as possible; solutions should be decided on the basis of technical merit.</p> </blockquote> <p>Now that’s something I can get behind! Bet you that’s not in the Linux COC?</p> <p>He also went to university in my hometown, so that’s pretty cool! I can support a local madman who thinks he can make a better operating system than all those corporations. Maybe he was right, maybe not. What I know is I am excited to find out!</p> <p>Wish my luck on my OpenBSD journey. I will post updates here along the way.</p> <p>Happy hacking!</p>As Linux becomes controlled by corporate sponsors and becomes more full of proprietary blobs, drivers, and even closed-source software like Steam, One may wonder if there are other options out there. For me, somebody that is intensely interested in security, there is one option: OpenBSD.Know How Your Representative Votes In Parliament2020-07-30T00:00:00-06:002020-07-30T00:00:00-06:00/2020/07/30/canadian-parliament<p>As an advocate for openness, I had an idea to make a project out of the government of Canada’s <a href="https://open.canada.ca/en/open-data">Open Data</a> initiative to take a look at how my local MP voted on various pieces of legislation. It turns out though that this was not necessary due to how easy it was to find this information on the government’s own website. In this article, I will explain how you can do the same.</p> <h3 id="1-find-your-representative">1. Find Your Representative</h3> <p>The first step in this process is to find who your representative is. To do so, go to the government’s own website <a href="https://www.ourcommons.ca/Members/en">ourcommons.ca’s search tool</a>.</p> <p>Simply type in your postal code in the search box to find out who your MP is.</p> <h3 id="2-their-voting-record">2. Their Voting Record</h3> <p>Every MP’s voting record is public knowledge, and it is available nice and simple in a table on that MP’s page. For example, this is a link to <a href="https://www.ourcommons.ca/Members/en/pierre-poilievre(25524)/votes">Pierre Poilievre’s voting record</a>.</p> <p>To find your MP’s voting record, do step one, then: After the <strong>Overview</strong>, and <strong>Seat in The House</strong> sections, there are three tabs, <strong>Roles</strong>, <strong>Work</strong>, and <strong>Contact</strong>. Click on work. At the bottom of that tab is a link which says <strong>Chamber Votes</strong>. This will open a small window with some recent votes by this politician. If you want to see all their votes, there is a button at the bottom named <strong>All Votes by This Member</strong>.</p> <p>Tada! You can now keep your local MP accountable for anything you do or do not support.</p> <h3 id="3-bill-details">3. Bill Details</h3> <p>If you want to get into the nitty gritty, once you open a specific bill, you can actually find out the status of said bill, or read the actual text by clicking the <strong>View this Bill on LEGISinfo</strong> button.</p> <p>Both the status of the bill, and a link to a PDF document containing the bilingual text of the bill are visible in the main body of the page.</p> <h4 id="conclusion">Conclusion</h4> <p>I thought this was pretty cool! It was <em>way</em> simpler than I thought it would be.</p> <p>Thanks, Canada!</p>As an advocate for openness, I had an idea to make a project out of the government of Canada’s Open Data initiative to take a look at how my local MP voted on various pieces of legislation. It turns out though that this was not necessary due to how easy it was to find this information on the government’s own website. In this article, I will explain how you can do the same.Installing MultiCraft on Gentoo Linux2020-07-19T00:00:00-06:002020-07-19T00:00:00-06:00/2020/07/19/multicraft-php-gentoo<p>In a very odd combination of requirements, I needed to install <a href="https://multicraft.org">MultiCraft</a> on a Gentoo Linux system. The PHP <code class="language-plaintext highlighter-rouge">USE</code> flags are important so you don’t have to recompile it three times like I did.</p> <p>Here are some useful tips I came across:</p> <h3 id="php-use-flags">PHP <code class="language-plaintext highlighter-rouge">USE</code> flags</h3> <p>In <code class="language-plaintext highlighter-rouge">/etc/portage/package.use/php</code> I placed the following line:</p> <pre class="terminal"> dev-lang/php cgi mysql mysqli fpm pdo gd truetype </pre> <p>This should give you enough for a mysql backended MultiCraft installation. The <code class="language-plaintext highlighter-rouge">cgi</code> option may not be required as <code class="language-plaintext highlighter-rouge">fpm</code> stands for <em>FastCGI Process Managment</em>. I don’t know for sure though.</p> <h3 id="paper">Paper</h3> <p>This will grab the latest version of the Paper jar file using <a href="https://yivesmirror.com">YivesMirror</a>. I’m not sure how reputable it is, but my buddy who works with this stuff more often than me seemed to recognize it.</p> <pre class="terminal"> ## See the default craftbukkit.jar.conf for a detailed documentation of the ## format of this file. [config] name = Paper 1.16.1 Latest source = https://yivesmirror.com/files/paper/Paper-1.16.1-latest.jar category = Mods [encoding] #encode = system #decode = system #fileEncoding = latin-1 [start] command = "{JAVA}" -Xmx{MAX_MEMORY}M -Xms{START_MEMORY}M -XX:MaxPermSize=128M -Djline.terminal=jline.UnsupportedTerminal -jar "{JAR}" nogui </pre> <h3 id="other-tips">Other Tips</h3> <p>Do not use the option to setup a separate user for each server. This completely stalled any work getting done with a ton of ‘permission denied’ errors.</p> <h4 id="security">Security</h4> <p>If the panel is in the root directory of your NGINX web server, use the following in your server block to deny access to the <code class="language-plaintext highlighter-rouge">/protected</code> directory.</p> <pre class="terminal"> location /protected { deny all; return 404; } </pre> <h5 id="mysql">MySQL</h5> <p>It is always good practice to separate privileges. The MultiCraft daemon should have one SQL login, with one database allocated to it. The MultiCraft panel should have a separate SQL login, with a separate database allocated to it.</p> <p>You can do this with the following commands in your MySQL prompt:</p> <pre class="terminal"> sql&gt; CREATE DATABASE multicraft_daemon_database; Query OK, 0 rows affected (0.01 sec) sql&gt; CREATE DATABASE multicraft_panel_database; Query OK, 0 rows affected (0.01 sec) sql&gt; CREATE USER 'muilticraft_daemon'@'localhost' IDENTIFIED BY 'strong password here'; Query OK, 0 rows affected (0.01 sec) sql&gt; CREATE USER 'multicraft_panel'@'localhost' IDENTIFIED BY 'different strong password here'; Query OK, 0 rows affected (0.01 sec) sql&gt; GRANT ALL PRIVILEGES ON multicraft_daemon_database . * TO 'multicraft_daemon'@'localhost'; Query OK, 0 rows affected (0.01 sec) sql&gt; GRANT ALL PRIVILEGES ON multicraft_panel_database . * TO 'mutlicraft_panel'@'localhost'; Query OK, 0 rows affected (0.01 sec) </pre> <p>During setup, make sure the proper credentials are used for each step. Database 1 is the panel database. Database 2 is the daemon database.</p> <p>Happy hacking :)</p>In a very odd combination of requirements, I needed to install MultiCraft on a Gentoo Linux system. The PHP USE flags are important so you don’t have to recompile it three times like I did.Independence2020-07-12T00:00:00-06:002020-07-12T00:00:00-06:00/2020/07/12/independence<blockquote> <p>“When given a choice between independence and dependence, always choose independence; you will never regret that choice!”—Luke Smith</p> </blockquote> <p>Whatever you may believe about the YouTube personality Luke Smith, the quote above summarizes a core principle of mine. Much like many people have religious principles, I have <em>Independence</em>.</p> <p>My choice to use Linux as my primary operating system, host my own website, own my own domain name—all of these are directly related to this core principle of independence.</p> <p>I never want a man, or a company to have too much power over my life. Just like I would not trust just any person to be able to read my emails, know where I live, where I am going, who are my friends, what do I believe; in the same way, I do not trust a company with that same information.</p> <blockquote> <p>“If you want to find out what a man is to the bottom, give him power. Any man can stand adversity — only a great man can stand prosperity.”—Robert Ingersoll</p> </blockquote> <p>Take control of your own digital life:</p> <ol> <li>Own your own domain.</li> <li>Hookup an email and a website to that.</li> </ol> <p>That’s it!</p> <p>Without this, any of your internet privileges can be revoked at any time by Google, Facebook, YouTube, Twitter, or even an angry Twitter Mob. Maybe because they hate your skin colour, maybe they hate your religious/political views, or maybe you got caught on a technicality.</p> <p>If you own your own domain, however:</p> <p>Your email provider goes down/bans you: change your provider; keep the email.</p> <p>Your website is pulled for controversial views: switch hosts.</p> <p>Protect yourself; give yourself choices. Why give others that power when you could have it for yourself?</p>“When given a choice between independence and dependence, always choose independence; you will never regret that choice!”—Luke Smith \ No newline at end of file