diff --git a/apps/mosquitto_ctrl/broker.c b/apps/mosquitto_ctrl/broker.c index 1ee7f99e..23081086 100644 --- a/apps/mosquitto_ctrl/broker.c +++ b/apps/mosquitto_ctrl/broker.c @@ -175,7 +175,7 @@ static void broker__payload_callback(struct mosq_ctrl *ctrl, long payloadlen, co j_error = cJSON_GetObjectItem(j_response, "error"); if(j_error){ - fprintf(stderr, "%s: Error: %s\n", j_command->valuestring, j_error->valuestring); + fprintf(stderr, "%s: Error: %s.\n", j_command->valuestring, j_error->valuestring); }else{ if(!strcasecmp(j_command->valuestring, "listPlugins")){ print_plugin_info(j_response); diff --git a/apps/mosquitto_ctrl/dynsec.c b/apps/mosquitto_ctrl/dynsec.c index a6dc5373..8a941ad2 100644 --- a/apps/mosquitto_ctrl/dynsec.c +++ b/apps/mosquitto_ctrl/dynsec.c @@ -394,7 +394,7 @@ static void dynsec__payload_callback(struct mosq_ctrl *ctrl, long payloadlen, co j_error = cJSON_GetObjectItem(j_response, "error"); if(j_error){ - fprintf(stderr, "%s: Error: %s\n", j_command->valuestring, j_error->valuestring); + fprintf(stderr, "%s: Error: %s.\n", j_command->valuestring, j_error->valuestring); }else{ if(!strcasecmp(j_command->valuestring, "listClients")){ print_list(j_response, "clients", "username"); diff --git a/apps/mosquitto_ctrl/mosquitto_ctrl.c b/apps/mosquitto_ctrl/mosquitto_ctrl.c index 78e8bb0b..989f4948 100644 --- a/apps/mosquitto_ctrl/mosquitto_ctrl.c +++ b/apps/mosquitto_ctrl/mosquitto_ctrl.c @@ -110,7 +110,7 @@ int main(int argc, char *argv[]) }else if(rc == MOSQ_ERR_UNKNOWN){ /* Message printed already */ }else{ - fprintf(stderr, "Error: %s\n", mosquitto_strerror(rc)); + fprintf(stderr, "Error: %s.\n", mosquitto_strerror(rc)); } } diff --git a/apps/mosquitto_ctrl/options.c b/apps/mosquitto_ctrl/options.c index 7b8146d1..ca752712 100644 --- a/apps/mosquitto_ctrl/options.c +++ b/apps/mosquitto_ctrl/options.c @@ -709,7 +709,7 @@ int client_connect(struct mosquitto *mosq, struct mosq_config *cfg) #else FormatMessage(FORMAT_MESSAGE_FROM_SYSTEM, NULL, errno, 0, (LPTSTR)&err, 1024, NULL); #endif - fprintf(stderr, "Error: %s\n", err); + fprintf(stderr, "Error: %s.\n", err); }else{ fprintf(stderr, "Unable to connect (%s).\n", mosquitto_strerror(rc)); } diff --git a/lib/strings_mosq.c b/lib/strings_mosq.c index 850ed9b5..f92e6f1e 100644 --- a/lib/strings_mosq.c +++ b/lib/strings_mosq.c @@ -31,62 +31,109 @@ Contributors: const char *mosquitto_strerror(int mosq_errno) { switch(mosq_errno){ + case MOSQ_ERR_QUOTA_EXCEEDED: + return "Quota exceeded"; + case MOSQ_ERR_AUTH_DELAYED: + return "Authentication delayed"; case MOSQ_ERR_AUTH_CONTINUE: - return "Continue with authentication."; + return "Continue with authentication"; case MOSQ_ERR_NO_SUBSCRIBERS: - return "No subscribers."; + return "No subscribers"; case MOSQ_ERR_SUB_EXISTS: - return "Subscription already exists."; + return "Subscription already exists"; case MOSQ_ERR_CONN_PENDING: - return "Connection pending."; + return "Connection pending"; case MOSQ_ERR_SUCCESS: - return "No error."; + return "No error"; case MOSQ_ERR_NOMEM: - return "Out of memory."; + return "Out of memory"; case MOSQ_ERR_PROTOCOL: - return "A network protocol error occurred when communicating with the broker."; + return "A network protocol error occurred when communicating with the broker"; case MOSQ_ERR_INVAL: - return "Invalid input."; + return "Invalid input"; case MOSQ_ERR_NO_CONN: - return "The client is not currently connected."; + return "The client is not currently connected"; case MOSQ_ERR_CONN_REFUSED: - return "The connection was refused."; + return "The connection was refused"; case MOSQ_ERR_NOT_FOUND: - return "Message not found (internal error)."; + return "Message not found (internal error)"; case MOSQ_ERR_CONN_LOST: - return "The connection was lost."; + return "The connection was lost"; case MOSQ_ERR_TLS: - return "A TLS error occurred."; + return "A TLS error occurred"; case MOSQ_ERR_PAYLOAD_SIZE: - return "Payload too large."; + return "Payload too large"; case MOSQ_ERR_NOT_SUPPORTED: - return "This feature is not supported."; + return "This feature is not supported"; case MOSQ_ERR_AUTH: - return "Authorisation failed."; + return "Authorisation failed"; case MOSQ_ERR_ACL_DENIED: - return "Access denied by ACL."; + return "Access denied by ACL"; case MOSQ_ERR_UNKNOWN: - return "Unknown error."; + return "Unknown error"; case MOSQ_ERR_ERRNO: return strerror(errno); case MOSQ_ERR_EAI: - return "Lookup error."; + return "Lookup error"; case MOSQ_ERR_PROXY: - return "Proxy error."; + return "Proxy error"; + case MOSQ_ERR_PLUGIN_DEFER: + return "Plugin deferring result"; case MOSQ_ERR_MALFORMED_UTF8: return "Malformed UTF-8"; + case MOSQ_ERR_KEEPALIVE: + return "Keepalive exceeded"; + case MOSQ_ERR_LOOKUP: + return "Lookup failed"; + case MOSQ_ERR_MALFORMED_PACKET: + return "Malformed packet"; case MOSQ_ERR_DUPLICATE_PROPERTY: return "Duplicate property in property list"; case MOSQ_ERR_TLS_HANDSHAKE: - return "TLS handshake failed."; + return "TLS handshake failed"; case MOSQ_ERR_QOS_NOT_SUPPORTED: - return "Requested QoS not supported on server."; + return "Requested QoS not supported on server"; case MOSQ_ERR_OVERSIZE_PACKET: - return "Packet larger than supported by the server."; + return "Packet larger than supported by the server"; case MOSQ_ERR_OCSP: - return "OCSP error."; + return "OCSP error"; + case MOSQ_ERR_TIMEOUT: + return "Timeout"; + case MOSQ_ERR_ALREADY_EXISTS: + return "Entry already exists"; + case MOSQ_ERR_PLUGIN_IGNORE: + return "Ignore plugin"; + + case MOSQ_ERR_UNSPECIFIED: + return "Unspecified error"; + case MOSQ_ERR_IMPLEMENTATION_SPECIFIC: + return "Implementaion specific error"; + case MOSQ_ERR_CLIENT_IDENTIFIER_NOT_VALID: + return "Client identifier not valid"; + case MOSQ_ERR_BAD_USERNAME_OR_PASSWORD: + return "Bad username or password"; + case MOSQ_ERR_SERVER_UNAVAILABLE: + return "Server unavailable"; + case MOSQ_ERR_SERVER_BUSY: + return "Server busy"; + case MOSQ_ERR_BANNED: + return "Banned"; + case MOSQ_ERR_BAD_AUTHENTICATION_METHOD: + return "Bad authentication method"; + case MOSQ_ERR_SESSION_TAKEN_OVER: + return "Session taken over"; + case MOSQ_ERR_RECEIVE_MAXIMUM_EXCEEDED: + return "Receive maximum exceeded"; + case MOSQ_ERR_TOPIC_ALIAS_INVALID: + return "Topic alias invalid"; + case MOSQ_ERR_ADMINISTRATIVE_ACTION: + return "Administrative action"; + case MOSQ_ERR_RETAIN_NOT_SUPPORTED: + return "Retain not supported"; + case MOSQ_ERR_CONNECTION_RATE_EXCEEDED: + return "Connection rate exceeded"; default: - return "Unknown error."; + return "Unknown error"; } } @@ -94,19 +141,19 @@ const char *mosquitto_connack_string(int connack_code) { switch(connack_code){ case 0: - return "Connection Accepted."; + return "Connection Accepted"; case 1: - return "Connection Refused: unacceptable protocol version."; + return "Connection Refused: unacceptable protocol version"; case 2: - return "Connection Refused: identifier rejected."; + return "Connection Refused: identifier rejected"; case 3: - return "Connection Refused: broker unavailable."; + return "Connection Refused: broker unavailable"; case 4: - return "Connection Refused: bad user name or password."; + return "Connection Refused: bad user name or password"; case 5: - return "Connection Refused: not authorised."; + return "Connection Refused: not authorised"; default: - return "Connection Refused: unknown reason."; + return "Connection Refused: unknown reason"; } } @@ -224,8 +271,12 @@ int mosquitto_string_to_command(const char *str, int *cmd) *cmd = CMD_PUBCOMP; }else if(!strcasecmp(str, "subscribe")){ *cmd = CMD_SUBSCRIBE; + }else if(!strcasecmp(str, "suback")){ + *cmd = CMD_SUBACK; }else if(!strcasecmp(str, "unsubscribe")){ *cmd = CMD_UNSUBSCRIBE; + }else if(!strcasecmp(str, "unsuback")){ + *cmd = CMD_UNSUBACK; }else if(!strcasecmp(str, "disconnect")){ *cmd = CMD_DISCONNECT; }else if(!strcasecmp(str, "auth")){ @@ -233,6 +284,7 @@ int mosquitto_string_to_command(const char *str, int *cmd) }else if(!strcasecmp(str, "will")){ *cmd = CMD_WILL; }else{ + *cmd = 0; return MOSQ_ERR_INVAL; } return MOSQ_ERR_SUCCESS; diff --git a/test/unit/CMakeLists.txt b/test/unit/CMakeLists.txt index 9ea069c4..6c8f3254 100644 --- a/test/unit/CMakeLists.txt +++ b/test/unit/CMakeLists.txt @@ -26,6 +26,7 @@ add_executable(broker-test property_read.c property_user_read.c property_write.c + strings_test.c stubs.c util_topic_test.c utf8.c @@ -36,6 +37,7 @@ add_executable(broker-test ../../lib/property_mosq.c ../../lib/memory_mosq.c ../../common/misc_mosq.c + ../../lib/strings_mosq.c ../../lib/util_mosq.c ../../lib/util_topic.c ../../lib/utf8_mosq.c diff --git a/test/unit/Makefile b/test/unit/Makefile index 22ab7f72..5846c093 100644 --- a/test/unit/Makefile +++ b/test/unit/Makefile @@ -24,6 +24,7 @@ TEST_OBJS = \ property_read.o \ property_user_read.o \ property_write.o \ + strings_test.o \ lib_stubs.o \ util_topic_test.o \ utf8.o @@ -34,6 +35,7 @@ LIB_OBJS = \ ${R}/lib/packet_datatypes.o \ ${R}/lib/packet_mosq.o \ ${R}/lib/property_mosq.o \ + ${R}/lib/strings_mosq.o \ ${R}/lib/util_mosq.o \ ${R}/lib/util_topic.o \ ${R}/lib/utf8_mosq.o diff --git a/test/unit/strings_test.c b/test/unit/strings_test.c new file mode 100644 index 00000000..8535e58b --- /dev/null +++ b/test/unit/strings_test.c @@ -0,0 +1,205 @@ +/* Tests for int to string functions. */ + +#include +#include + +#include "mosquitto.h" + +static void TEST_mosquitto_strerror(void) +{ + const char *str; + int used[] = {-6, -5, -4, -3, -2, -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, + 12, /* 13, */ 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 31, 32, + 128, 131, 133, 134, 136, 137, 138, 140, 142, 147, 148, 152, 154, 159}; + + /* Iterate over all possible errors, checking we have a place holder for all + * unused errors, and that all used errors do not have place holder text. */ + for(int err=-256; err<256; err++){ + str = mosquitto_strerror(err); + CU_ASSERT_PTR_NOT_NULL(str); + if(str){ + bool is_used = false; + for(size_t i=0; i