test_connect_destroy.c
Go to the documentation of this file.
1 /*******************************************************************************
2  * Copyright (c) 2009, 2020 IBM Corp. and others
3  *
4  * All rights reserved. This program and the accompanying materials
5  * are made available under the terms of the Eclipse Public License v2.0
6  * and Eclipse Distribution License v1.0 which accompany this distribution.
7  *
8  * The Eclipse Public License is available at
9  * https://www.eclipse.org/legal/epl-2.0/
10  * and the Eclipse Distribution License is available at
11  * http://www.eclipse.org/org/documents/edl-v10.php.
12  *
13  * Contributors:
14  * Michal Kasperek - initial API and implementation and/or initial documentation
15  *******************************************************************************/
16 
22 #include "MQTTClient.h"
23 #include "Thread.h"
24 #include <string.h>
25 #include <stdlib.h>
26 
27 #if !defined(_WINDOWS)
28  #include <sys/time.h>
29  #include <sys/socket.h>
30  #include <unistd.h>
31  #include <errno.h>
32  #define WINAPI
33 #else
34  #include <windows.h>
35  #define setenv(a, b, c) _putenv_s(a, b)
36 #endif
37 
38 #define ARRAY_SIZE(a) (sizeof(a) / sizeof(a[0]))
39 
40 void usage(void)
41 {
42  printf("help!!\n");
43  exit(EXIT_FAILURE);
44 }
45 
46 struct Options
47 {
48  char* connection;
49  char** haconnections;
50  int hacount;
51  int verbose;
52  int test_no;
53  int MQTTVersion;
54  int iterations;
55 } options =
56 {
57  "localhost:1883",
58  NULL,
59  0,
60  0,
61  0,
63  100,
64 };
65 
66 void getopts(int argc, char** argv)
67 {
68  int count = 1;
69 
70  while (count < argc)
71  {
72  if (strcmp(argv[count], "--test_no") == 0)
73  {
74  if (++count < argc)
75  options.test_no = atoi(argv[count]);
76  else
77  usage();
78  }
79  else if (strcmp(argv[count], "--connection") == 0)
80  {
81  if (++count < argc)
82  {
83  options.connection = argv[count];
84  printf("\nSetting connection to %s\n", options.connection);
85  }
86  else
87  usage();
88  }
89  else if (strcmp(argv[count], "--haconnections") == 0)
90  {
91  if (++count < argc)
92  {
93  char* tok = strtok(argv[count], " ");
94  options.hacount = 0;
95  options.haconnections = malloc(sizeof(char*) * 5);
96  while (tok)
97  {
98  options.haconnections[options.hacount] = malloc(strlen(tok) + 1);
99  strcpy(options.haconnections[options.hacount], tok);
100  options.hacount++;
101  tok = strtok(NULL, " ");
102  }
103  }
104  else
105  usage();
106  }
107  else if (strcmp(argv[count], "--MQTTversion") == 0)
108  {
109  if (++count < argc)
110  {
111  options.MQTTVersion = atoi(argv[count]);
112  printf("setting MQTT version to %d\n", options.MQTTVersion);
113  }
114  else
115  usage();
116  }
117  else if (strcmp(argv[count], "--iterations") == 0)
118  {
119  if (++count < argc)
120  options.iterations = atoi(argv[count]);
121  else
122  usage();
123  }
124  else if (strcmp(argv[count], "--verbose") == 0)
125  {
126  options.verbose = 1;
127  printf("\nSetting verbose on\n");
128  }
129  count++;
130  }
131 }
132 
133 
134 #define LOGA_DEBUG 0
135 #define LOGA_INFO 1
136 #include <stdarg.h>
137 #include <time.h>
138 #include <sys/timeb.h>
139 void MyLog(int LOGA_level, char* format, ...)
140 {
141  static char msg_buf[256];
142  va_list args;
143 #if defined(_WIN32) || defined(_WINDOWS)
144  struct timeb ts;
145 #else
146  struct timeval ts;
147 #endif
148  struct tm timeinfo;
149 
150  if (LOGA_level == LOGA_DEBUG && options.verbose == 0)
151  return;
152 
153 #if defined(_WIN32) || defined(_WINDOWS)
154  ftime(&ts);
155  localtime_s(&timeinfo, &ts.time);
156 #else
157  gettimeofday(&ts, NULL);
158  localtime_r(&ts.tv_sec, &timeinfo);
159 #endif
160  strftime(msg_buf, 80, "%Y%m%d %H%M%S", &timeinfo);
161 
162 #if defined(_WIN32) || defined(_WINDOWS)
163  sprintf(&msg_buf[strlen(msg_buf)], ".%.3hu ", ts.millitm);
164 #else
165  sprintf(&msg_buf[strlen(msg_buf)], ".%.3lu ", ts.tv_usec / 1000);
166 #endif
167 
168  va_start(args, format);
169  vsnprintf(&msg_buf[strlen(msg_buf)], sizeof(msg_buf) - strlen(msg_buf), format, args);
170  va_end(args);
171 
172  printf("%s\n", msg_buf);
173  fflush(stdout);
174 }
175 
176 
177 void MySleep(long milliseconds)
178 {
179 #if defined(WIN32) || defined(WIN64)
180  Sleep(milliseconds);
181 #else
182  usleep(milliseconds*1000);
183 #endif
184 }
185 
186 #if defined(WIN32) || defined(_WINDOWS)
187 #define START_TIME_TYPE DWORD
188 static DWORD start_time = 0;
190 {
191  return GetTickCount();
192 }
193 #elif defined(AIX)
194 #define START_TIME_TYPE struct timespec
196 {
197  static struct timespec start;
198  clock_gettime(CLOCK_REALTIME, &start);
199  return start;
200 }
201 #else
202 #define START_TIME_TYPE struct timeval
203 /* TODO - unused - remove? static struct timeval start_time; */
205 {
206  struct timeval start_time;
207  gettimeofday(&start_time, NULL);
208  return start_time;
209 }
210 #endif
211 
212 
213 #if defined(WIN32)
214 long elapsed(START_TIME_TYPE start_time)
215 {
216  return GetTickCount() - start_time;
217 }
218 #elif defined(AIX)
219 #define assert(a)
220 long elapsed(struct timespec start)
221 {
222  struct timespec now, res;
223 
224  clock_gettime(CLOCK_REALTIME, &now);
225  ntimersub(now, start, res);
226  return (res.tv_sec)*1000L + (res.tv_nsec)/1000000L;
227 }
228 #else
229 long elapsed(START_TIME_TYPE start_time)
230 {
231  struct timeval now, res;
232 
233  gettimeofday(&now, NULL);
234  timersub(&now, &start_time, &res);
235  return (res.tv_sec)*1000 + (res.tv_usec)/1000;
236 }
237 #endif
238 
239 
240 #define assert(a, b, c, d) myassert(__FILE__, __LINE__, a, b, c, d)
241 #define assert1(a, b, c, d, e) myassert(__FILE__, __LINE__, a, b, c, d, e)
242 
243 int tests = 0;
244 int failures = 0;
245 FILE* xml;
247 char output[3000];
249 
250 
252 {
253  long duration = elapsed(global_start_time);
254 
255  fprintf(xml, " time=\"%ld.%.3ld\" >\n", duration / 1000, duration % 1000);
256  if (cur_output != output)
257  {
258  fprintf(xml, "%s", output);
259  cur_output = output;
260  }
261  fprintf(xml, "</testcase>\n");
262 }
263 
264 
265 void myassert(char* filename, int lineno, char* description, int value, char* format, ...)
266 {
267  ++tests;
268  if (!value)
269  {
270  va_list args;
271 
272  ++failures;
273  MyLog(LOGA_INFO, "Assertion failed, file %s, line %d, description: %s\n", filename, lineno, description);
274 
275  va_start(args, format);
276  vprintf(format, args);
277  va_end(args);
278 
279  cur_output += sprintf(cur_output, "<failure type=\"%s\">file %s, line %d </failure>\n",
280  description, filename, lineno);
281  }
282  else
283  MyLog(LOGA_DEBUG, "Assertion succeeded, file %s, line %d, description: %s", filename, lineno, description);
284 }
285 
286 void lock_mutex(mutex_type amutex)
287 {
288  int rc = Thread_lock_mutex(amutex);
289  if (rc != 0)
290  MyLog(LOGA_INFO, "Error %s locking mutex", strerror(rc));
291 }
292 
294 {
295  int rc = Thread_unlock_mutex(amutex);
296  if (rc != 0)
297  MyLog(LOGA_INFO, "Error %s unlocking mutex", strerror(rc));
298 }
299 
300 
301 /*********************************************************************
302 
303 Test1: destroy MQTT client while connectig
304 
305 *********************************************************************/
306 
307 struct thread_parms
308 {
309  MQTTClient* c;
310 };
311 
313 {
314  MySleep(rand() % 500);
315 
316  struct thread_parms *parms = n;
317  MQTTClient* c = parms->c;
318 
320  return 0;
321 }
322 
323 
324 int test1(struct Options options)
325 {
326  srand((unsigned int)time(0));
327 
328  MQTTClient c;
331  int rc = 0;
332  char* test_topic = "C client test1";
333 
334  fprintf(xml, "<testcase classname=\"test1\" name=\"destroy mqtt while connecting\"");
336  failures = 0;
337  MyLog(LOGA_INFO, "Starting test 1 - execute destroy while connecting");
338 
339  rc = MQTTClient_create(&c, options.connection, "connect crash test",
341  assert("good rc from create", rc == MQTTCLIENT_SUCCESS, "rc was %d\n", rc);
342  if (rc != MQTTCLIENT_SUCCESS)
343  {
344  MQTTClient_destroy(&c);
345  goto exit;
346  }
347 
348  opts.connectTimeout = 30;
349  opts.keepAliveInterval = 20;
350  opts.cleansession = 1;
351  opts.username = "testuser";
352  opts.password = "testpassword";
353  opts.MQTTVersion = options.MQTTVersion;
354  if (options.haconnections != NULL)
355  {
356  opts.serverURIs = options.haconnections;
357  opts.serverURIcount = options.hacount;
358  }
359 
360  opts.will = &wopts;
361  opts.will->message = "will message";
362  opts.will->qos = 1;
363  opts.will->retained = 0;
364  opts.will->topicName = "will topic";
365  opts.will = NULL;
366 
367  struct thread_parms parms = {&c};
368  Thread_start(test1_destroy, (void*)&parms);
369 
370  MQTTClient_connect(c, &opts);
371 
372  MySleep(1000);
373 
374 exit:
375  MyLog(LOGA_INFO, "TEST1: test %s. %d tests run, %d failures.",
376  (failures == 0) ? "passed" : "failed", tests, failures);
378  return failures;
379 }
380 
381 
382 int main(int argc, char** argv)
383 {
384  int rc = 0;
385  int (*tests[])() = {NULL, test1};
386  int i;
387 
388  xml = fopen("TEST-test2.xml", "w");
389  fprintf(xml, "<testsuite name=\"test1\" tests=\"%d\">\n", (int)(ARRAY_SIZE(tests) - 1));
390 
391  setenv("MQTT_C_CLIENT_TRACE", "ON", 1);
392  setenv("MQTT_C_CLIENT_TRACE_LEVEL", "ERROR", 0);
393 
394  getopts(argc, argv);
395 
396  for (i = 0; i < options.iterations; ++i)
397  {
398  if (options.test_no == 0)
399  { /* run all the tests */
401  rc += tests[options.test_no](options); /* return number of failures. 0 = test succeeded */
402 
403  options.test_no = 0;
404  }
405  else
406  rc = tests[options.test_no](options); /* run just the selected test */
407  }
408 
409  if (rc == 0)
410  MyLog(LOGA_INFO, "verdict pass");
411  else
412  MyLog(LOGA_INFO, "verdict fail");
413 
414  fprintf(xml, "</testsuite>\n");
415  fclose(xml);
416  return rc;
417 }
#define START_TIME_TYPE
enum MQTTPropertyCodes value
char ** haconnections
Definition: test1.c:50
START_TIME_TYPE start_clock(void)
FMT_INLINE std::basic_string< Char > format(const S &format_str, Args &&...args)
Definition: core.h:2081
#define MQTTCLIENT_SUCCESS
Definition: MQTTClient.h:131
int MQTTClient_connect(MQTTClient handle, MQTTClient_connectOptions *options)
Definition: MQTTClient.c:1644
#define WINAPI
char * connection
#define LOGA_INFO
int Thread_lock_mutex(mutex_type mutex)
Definition: Thread.c:112
void unlock_mutex(mutex_type amutex)
struct pubsub_opts opts
Definition: paho_c_pub.c:42
size_t strftime(char *str, size_t count, const char *format, const std::tm *time)
Definition: chrono.h:375
#define LOGA_DEBUG
#define malloc(x)
Definition: Heap.h:41
MQTTClient * c
Definition: test2.c:344
struct Options options
int failures
void write_test_result(void)
static char msg_buf[512]
Definition: Log.c:122
#define MQTTClient_willOptions_initializer
Definition: MQTTClient.h:639
START_TIME_TYPE global_start_time
void usage(void)
constexpr size_t count()
Definition: core.h:960
int main(int argc, char **argv)
int hacount
Definition: test1.c:52
char output[3000]
description
Definition: setup.py:19
int Thread_unlock_mutex(mutex_type mutex)
Definition: Thread.c:133
FILE * xml
void lock_mutex(mutex_type amutex)
const char * topicName
Definition: MQTTClient.h:619
long elapsed(START_TIME_TYPE start_time)
#define mutex_type
Definition: mutex_type.h:22
void * MQTTClient
Definition: MQTTClient.h:246
int tests
void MyLog(int LOGA_level, char *format,...)
void MQTTClient_destroy(MQTTClient *handle)
Definition: MQTTClient.c:556
void MySleep(long milliseconds)
char * test_topic
Definition: test11.c:307
MQTTClient c
Definition: test10.c:1656
thread_return_type WINAPI test1_destroy(void *n)
float time
Definition: mqtt_test.py:17
void getopts(int argc, char **argv)
#define thread_return_type
Definition: Thread.h:44
null localtime_s(...)
Definition: chrono.h:286
#define MQTTCLIENT_PERSISTENCE_NONE
void myassert(char *filename, int lineno, char *description, int value, char *format,...)
#define MQTTClient_connectOptions_initializer
Definition: MQTTClient.h:953
thread_type Thread_start(thread_fn fn, void *parameter)
Definition: Thread.c:60
#define ARRAY_SIZE(a)
int test1(struct Options options)
char *const * serverURIs
Definition: MQTTClient.h:913
const char * message
Definition: MQTTClient.h:621
enum MQTTReasonCodes rc
Definition: test10.c:1112
int MQTTClient_create(MQTTClient *handle, const char *serverURI, const char *clientId, int persistence_type, void *persistence_context)
Definition: MQTTClient.c:507
#define MQTTVERSION_DEFAULT
Definition: MQTTAsync.h:195
MQTTClient_willOptions * will
Definition: MQTTClient.h:866
int test_no
Definition: test1.c:54
#define assert(a, b, c, d)
char * cur_output
Definition: test1.py:1


plotjuggler
Author(s): Davide Faconti
autogenerated on Sun Dec 6 2020 04:02:48