Using MQTT-TLS library to connect to AWS IoT Core

Hi, I’m new to particle and using an Argon with the firmware 1.5.2.
I need to connect my Argon to my AWS IoT Core preferable over MQTT with TLS, I tried to use the MQTT-TLS library but failed as i can’t get a connection to the server. I checked my certificates and key in MQTT.fx, there they work just fine.
I also tried to use the example1 but failed there too.

My code:

#include <Grove_Temperature_And_Humidity_Sensor.h>
#include <MQTT-TLS.h>
#include <certificates.h>

void callback(char* topic, byte* payload, unsigned int length);

MQTT client("a17c5omik6yjsa-ats.iot.eu-central-1.amazonaws.com", 8883, callback);
const char amazonIoTRootCAPem[] = AMAZON_IOT_ROOT_CA_PEM; 
const char clientKeyCrtPem[] = CLIENT_KEY_CRT_PEM;
const char clientKeyPem[] = CLIENT_KEY_PEM;


DHT temp(D2); 
String tempString; 

void callback(char* topic, byte* payload, unsigned int length) {
    char p[length + 1];
    memcpy(p, payload, length);
    p[length] = NULL;
    String message(p);
}


// setup() runs once, when the device is first turned on.
void setup() {
  // Put initialization like pinMode and begin functions here.

  //Start the Temp/Hum sensor
  temp.begin(); 

  // Enable TLS on the MQTT client
  client.enableTls(amazonIoTRootCAPem, sizeof(amazonIoTRootCAPem), 
                    clientKeyCrtPem, sizeof(clientKeyCrtPem), 
                    clientKeyPem, sizeof(clientKeyPem));
  client.connect("TempHum_Sensor1");
  Particle.publish("co", String(client.connect("adfahsdf")),PRIVATE);
  client.publish("TempHum_Sensor/test", "hallo");


}

// loop() runs over and over again, as quickly as it can execute.
void loop() {
  // The core of your code will likely live here.

  tempString = String(temp.getTempCelcius()); 
  //Particle.publish("temperature", tempString, PRIVATE);
  if (client.isConnected()){
    Serial.println("connected");
    Particle.publish("connected", "conn",PRIVATE);
    client.loop();
    client.publish("TempHum_Sensor/test", "hii");
  } else {
    Particle.publish("connected", "not", PRIVATE);
  }

  delay(10000); 

}

I think the problem might be the certificate part as I’m not sure about the formatting, I formatted everything to match the formatting of the examples.
Here is the code of my certificates.h file:

#define AMAZON_IOT_ROOT_CA_PEM                                             \
    "-----BEGIN CERTIFICATE----- \r\n"                                     \
    "MIIDQTCCAimgAwIBAgITBmyfz5m/jAo54vB4ikPmljZbyjANBgkqhkiG9w0BAQsF\r\n" \
    "ADA5MQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6\r\n" \
    "b24gUm9vdCBDQSAxMB4XDTE1MDUyNjAwMDAwMFoXDTM4MDExNzAwMDAwMFowOTEL\r\n" \
    "MAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJv\r\n" \
.....
    "5MsI+yMRQ+hDKXJioaldXgjUkK642M4UwtBV8ob2xJNDd2ZhwLnoQdeXeGADbkpy\r\n" \
    "rqXRfboQnoZsG4q5WTP468SQvvG5\r\n"                                     \
    "-----END CERTIFICATE----- "

#define CLIENT_KEY_CRT_PEM                                                 \
    "-----BEGIN CERTIFICATE----- \r\n"                                     \
    "MIIDWTCCAkGgAwIBAgIUN94dGYvsTJoeQvwxz6JgJcdOWjUwDQYJKoZIhvcNAQEL\r\n" \
    "BQAwTTFLMEkGA1UECwxCQW1hem9uIFdlYiBTZXJ2aWNlcyBPPUFtYXpvbi5jb20g\r\n" \
  ....
    "IdGvOolrrjKBhaGyutj4VsS3LZU8hraii+rQyfD5pJ7M8qQ+0ODV37b8Nb9Y\r\n"     \
    "-----END CERTIFICATE-----\r\n"

#define CLIENT_KEY_PEM                                                     \
    "-----BEGIN RSA PRIVATE KEY----- \r\n"                                     \
    "MIIEowIBAAKCAQEA2dS+/HsIGCN6d0tz+BZQ8eNj18OiyjNBzevQEdJ4tRKcfXgk\r\n" \
    "GkoDy/PPEjVQyuhd/2wLhp2zJX26ZnNPjyr4wy+UtdXPIElMwTYLI1Hf7s60+2o7\r\n" \
   ....
    "JnrlUw37EZMHI6EFF8AaVHRGshoOge8X9Xg8WJelwTkTZo38lZzU\r\n"             \
    "-----END RSA PRIVATE KEY-----\r\n"\

Do you have any idea why it doesn’t work?
Thanks!

The only thing different with mine as far as keys is I made sure there were no spaces between between ---- and \r\n.

Also, I use strlen instead of sizeof in enableTls(), but my keys are char * and not defines.

Try changing to:

#define AMAZON_IOT_ROOT_CA_PEM                                             \
    "-----BEGIN CERTIFICATE-----\r\n"                                     \
    "MIIDQTCCAimgAwIBAgITBmyfz5m/jAo54vB4ikPmljZbyjANBgkqhkiG9w0BAQsF\r\n" \
    "ADA5MQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6\r\n" \
    "b24gUm9vdCBDQSAxMB4XDTE1MDUyNjAwMDAwMFoXDTM4MDExNzAwMDAwMFowOTEL\r\n" \
    "MAkGA1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJv\r\n" \
.....
    "5MsI+yMRQ+hDKXJioaldXgjUkK642M4UwtBV8ob2xJNDd2ZhwLnoQdeXeGADbkpy\r\n" \
    "rqXRfboQnoZsG4q5WTP468SQvvG5\r\n"                                     \
    "-----END CERTIFICATE-----"
1 Like

@picsil Tanks for your reply, but those changes made no difference. I also tried to use the certificates as char* directly in my main file and not as an include, but i still can’t connect to my AWS IoT Core.

A problem that always occurs is this error message:
“cannot open source file “<mbedtls_config.h>” (dependency of “MQTT-TLS.h”)”
the code still compiles and flashes.

Any other ideas, what could be wrong, missing?

You may need to manually configure mbedtls. I don’t recall if it comes with a default config. See the README in the repo for details on how to configure.

https://github.com/hirotakaster/MQTT-TLS

The thing is there is only a file under mbedtls/config.h (with all the configurations as mentioned in the README) but no mbedtls_config.h. The mbedtls/config.h is #included in all of the other .h files but there is no mention of an mbedtls_config.h file.

Interesting. I don’t have that file either, and find no mention of it in the library source. I also did a full rebuild of my project and see no reference to it in the compiler output. Where did you install the library from? I’m using a copy forked from the github repo. If I recall when I downloaded it the github version was more up to date than the Particle library.

EDIT: I see that the current Particle library and github versions are in sync. version 0.2.23

First I used the install library command from the workbench, but now I tried to start everything from scratch, used the github code as library, reformatted the certificates, had no other library or anything in my code and still… no connection.

Thank you so much for your help!

EDIT: it works now, I did reformat the certificates to a “one-line” const char* (see the code below) - I don’t know why that changed anything as the size of the string stays the same and I had to use sizeof() instead of strlen(). Either way I’m really happy it finally works.
Again thank you for your help!!!

#include "cert.h"
#include "MQTT-TLS.h"

const char awsRootCert[] = "-----BEGIN CERTIFICATE-----\r\nMIIDQTCCAimgAwIBAgITBmyfz5m/jAo54vB4ikPmljZbyjANBgkqhkiG9w0BAQsF\r\nADA5MQswC-----END CERTIFICATE-----";
const char awsClientCert[] = "-----BEGIN CERTIFICATE-----\r\nMIIDWTCCAkGgAwIBAgIUN94dGYvsTJoeQvwxz6JgJcdOWjUwDQYJKoZIhvcNAQEL\r\nBQAwTT-----END CERTIFICATE-----";
const char awsClientKey[] = "-----BEGIN RSA PRIVATE KEY-----\r\nMIIEowIBAAKCAQEA2dS+/HsIGCN6d0tz+BZQ8eNj18OiyjNBzevQEdJ4tRKcfXgk\r\nGkoDy/PPEjV----END RSA PRIVATE KEY-----";

void callback(char* topic, byte* payload, unsigned int length);

MQTT client("a17c5omik6yjsa-ats.iot.eu-central-1.amazonaws.com",8883, callback);

void callback(char* topic, byte* payload, unsigned int length) {
    char p[length + 1];
    memcpy(p, payload, length);
    p[length] = NULL;
    String message(p);
}


// setup() runs once, when the device is first turned on.
void setup() {
  // Put initialization like pinMode and begin functions here.

client.enableTls(awsRootCert, sizeof(awsRootCert),awsClientCert, sizeof(awsClientCert), awsClientKey, sizeof(awsClientKey));
client.connect("Particle_1");
client.publish("sensor/test", "temp");


}

// loop() runs over and over again, as quickly as it can execute.
void loop() {
  if(client.isConnected()){
    client.loop();
    client.publish("sensor/test", "80");
    Particle.publish("connection", "connected", PRIVATE);
  } else
  {
    Particle.publish("connection", "not connected", PRIVATE);
  }
  

  delay(10000);
  // The core of your code will likely live here.

}
3 Likes

This topic was automatically closed 60 days after the last reply. New replies are no longer allowed.