Hi smitthhyy,

I am the author of the wolfMQTT library and did the integration into Harmony. I just downloaded the Harmony v2.05 to test it out. You must be having some include issues. The build error doesn't make sense to me since `mqtt_packet.h`defines `MqttMessage`, which is included just above in mqtt_client.h.

As for v0.10 in Harmony it looks like Microchip hasn't been updating the library, so I will ping them about getting it updated.

For now the best solution is to download the latest from us directly and replace it inside the Harmony `third_party/tcpip/wolfmqtt`.
https://github.com/wolfSSL/wolfMQTT
Then you'll have to re-generate your Harmony code. The README.md Kaleb provided explains how to do this.

Let me know if that is helpful or not. If you continue to get errors please email us at support@wolfssl.com and include the project for reference.

Thanks,
David Garske, wolfSSL

Hi lalonde,

For the RSA using our signature wrapper `wc_SignatureGenerate` the type `WC_SIGNATURE_TYPE_RSA_W_ENC` adds ASN1 DER encoding which includes the OID around the signature. Both `WC_SIGNATURE_TYPE_RSA` and `WC_SIGNATURE_TYPE_RSA_W_ENC` using PKCS v1.5.

Thanks,
David Garske, wolfSSL

328

(1 replies, posted in wolfCrypt)

Hi ravi.kumar,

To use the `TLS13-AES128-GCM-SHA256` cipher suite you must also enable AES GCM. Please try adding `--enable-aesgcm` to your ./configure options.

Another helpful tip is you can get a list of available cipher suites using:
./examples/client/client -e

You can get a list of ./configure commands using `./configure --help`.

Thanks,
David Garske, wolfSSL

Hi swessidorsaf,

Have you downloaded the latest v3.12.2 release we just posted?
https://github.com/wolfSSL/wolfssl/rele … 2.2-stable

If you are getting a "make check" error can you provide the ./configure string you are using the the platform/OS?

Thanks,
David Garske, wolfSSL

Hi Cxdinter,

Most AES mode require the input to be multiples of block size (16 bytes). TLS handles padding for block size. You should be able to pad with zeros if you want as long as the input is a multiple of 16 bytes. The resulting output will be the same length as the input. The decrypted text on the other side will have the padding and be a multiple of the block size. Most padding scheme use a length and known pad character. If you want to use AES and not worry about padding, I'd recommend AES GCM, which is an authentication cipher (wc_AesGcmEncrypt / wc_AesGcmDecrypt) and allows for any size input.

Thanks,
David Garske, wolfSSL

Hi cxdinter,

RSA can encrypt up to the key size (2048 bits is 256 bytes), but it is not something you would normally use to encrypt larger amounts of data because of performance. Typically a key is secretly exchanged using DHE or ECDHE and that key is used as an encryption key for AES, 3DES or ChaCha20. This is what TLS handles automatically. Can you provide some more background to help us understand the situation?

The RSA functions are wc_RsaPublicEncrypt and wc_RsaPrivateDecrypt.
The ECC key agreement is wc_ecc_shared_secret.
The AES encrypt decrypt functions depend on the mode. AES CBC for example is: wc_AesCbcEncrypt and wc_AesCbcDecrypt.

If you are looking for something more lightweight to securely exchange messages you could look at our ECC encrypt example here:
https://github.com/wolfSSL/wolfssl-exam … aster/btle

Thanks,
David Garske, wolfSSL

332

(1 replies, posted in wolfSSL)

Hi bthoms01,

Usually this error means there was an issue placing network bytes into the read buffer.

You have `MQX_USE_IO_OLD` defined which causes the wolfio.c to use the old MQX RTCS. You might try adding some debug in the IO and doing a Wireshark trace.

Another option is to enable and set IO callbacks where you can handle the socket read/writes directly. To do this define `WOLFSSL_USER_IO` and set IO callbacks using:
WOLFSSL_API void wolfSSL_SetIORecv(WOLFSSL_CTX *ctx, CallbackIORecv CBIORecv);
WOLFSSL_API void wolfSSL_SetIOSend(WOLFSSL_CTX *ctx, CallbackIOSend CBIOSend);

You can find an example for this here:
https://github.com/wolfSSL/wolfssl-exam … ack.c#L194

If you don't require support for pre TLS 1.2 I'd recommend adding `NO_OLD_TLS`.

Let me know if that information is helpful or if you have any other questions.

Thanks,
David Garske, wolfSSL

Hi Ravi,

Thanks for the report. I was able to reproduce a build error with `./configure --disable-ecc -enable-tls13 && make`, so I've issued a PR for it here:
https://github.com/wolfSSL/wolfssl/pull/1187
https://github.com/wolfSSL/wolfssl/pull … 639fbL5059

Marking this forum case as solved.

Thanks,
David Garske, wolfSSL

Hi Ravi,

The ECC algorithm is only on by default wit the `x86_64` platform. Please try using `./configure --enable-ecc --enable-tls13`. If that doesn't work can you provide the wolfSSL version (or Git commit #) along with which platform you are building on?

Thanks,
David Garske, wolfSS

Hi Kackle123,

Thanks for the report. I've pushed a fix in PR #39 here:
https://github.com/wolfSSL/wolfMQTT/pull/39

David Garske, wolfSSL

Hi Eyal,

That's wonderful! Very happy you got it all working.
Let me know if you have any other questions or issues.

Cheers,
David Garske

Hi Eyal,

What you have is an incomplete CSR, which is missing the signature. When comparing the one you generated with one from openssl the only difference was the missing signature at the bottom:

openssl asn1parse -inform der -in mycsr.der -dump
...
  248:d=1  hl=2 l=   9 cons: SEQUENCE          
  250:d=2  hl=2 l=   7 prim: OBJECT            :ecdsa-with-SHA1
  259:d=1  hl=2 l=  72 prim: BIT STRING        

Here is a complete code example for creating a valid CSR.

#include <wolfssl/options.h>
#include <wolfssl/wolfcrypt/settings.h>
#include <wolfssl/wolfcrypt/ecc.h>
#include <wolfssl/wolfcrypt/asn_public.h>

#define MAX_TEMP_SIZE 1024

/* Build using:
gcc -lwolfssl -o makecsr makecsr.c
*/

int main(void)
{
    ecc_key key;
    WC_RNG rng;
    Cert req;
    byte der[MAX_TEMP_SIZE], pem[MAX_TEMP_SIZE];
    int  derSz, pemSz;

    wc_ecc_init(&key);
    wc_InitRng(&rng);

    wc_ecc_make_key_ex(&rng, 32, &key, ECC_SECP256R1);

    derSz = wc_EccKeyToDer(&key, der, sizeof(der));

    memset(pem, 0, sizeof(pem));
    pemSz = wc_DerToPem(der, derSz, pem, sizeof(pem), ECC_PRIVATEKEY_TYPE);
    printf("%s", pem);

    wc_InitCert(&req);
    strncpy(req.subject.country, "US", CTC_NAME_SIZE);
    strncpy(req.subject.state, "OR", CTC_NAME_SIZE);
    strncpy(req.subject.locality, "Portland", CTC_NAME_SIZE);
    strncpy(req.subject.org, "yaSSL", CTC_NAME_SIZE);
    strncpy(req.subject.unit, "Development", CTC_NAME_SIZE);
    strncpy(req.subject.commonName, "www.wolfssl.com", CTC_NAME_SIZE);
    strncpy(req.subject.email, "info@wolfssl.com", CTC_NAME_SIZE);
    derSz = wc_MakeCertReq(&req, der, sizeof(der), NULL, &key);

    req.sigType = CTC_SHA256wECDSA;
    derSz = wc_SignCert(req.bodySz, req.sigType, der, sizeof(der), NULL, &key, &rng);

    pemSz = wc_DerToPem(der, derSz, pem, sizeof(pem), CERTREQ_TYPE);
    printf("%s", pem);

    wc_ecc_free(&key);
    wc_FreeRng(&rng);

    return 0;
}
gcc -lwolfssl -o makecsr makecsr.c
./makecsr > mycsr.csr

cat mycsr.csr 
-----BEGIN EC PRIVATE KEY-----
MHcCAQEEIJEIx4rTDoZFi7lsCiOX7XyTXnXOvj4VPDoQDGeD4p8woAoGCCqGSM49
AwEHoUQDQgAEMZygsN1xZH/QRxMszDej8bL84by+XQ4sziXUT83HGkTUx9puoNeI
UxlctiaTT1IgwCg9GCpC52SXU/e/NtvoUw==
-----END EC PRIVATE KEY-----
-----BEGIN CERTIFICATE REQUEST-----
MIIBSTCB8QIBAjCBjjELMAkGA1UEBhMCVVMxCzAJBgNVBAgMAk9SMREwDwYDVQQH
DAhQb3J0bGFuZDEOMAwGA1UECgwFeWFTU0wxFDASBgNVBAsMC0RldmVsb3BtZW50
MRgwFgYDVQQDDA93d3cud29sZnNzbC5jb20xHzAdBgkqhkiG9w0BCQEWEGluZm9A
d29sZnNzbC5jb20wWTATBgcqhkjOPQIBBggqhkjOPQMBBwNCAAQxnKCw3XFkf9BH
EyzMN6PxsvzhvL5dDizOJdRPzccaRNTH2m6g14hTGVy2JpNPUiDAKD0YKkLnZJdT
97822+hToAAwCgYIKoZIzj0EAwIDRwAwRAIgMdviSP9zLvYaNm1hcCVqG8jOvJz2
T34DlP3XXKI3cZ4CIFsNEquqCPbIkKGC8pOW9fUcmf6sWlgrra6uedL+PaCF
-----END CERTIFICATE REQUEST-----

openssl req -in mycsr.csr -text -noout
Certificate Request:
    Data:
        Version: 2 (0x2)
        Subject: C=US, ST=OR, L=Portland, O=yaSSL, OU=Development, CN=www.wolfssl.com/emailAddress=info@wolfssl.com
        Subject Public Key Info:
            Public Key Algorithm: id-ecPublicKey
            EC Public Key: 
                pub: 
                    04:31:9c:a0:b0:dd:71:64:7f:d0:47:13:2c:cc:37:
                    a3:f1:b2:fc:e1:bc:be:5d:0e:2c:ce:25:d4:4f:cd:
                    c7:1a:44:d4:c7:da:6e:a0:d7:88:53:19:5c:b6:26:
                    93:4f:52:20:c0:28:3d:18:2a:42:e7:64:97:53:f7:
                    bf:36:db:e8:53
                ASN1 OID: prime256v1
        Attributes:
            a0:00
    Signature Algorithm: ecdsa-with-SHA256
        30:44:02:20:31:db:e2:48:ff:73:2e:f6:1a:36:6d:61:70:25:
        6a:1b:c8:ce:bc:9c:f6:4f:7e:03:94:fd:d7:5c:a2:37:71:9e:
        02:20:5b:0d:12:ab:aa:08:f6:c8:90:a1:82:f2:93:96:f5:f5:
        1c:99:fe:ac:5a:58:2b:ad:ae:ae:79:d2:fe:3d:a0:85

Let me know if you have any questions.

Thanks,
David Garske, wolfSSL

Hi Eyal,

I'm happy to hear you got it working!

The `-----BEGIN EC PARAMETERS-----\nBggqhkjOPQMBBw==\n-----END EC PARAMETERS-----` part is static. Meaning for a prime256v1 256-bit key its always the same and you can always pre-pend it to the generated key if its required. This is just a base 64 encoded ASN1 object id, which indicates prime256v1. I've added this to our feature request list. It would be good for us to have the ability to generate these ECC parameters.

The default curve type is the NIST prime curves, so when calling wc_ecc_make_key with 32 you get a NIST prime256v1 curve. If you use the wc_ecc_make_key_ex function you can provide a curve_id such as `ECC_SECP256R1`.

You can see all the ECC build options here:
https://github.com/wolfSSL/wolfssl/blob … /ecc.c#L32

You can see a list of all supported curves here:
https://github.com/wolfSSL/wolfssl/blob … ecc.c#L456

If you would like to save code space you can define `ECC_USER_CURVES`, which allows you to define specific curve sizes manually using the 'HAVE_ECC###`defines (256-bit is on by default).

Thanks,
David Garske, wolfSSL

Hi Eyal,

If you are only using the wolfCrypt portion of the library you can:
1. define `WOLFCRYPT_ONLY`.
2. Include relevant source files in /wolfcrypt/src/*.c
3. Include relevant headers in /wolfssl/wolfcrypt/*.h

For the build options you are using the only files you would to include are: asn.c, ecc.c, sha256.c and random.c. However I would recommend pulling in all the files/headers and letting the linker optimize out any used functions. This should the same code size, but allow you to expand your use.

If you do not have a hardware RNG, then you should use the pseudo DBRG based on SHA256. To seed the DRBG you'll need to find some random source such as a microsecond counter or ADC noise.

Here are the defines and code example for doing this:

#define HAVE_HASHDRBG

#define CUSTOM_RAND_TYPE      unsigned int
extern unsigned int custom_rand_generate(void);
#define CUSTOM_RAND_GENERATE  custom_rand_generate

unsigned int custom_rand_generate(void)
{
    /* TODO: build 32-bits of RNG and return */
    return myRng;
}

Thanks,
David Garske, wolfSSL

Hi Eyal,

Thanks for evaluating wolfSSL! We have many customers using the STM32F4 with FreeRTOS. That is a great question!

To generate an ECC key:
1.  Make sure you have the `HAVE_ECC` defined.
2. Call:

ecc_key eccKey;
wc_ecc_make_key(rng, keySize, & eccKey);

Example: https://github.com/wolfSSL/wolfssl/blob … t.c#L11231

To create a CSR based on this ECC key:
1. Make sure you have `WOLFSSL_CERT_GEN` and `WOLFSSL_CERT_REQ` defined.
2. Call:

Cert req;
wc_MakeCertReq(&req, der, derSz, NULL, &eccKey);

Example: https://github.com/wolfSSL/wolfssl/blob … st.c#L8953

For an embedded system I find it best to put all my build options into a `user_settings.h` file (somewhere in your include path) and define `WOLFSSL_USER_SETTINGS`. You can find a good example for this here:

https://github.com/wolfSSL/wolfssl/blob … settings.h

Let me know if you have any issues or further questions.

Thanks,
David Garske, wolfSSL

Hi tdoering,

Thanks for the excellent question and details.

Yes having an intermediate CA for each device, which generated and signed by a root during manufacturing is a very good solution.

The server certificate for the TLS server should present a cert chain with the server peer certificate first, then the intermediate cert. If the public root CA is loaded on the key store/browser then this will be a valid certificate chain.

We have an example for creating a server certificate at runtime here:
https://github.com/wolfSSL/wolfssl-examples/pull/70

You can find examples for creating a cert request and having it signed here:
https://github.com/wolfSSL/wolfssl/blob … st.c#L8900

Let me know if you have any issues or questions.

Thanks,
David Garske, wolfSSL

342

(2 replies, posted in wolfSSL)

Hi Brad,

I would agree with it being a stack size issue, but if you've increased it to 132KB that would be more than required. Depending on the configuration a typical stack use for a TLS session is about 15 KB.

Its possible there is a BIG ENDIAN issue, but we continuously test with little and big endian, so I don't think that's the problem.

There are a couple of defines you can try using that might help:

#define ECC_TIMING_RESISTANT
#define NO_64BIT

The NO_64BIT could help if your compiler is having issue with the long long type. The ECC timing resistance uses a different math computation that is slower, but uses less stack.

Also you can limit the ECC curve size for by using `#define ECC_USER_CURVES`. This will enable only 256-bit curves by default and you can use defines like `HAVE_ECC384` to enable other curve sizes.

Here is an ECC section of a `user_settings.h`, which might be helpful:
https://github.com/wolfSSL/wolfssl/blob … ings.h#L48

Let me know if this helps or if you have any other questions.

Thanks,
David Garske, wolfSSL

Hi Nimesh,

To include wolfMQTT into your project you can either include the sources directly or compile them as a static library. I would recommend doing it the same as you are doing with wolfSSL. Either way is supported.

The wolfMQTT library itself is very compact (only about 4 KB). The only RAM allocated is for the TX/RX buffer, which defaults to 1024 bytes, but can be reduced.

I don't have any documentation for using wolfMQTT with TI_RTOS, but if you've got it working with wolfSSL then it should be easy to add wolfMQTT. The wolfMQTT library has no RTOS dependencies besides the network callbacks in examples/mqttnet.c. You can use that file as a template for implementing the TI_RTOS network calls.

The best reference for TI_RTOS can be found here:
https://github.com/wolfSSL/wolfssl/tree/master/tirtos

Thanks,
David Garske, wolfSSL

Hi Nimesh,

It sounds like you've already got past the most difficult part which is getting TLS running. Adding wolfMQTT on top is quite simple. You can download the latest source code for wolfMQTT v0.13 here:
https://github.com/wolfSSL/wolfMQTT

We have an example for using AWS in the 'examples/aws/awsiot.c` file. To enable TLS support build with the define `ENABLE_MQTT_TLS` set. You may need to change the `examples/mqttnet.c` to use TI-RTOS compatible network calls.

Let me know if you have any issues or questions.

Thanks,
David Garske, wolfSSL

345

(10 replies, posted in wolfSSL)

Hi Gussabina,

The IO read callback will ask for X bytes. If your network return X+10 bytes (for example) you will need to cache the extra 10 bytes until the next callback. Typically when you ask a network stack for X bytes it only returns X bytes. However if you are using something besides a network stack and asking the hardware for a buffer, you may receive more than X bytes. Its up to you to cache those extra bytes until the next IO read callback.

Let me know if that helps or not.

Thanks,
David Garske, wolfSSL

346

(10 replies, posted in wolfSSL)

Hi Gussabina,

That explains the issue you are seeing. The protection needs to happen at the MQTT protocol level since MQTT does not provide a way to split up publish messages. There is a header and the message follows behind which may span over multiple TLS / TCP packets. Additionally the publish being sent can respond with a confirmation if using Qos of 1 or 2.

So the answer is you will need to implement a way to make sure each thread has exclusive access to the MQTT library. I'd recommend either have single thread and using FreeRTOS queue to pass between threads or adding mutex protection around both MQTT tasks and implement non-blocking MQTT mode so it does not block and each thread gets access to the socket.

Thanks,
David Garske, wolfSSL

347

(10 replies, posted in wolfSSL)

Hi Gussabina,

If you are using FreeRTOS you can define `FREERTOS` instead of `SINGLE_THREADED` to enable mutex protection in the wolfSSL library.

The wolfMQTT library on the other-hand does not support multi-threads. To solve that you have a couple options:
1. Have one thread dedicated to handling the RX and TX of publish messages. Define `WOLFMQTT_NONBLOCK` and if you get back the `MQTT_CODE_CONTINUE` response code then it means no RX data is available. You can then use/check a FreeRTOS queue for any messages to TX.
2. Use a mutex to protect access to the socket between two threads. You'll also need to use non-blocking mode so you aren't blocked on the socket read.

It sounds like the eventual failure might be due to multiple threads trying to rx/tx publish messages at the same time. This would get the data in the socket out of sync and probably cause the decrypt error.

Thanks,
David Garske, wolfSSL

348

(10 replies, posted in wolfSSL)

Hi Gus,

Typically if things break-down after the connection has already been running fine indicates to me some memory issue either with corruption or memory leak. I recommend adding some memory checking to measure heap use and also stack use. We have some hooks for monitoring heap that can be enabled using `WOLFSSL_TRACK_MEMORY`. This will add tracking on XMALLOC/XFREE and display a result on wolfSSL_Cleanup() or `ShowMemoryTracker()`. Measuring stack is typically RTOS specific. What OS / Micro-controller are you using? Are you using any hardware crypto acceleration?

A typical recovery for a connection error would be to call `wolfSSL_shutdown(ssl)`, `wolfSSL_free(ssl)` and `close()` the socket. This will cleanup everything and allow you to reconnect again just as you did before. If you are having a memory issue I suspect you'll see problems reconnecting as well. We have a collection of TLS examples here: https://github.com/wolfSSL/wolfssl-exam … master/tls

Thanks,
David Garske, wolfSSL

349

(1 replies, posted in wolfCrypt)

Hi Csaba,

The wolfCrypt test results up to the point of failure look normal. Typically when we see a failure in RSA its because of a memory or configuration issue.

Please check the following:
1. Make sure your stack enough reserved space. For my wolfCrypt test on a PIC32MZ here I set it to 20480 bytes.
2. If you are setting the FP_MAX_BITS make sure and use the max key size times 2 (so 2048-bit RSA will require `#define FP_MAX_BITS 4096`).
3. For the wolfCrypt self test it requires certificates. Typically these come from the file system in ./certs. If NO_FILESYSTEM is defined then you'll need to set either USE_CERT_BUFFERS_2048 or USE_CERT_BUFFERS_1024 depending on your FP_MAX_BITS.

For setting up the library to just enable SHA1 and RSA you can define `WOLFSSL_USER_SETTINGS` and the `user_settings.h`file somewhere in your include path. You can find examples for this here:

https://github.com/wolfSSL/wolfssl/blob … settings.h

If this doesn't help please let me know the error code from the failed wc_Rsa function and the test which is failing.

Thanks,
David Garske, wolfSSL

350

(9 replies, posted in wolfMQTT)

Hi Kackle123,

That's excellent you got it working! Thanks for sending that information. I'll look into the use of `htons` for MQX in the wolfMQTT examples and see if I can fix that.

Thanks,
David Garske, wolfSSL