Hans was still thinking about the Wolf as he headed into town to get supplies. It was a nice day so he decided to wander down the side of the stream. As he passed the mill he looked up at the water wheel. The stream had been diverted into a wooden channel to power the wheel and then following the mill pond it rejoined the main flow.

 

"If I use a VPN client on the Yun then I could control my own channel to the weather service", he thought. When Hans reached the market he posted a letter to the weather service explaining his idea, bought the provisions and headed home.

 

VPN.png

 

Special Delivery

 

A few days later there was a knock on the door. "Hello", said the uniformed man. "You're not our usual postman" said Hans. "No", said the man, "he's off sick so I've come from the next town to stand in", and he handed Hans a letter.

 

The letter was sealed with a red wax seal with a big Y!. Inside was a paper with an official header on it that he instantly recognised. It was a letter from the weather service and it was not the news that Hans wanted to hear. Yes they could provide a VPN but it would need extra equipment installed in their office so would cost Hans 1000 gold coins per month. Hans and Matilda could not afford that but there must be another way.

 

Hans thought about the sealed envelope and the company identifier and wondered if the Yun could be configured for HTTPS connections. Simply adding the "s" to the end of the URL returned nothing so he added an extra parameter to try to capture the error stream back to the Arduino.

 

#include <Process.h>
void setup() {
  // Initialize Bridge
  Bridge.begin();

  // Initialize Serial
  Serial.begin(9600);

  // Wait until a Serial Monitor is connected.
  while (!Serial);

  // run various example processes
  runCurl();
}

void loop() {
  // Do nothing here.
}

void runCurl() {
  // Launch "curl" command and get Arduino ascii art logo from the network
  // curl is command line program for transferring data using different internet protocols
  Process p;        // Create a process and call it "p"
  p.begin("curl");  // Process that launch the "curl" command
  p.addParameter("https://query.yahooapis.com/v1/public/yql?q=select%20item.condition.text%20from%20weather.forecast%20where%20woeid%20in%20(select%20woeid%20from%20geo.places(1)%20where%20text%3D%22Chicago%20IL%22)&format=json&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys"); // Add the URL parameter to "curl"
  p.addParameter("&2>1"); // should pipe error output to stdout but does not
  p.run();      // Run the process and wait for its termination

  while (p.available()>0) {
    char c = p.read();
    Serial.print(c);
  }
  // Ensure the last bit of data is sent.
  Serial.flush();
}







 

That did not work so Han's tried a different approach using runShellCommand because the "&2>1" may need to be interpreted by the shell.

 

#include <Process.h>
void setup() {
  // Initialize Bridge
  delay(2500);
  Bridge.begin();
  // Initialize Serial
  Serial.begin(9600);
  // Wait until a Serial Monitor is connected.
  while (!Serial);
  Serial.println("Running Curl");
  // run various example processes
  runCurl();
  Serial.println("Done");
}
void loop() {
  // Do nothing here.
}
void runCurl() {
  Process p;        // Create a process and call it "p"
  p.runShellCommand("curl \"https://query.yahooapis.com/v1/public/yql?q=select%20item.condition.text%20from%20weather.forecast%20where%20woeid%20in%20(select%20woeid%20from%20geo.places(1)%20where%20text%3D%22Chicago%20IL%22)&format=json&env=store%3A%2F%2Fdatatables.org%2Falltableswithkeys\" 2>&1");
  while (p.available()>0) {
    char c = p.read();
    Serial.print(c);
  }
  // Ensure the last bit of data is sent.
  Serial.flush();
}





 

This displayed the following error message:

 

Running Curl
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0
curl: (60) SSL certificate problem: unable to get local issuer certificate
More details here: http://curl.haxx.se/docs/sslcerts.html
curl performs SSL certificate verification by default, using a "bundle"
 of Certificate Authority (CA) public keys (CA certs). If the default
 bundle file isn't adequate, you can specify an alternate file
 using the --cacert option.
If this HTTPS server uses a certificate signed by a CA represented in
 the bundle, the certificate verification probably failed due to a
 problem with the certificate (it might be expired, or the name might
 not match the domain name in the URL).
If you'd like to turn off curl's verification of the certificate, use
 the -k (or --insecure) option.
Done





 

Hans installed the certificates into /etc/ssl/certs using the package manager.

opkg update
opkg install ca-certificates




 

However the problem persisted.

 

After several hours of reading and googling the solution was found on the OpenWRT forum.

 

"The ca-certificates package is missing the HASH-links to the certificates"

https://forum.openwrt.org/viewtopic.php?id=50661

 

These can be added using openssl-util and a shell script provided in that article

 

#! /bin/sh
OPENSSL=/usr/bin/openssl
CERTDIR=/etc/ssl/certs

# Install openssl-util if need
[ ! -f ${OPENSSL} ] && opkg update && opkg install openssl-util

for CERTFILE in ${CERTDIR}/*; do
        # create symbolic link from hash
        echo -en "Certificate ${CERTFILE##*/}\n  generating hash: "
        HASH=$(${OPENSSL} x509 -hash -noout -in ${CERTFILE})
        echo "$HASH"

        # handle hash collision
        SUFFIX=0
        while [ -h "${CERTDIR}/${HASH}.${SUFFIX}" ]; do
                let "SUFFIX += 1"
        done

        echo "  linking ${HASH}.${SUFFIX} -> ${CERTFILE##*/}"
        ln -s ${CERTFILE##*/} ${CERTDIR}/${HASH}.${SUFFIX}
done




Hans fired up the Arduino Serial monitor and the script returned the forecast, it was going to be a great day!

Success.png

Hans was now happy that he had secure end to end communications.

Reference:

http://curl.haxx.se/docs/sslcerts.html

http://wiki.openwrt.org/doc/howto/wget-ssl-certs

 

Next: Enchanted Objects Design Challenge - The snake, the troll and the fighting dwarves