@@ -117,14 +117,17 @@ int tp_poll(struct mqtt_sn_client *client)
117
117
return recvfrom_data .sz ;
118
118
}
119
119
120
- static ZTEST_BMEM struct mqtt_sn_client mqtt_clients [8 ];
120
+ #define NUM_TEST_CLIENTS 10
121
+ static ZTEST_BMEM struct mqtt_sn_client mqtt_clients [NUM_TEST_CLIENTS ];
121
122
static ZTEST_BMEM struct mqtt_sn_client * mqtt_client ;
122
123
123
124
static void setup (void * f )
124
125
{
125
126
ARG_UNUSED (f );
126
127
static ZTEST_BMEM size_t i ;
127
128
129
+ zassert_true (i < NUM_TEST_CLIENTS , "Too few clients, increase NUM_TEST_CLIENTS" );
130
+
128
131
mqtt_client = & mqtt_clients [i ++ ];
129
132
130
133
transport = (struct mqtt_sn_transport ){
@@ -383,6 +386,7 @@ static ZTEST(mqtt_sn_client, test_mqtt_sn_connect_will)
383
386
zassert_equal (evt_cb_data .last_evt .type , MQTT_SN_EVT_CONNECTED , "Wrong event" );
384
387
}
385
388
389
+ /* Test a simple PUBLISH message */
386
390
static ZTEST (mqtt_sn_client , test_mqtt_sn_publish_qos0 )
387
391
{
388
392
struct mqtt_sn_data data = MQTT_SN_DATA_STRING_LITERAL ("Hello, World!" );
@@ -402,17 +406,143 @@ static ZTEST(mqtt_sn_client, test_mqtt_sn_publish_qos0)
402
406
err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (10 ));
403
407
zassert_equal (err , 0 , "Timed out waiting for callback." );
404
408
assert_msg_send (1 , 12 , & gw_addr );
409
+
410
+ /* Send REGACK in response */
405
411
err = input (mqtt_client , regack , sizeof (regack ), & gw_addr );
406
412
zassert_equal (err , 0 , "unexpected error %d" );
407
413
err = k_sem_take (& mqtt_sn_tx_sem , K_NO_WAIT );
408
414
assert_msg_send (0 , 0 , NULL );
415
+
416
+ /* Expect PUBLISH to be sent */
409
417
err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (10 ));
410
418
zassert_equal (err , 0 , "Timed out waiting for callback." );
411
419
assert_msg_send (1 , 20 , & gw_addr );
412
420
421
+ /* Expect publishes to be empty - all done */
413
422
zassert_true (sys_slist_is_empty (& mqtt_client -> publish ), "Publish not empty" );
423
+
424
+ /* Expect topics not to be empty - should be remembered */
414
425
zassert_false (sys_slist_is_empty (& mqtt_client -> topic ), "Topic empty" );
426
+ }
427
+
428
+ /*
429
+ * Test two PUBLISH messages
430
+ *
431
+ * 6.5 Topic Name Registration Procedure
432
+ * ...
433
+ * At any point in time a client may have only one REGISTER message outstanding, i.e. it has to wait
434
+ * for a REGACK message before it can register another topic name.
435
+ */
436
+ static ZTEST (mqtt_sn_client , test_mqtt_sn_wait_regack )
437
+ {
438
+ struct mqtt_sn_data data = MQTT_SN_DATA_STRING_LITERAL ("Hello, World!" );
439
+ struct mqtt_sn_data topic1 = MQTT_SN_DATA_STRING_LITERAL ("zephyr1" );
440
+ struct mqtt_sn_data topic2 = MQTT_SN_DATA_STRING_LITERAL ("zephyr2" );
441
+ /* registration ack with topic ID 0x1A1B, msg ID 0x0002, return code accepted */
442
+ uint8_t regack1 [] = {7 , 0x0B , 0x1A , 0x1B , 0x00 , 0x03 , 0 };
443
+ /* registration ack with topic ID 0x1A1C, msg ID 0x0003, return code accepted */
444
+ uint8_t regack2 [] = {7 , 0x0B , 0x1A , 0x1C , 0x00 , 0x05 , 0 };
445
+ int err ;
446
+
447
+ mqtt_sn_connect_no_will (mqtt_client );
448
+ err = k_sem_take (& mqtt_sn_tx_sem , K_NO_WAIT );
449
+
450
+ err = mqtt_sn_publish (mqtt_client , MQTT_SN_QOS_0 , & topic1 , false, & data );
451
+ zassert_equal (err , 0 , "Unexpected error %d" , err );
452
+ err = mqtt_sn_publish (mqtt_client , MQTT_SN_QOS_0 , & topic2 , false, & data );
453
+ zassert_equal (err , 0 , "Unexpected error %d" , err );
454
+
455
+ assert_msg_send (0 , 0 , NULL );
456
+
457
+ /* Expect one and only one REGISTER to be sent */
458
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (10 ));
459
+ zassert_equal (err , 0 , "Timed out waiting for callback." );
460
+ assert_msg_send (1 , 13 , & gw_addr );
461
+
462
+ /* Send REGACK in response */
463
+ err = input (mqtt_client , regack1 , sizeof (regack1 ), & gw_addr );
464
+ zassert_equal (err , 0 , "unexpected error %d" );
465
+ err = k_sem_take (& mqtt_sn_tx_sem , K_NO_WAIT );
466
+ assert_msg_send (0 , 0 , NULL );
467
+
468
+ /* Expect one more REGISTER and one PUBLISH to be sent */
469
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (10 ));
470
+ zassert_equal (err , 0 , "Timed out waiting for callback." );
471
+ assert_msg_send (2 , 20 , & gw_addr );
415
472
473
+ /* Expect publishes not to be empty - not done yet */
474
+ zassert_false (sys_slist_is_empty (& mqtt_client -> publish ), "Publish not empty" );
475
+
476
+ /* Send next REGACK in response */
477
+ err = input (mqtt_client , regack2 , sizeof (regack2 ), & gw_addr );
478
+ zassert_equal (err , 0 , "unexpected error %d" );
479
+ err = k_sem_take (& mqtt_sn_tx_sem , K_NO_WAIT );
480
+ assert_msg_send (0 , 0 , NULL );
481
+
482
+ /* Expect one more PUBLISH to be sent */
483
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (10 ));
484
+ zassert_equal (err , 0 , "Timed out waiting for callback." );
485
+ assert_msg_send (1 , 20 , & gw_addr );
486
+
487
+ /* Expect publishes to be empty - all done */
488
+ zassert_true (sys_slist_is_empty (& mqtt_client -> publish ), "Publish not empty" );
489
+
490
+ /* Expect topics not to be empty - should be remembered */
491
+ zassert_false (sys_slist_is_empty (& mqtt_client -> topic ), "Topic empty" );
492
+ }
493
+
494
+ /*
495
+ * Test two SUBSCRIBE / UNSUBSCRIBE messages
496
+ *
497
+ * 6.9 Client’s Topic Subscribe/Un-subscribe Procedure
498
+ * ...
499
+ * As for the REGISTER procedure, a client may have only one SUBSCRIBE or one UNSUBCRIBE transaction
500
+ * open at a time.
501
+ */
502
+ static ZTEST (mqtt_sn_client , test_mqtt_sn_wait_suback )
503
+ {
504
+ struct mqtt_sn_data topic1 = MQTT_SN_DATA_STRING_LITERAL ("zephyr1" );
505
+ struct mqtt_sn_data topic2 = MQTT_SN_DATA_STRING_LITERAL ("zephyr2" );
506
+ uint8_t suback1 [] = {8 , 0x13 , 0 , 0x1B , 0x1B , 0x00 , 0x07 , 0 };
507
+ uint8_t suback2 [] = {8 , 0x13 , 0 , 0x1B , 0x1C , 0x00 , 0x08 , 0 };
508
+ int err ;
509
+
510
+ mqtt_sn_connect_no_will (mqtt_client );
511
+ err = k_sem_take (& mqtt_sn_tx_sem , K_NO_WAIT );
512
+
513
+ err = mqtt_sn_subscribe (mqtt_client , MQTT_SN_QOS_0 , & topic1 );
514
+ zassert_ok (err , "Unexpected error %d" , err );
515
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (1 ));
516
+ /* Expect a SUBSCRIBE message */
517
+ assert_msg_send (1 , 12 , & gw_addr );
518
+
519
+ err = mqtt_sn_subscribe (mqtt_client , MQTT_SN_QOS_0 , & topic2 );
520
+ zassert_ok (err , "Unexpected error %d" , err );
521
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (1 ));
522
+ /* Expect NO message */
523
+ assert_msg_send (0 , 0 , NULL );
524
+
525
+ err = input (mqtt_client , suback1 , sizeof (suback1 ), & gw_addr );
526
+ zassert_ok (err , "unexpected error %d" );
527
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (1 ));
528
+ /* Expect second SUBSCRIBE message */
529
+ assert_msg_send (1 , 12 , & gw_addr );
530
+
531
+ err = mqtt_sn_unsubscribe (mqtt_client , MQTT_SN_QOS_0 , & topic1 );
532
+ zassert_ok (err , "Unexpected error %d" , err );
533
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (1 ));
534
+ /* Expect NO message - SUBSCRIBE in progress */
535
+ assert_msg_send (0 , 0 , NULL );
536
+
537
+ /* Unsubscribe while subscribe in progress - should fail */
538
+ err = mqtt_sn_unsubscribe (mqtt_client , MQTT_SN_QOS_0 , & topic2 );
539
+ zassert_not_ok (err , "Error expected" );
540
+
541
+ err = input (mqtt_client , suback2 , sizeof (suback2 ), & gw_addr );
542
+ zassert_ok (err , "unexpected error %d" );
543
+ err = k_sem_take (& mqtt_sn_tx_sem , K_SECONDS (1 ));
544
+ /* Expect UNSUBSCRIBE message */
545
+ assert_msg_send (1 , 12 , & gw_addr );
416
546
}
417
547
418
548
ZTEST_SUITE (mqtt_sn_client , NULL , NULL , setup , cleanup , NULL );
0 commit comments