Patchwork lib: arg + framework: more robust out of memory handling.

login
register
mail settings
Submitter Colin King
Date March 2, 2012, 11:11 a.m.
Message ID <1330686702-28964-1-git-send-email-colin.king@canonical.com>
Download mbox | patch
Permalink /patch/144220/
State Accepted
Headers show

Comments

Colin King - March 2, 2012, 11:11 a.m.
From: Colin Ian King <colin.king@canonical.com>

Signed-off-by: Colin Ian King <colin.king@canonical.com>
---
 src/lib/src/fwts_args.c      |   16 +++++++++++++---
 src/lib/src/fwts_framework.c |   23 +++++++++++++++++++----
 2 files changed, 32 insertions(+), 7 deletions(-)
Keng-Yu Lin - March 5, 2012, 9:51 a.m.
On Fri, Mar 2, 2012 at 7:11 PM, Colin King <colin.king@canonical.com> wrote:
> From: Colin Ian King <colin.king@canonical.com>
>
> Signed-off-by: Colin Ian King <colin.king@canonical.com>
> ---
>  src/lib/src/fwts_args.c      |   16 +++++++++++++---
>  src/lib/src/fwts_framework.c |   23 +++++++++++++++++++----
>  2 files changed, 32 insertions(+), 7 deletions(-)
>
> diff --git a/src/lib/src/fwts_args.c b/src/lib/src/fwts_args.c
> index 9837959..11342cf 100644
> --- a/src/lib/src/fwts_args.c
> +++ b/src/lib/src/fwts_args.c
> @@ -100,11 +100,13 @@ int fwts_args_parse(fwts_framework *fw, int argc, char * const argv[])
>        int c;
>        int option_index;
>        int ret = FWTS_OK;
> -
>        char *short_options = NULL;
>
> -       if ((long_options = calloc(1, (total_options + 1) * sizeof(struct option))) == NULL)
> +       long_options = calloc(1, (total_options + 1) * sizeof(struct option));
> +       if (long_options == NULL) {
> +               fwts_log_error(fw, "Out of memory allocating long options.");
>                return FWTS_ERROR;
> +       }
>
>        /*
>         *  Build a getopt_long options table from all the options tables
> @@ -128,6 +130,12 @@ int fwts_args_parse(fwts_framework *fw, int argc, char * const argv[])
>                                        strcat(short_options, short_name);
>                                } else {
>                                        short_options = calloc(1, len + 1);
> +                                       if (short_options == NULL) {
> +                                               fwts_log_error(fw,
> +                                                       "Out of memory "
> +                                                       "allocating options.");
> +                                               return FWTS_ERROR;
> +                                       }
>                                        strcpy(short_options, short_name);
>                                }
>                        }
> @@ -291,7 +299,8 @@ int fwts_args_free(void)
>
>  /*
>  *  fwts_args_comma_list
> - *     given a comma separated list, return a string of space separated terms
> + *     given a comma separated list, return a string of space separated terms.
> + *     returns NULL if failed
>  */
>  char *fwts_args_comma_list(const char *arg)
>  {
> @@ -322,6 +331,7 @@ char *fwts_args_comma_list(const char *arg)
>        /* Any empty list should return an empty string and not NULL */
>        if (retstr == NULL)
>                retstr = calloc(1, 1);
> +               /* Return NULL on calloc failure must be handled by caller */
>
>        return retstr;
>  }
> diff --git a/src/lib/src/fwts_framework.c b/src/lib/src/fwts_framework.c
> index 3f58c12..21535f2 100644
> --- a/src/lib/src/fwts_framework.c
> +++ b/src/lib/src/fwts_framework.c
> @@ -125,7 +125,10 @@ static int fwts_framework_compare_priority(void *data1, void *data2)
>
>  /*
>  * fwts_framework_test_add()
> - *    register a test, called by FWTS_REGISTER() macro
> + *    register a test, called by FWTS_REGISTER() macro.
> + *    this is called very early, so any errors need to
> + *    be reported to stderr because the logging engine
> + *    is not set up yet.
>  */
>  void fwts_framework_test_add(const char *name,
>        fwts_framework_ops *ops,
> @@ -159,8 +162,17 @@ void fwts_framework_test_add(const char *name,
>        fwts_list_add_ordered(&fwts_framework_test_list, new_test, fwts_framework_compare_priority);
>
>        /* Add any options and handler, if they exists */
> -       if (ops->options && ops->options_handler)
> -               fwts_args_add_options(ops->options, ops->options_handler, ops->options_check);
> +       if (ops->options && ops->options_handler) {
> +               int ret;
> +
> +               ret = fwts_args_add_options(ops->options, ops->options_handler,
> +                       ops->options_check);
> +               if (ret == FWTS_ERROR) {
> +                       fprintf(stderr, "FATAL: Could not allocate memory "
> +                               "for getopt options handler.");
> +                       exit(EXIT_FAILURE);
> +               }
> +       }
>  }
>
>  /*
> @@ -1059,7 +1071,10 @@ int fwts_framework_args(const int argc, char **argv)
>        if ((fw = (fwts_framework *)calloc(1, sizeof(fwts_framework))) == NULL)
>                return FWTS_ERROR;
>
> -       fwts_args_add_options(fwts_framework_options, fwts_framework_options_handler, NULL);
> +       ret = fwts_args_add_options(fwts_framework_options,
> +               fwts_framework_options_handler, NULL);
> +       if (ret == FWTS_ERROR)
> +               return ret;
>
>        fw->firmware_type = fwts_firmware_detect();
>
> --
> 1.7.9
>
Acked-by: Keng-Yu Lin <kengyu@canonical.com>
Alex Hung - March 7, 2012, 3 a.m.
On 03/02/2012 07:11 PM, Colin King wrote:
> From: Colin Ian King<colin.king@canonical.com>
>
> Signed-off-by: Colin Ian King<colin.king@canonical.com>
> ---
>   src/lib/src/fwts_args.c      |   16 +++++++++++++---
>   src/lib/src/fwts_framework.c |   23 +++++++++++++++++++----
>   2 files changed, 32 insertions(+), 7 deletions(-)
>
> diff --git a/src/lib/src/fwts_args.c b/src/lib/src/fwts_args.c
> index 9837959..11342cf 100644
> --- a/src/lib/src/fwts_args.c
> +++ b/src/lib/src/fwts_args.c
> @@ -100,11 +100,13 @@ int fwts_args_parse(fwts_framework *fw, int argc, char * const argv[])
>   	int c;
>   	int option_index;
>   	int ret = FWTS_OK;
> -
>   	char *short_options = NULL;
>
> -	if ((long_options = calloc(1, (total_options + 1) * sizeof(struct option))) == NULL)
> +	long_options = calloc(1, (total_options + 1) * sizeof(struct option));
> +	if (long_options == NULL) {
> +		fwts_log_error(fw, "Out of memory allocating long options.");
>   		return FWTS_ERROR;
> +	}
>
>   	/*
>   	 *  Build a getopt_long options table from all the options tables
> @@ -128,6 +130,12 @@ int fwts_args_parse(fwts_framework *fw, int argc, char * const argv[])
>   					strcat(short_options, short_name);
>   				} else {
>   					short_options = calloc(1, len + 1);
> +					if (short_options == NULL) {
> +						fwts_log_error(fw,
> +							"Out of memory "
> +							"allocating options.");
> +						return FWTS_ERROR;
> +					}
>   					strcpy(short_options, short_name);
>   				}
>   			}
> @@ -291,7 +299,8 @@ int fwts_args_free(void)
>
>   /*
>    *  fwts_args_comma_list
> - *	given a comma separated list, return a string of space separated terms
> + *	given a comma separated list, return a string of space separated terms.
> + *	returns NULL if failed
>    */
>   char *fwts_args_comma_list(const char *arg)
>   {
> @@ -322,6 +331,7 @@ char *fwts_args_comma_list(const char *arg)
>   	/* Any empty list should return an empty string and not NULL */
>   	if (retstr == NULL)
>   		retstr = calloc(1, 1);
> +		/* Return NULL on calloc failure must be handled by caller */
>
>   	return retstr;
>   }
> diff --git a/src/lib/src/fwts_framework.c b/src/lib/src/fwts_framework.c
> index 3f58c12..21535f2 100644
> --- a/src/lib/src/fwts_framework.c
> +++ b/src/lib/src/fwts_framework.c
> @@ -125,7 +125,10 @@ static int fwts_framework_compare_priority(void *data1, void *data2)
>
>   /*
>    * fwts_framework_test_add()
> - *    register a test, called by FWTS_REGISTER() macro
> + *    register a test, called by FWTS_REGISTER() macro.
> + *    this is called very early, so any errors need to
> + *    be reported to stderr because the logging engine
> + *    is not set up yet.
>    */
>   void fwts_framework_test_add(const char *name,
>   	fwts_framework_ops *ops,
> @@ -159,8 +162,17 @@ void fwts_framework_test_add(const char *name,
>   	fwts_list_add_ordered(&fwts_framework_test_list, new_test, fwts_framework_compare_priority);
>
>   	/* Add any options and handler, if they exists */
> -	if (ops->options&&  ops->options_handler)
> -		fwts_args_add_options(ops->options, ops->options_handler, ops->options_check);
> +	if (ops->options&&  ops->options_handler) {
> +		int ret;
> +
> +		ret = fwts_args_add_options(ops->options, ops->options_handler,
> +			ops->options_check);
> +		if (ret == FWTS_ERROR) {
> +			fprintf(stderr, "FATAL: Could not allocate memory "
> +				"for getopt options handler.");
> +			exit(EXIT_FAILURE);
> +		}
> +	}
>   }
>
>   /*
> @@ -1059,7 +1071,10 @@ int fwts_framework_args(const int argc, char **argv)
>   	if ((fw = (fwts_framework *)calloc(1, sizeof(fwts_framework))) == NULL)
>   		return FWTS_ERROR;
>
> -	fwts_args_add_options(fwts_framework_options, fwts_framework_options_handler, NULL);
> +	ret = fwts_args_add_options(fwts_framework_options,
> +		fwts_framework_options_handler, NULL);
> +	if (ret == FWTS_ERROR)
> +		return ret;
>
>   	fw->firmware_type = fwts_firmware_detect();
>
Acked-by: Alex Hung <alex.hung@canonical.com>

Patch

diff --git a/src/lib/src/fwts_args.c b/src/lib/src/fwts_args.c
index 9837959..11342cf 100644
--- a/src/lib/src/fwts_args.c
+++ b/src/lib/src/fwts_args.c
@@ -100,11 +100,13 @@  int fwts_args_parse(fwts_framework *fw, int argc, char * const argv[])
 	int c;
 	int option_index;
 	int ret = FWTS_OK;
-
 	char *short_options = NULL;
 
-	if ((long_options = calloc(1, (total_options + 1) * sizeof(struct option))) == NULL)
+	long_options = calloc(1, (total_options + 1) * sizeof(struct option));
+	if (long_options == NULL) {
+		fwts_log_error(fw, "Out of memory allocating long options.");
 		return FWTS_ERROR;
+	}
 
 	/*
 	 *  Build a getopt_long options table from all the options tables
@@ -128,6 +130,12 @@  int fwts_args_parse(fwts_framework *fw, int argc, char * const argv[])
 					strcat(short_options, short_name);
 				} else {
 					short_options = calloc(1, len + 1);
+					if (short_options == NULL) {
+						fwts_log_error(fw, 
+							"Out of memory "
+							"allocating options.");
+						return FWTS_ERROR;
+					}
 					strcpy(short_options, short_name);
 				}
 			}
@@ -291,7 +299,8 @@  int fwts_args_free(void)
 
 /*
  *  fwts_args_comma_list
- *	given a comma separated list, return a string of space separated terms
+ *	given a comma separated list, return a string of space separated terms.
+ *	returns NULL if failed
  */
 char *fwts_args_comma_list(const char *arg)
 {
@@ -322,6 +331,7 @@  char *fwts_args_comma_list(const char *arg)
 	/* Any empty list should return an empty string and not NULL */
 	if (retstr == NULL)
 		retstr = calloc(1, 1);
+		/* Return NULL on calloc failure must be handled by caller */
 
 	return retstr;
 }
diff --git a/src/lib/src/fwts_framework.c b/src/lib/src/fwts_framework.c
index 3f58c12..21535f2 100644
--- a/src/lib/src/fwts_framework.c
+++ b/src/lib/src/fwts_framework.c
@@ -125,7 +125,10 @@  static int fwts_framework_compare_priority(void *data1, void *data2)
 
 /*
  * fwts_framework_test_add()
- *    register a test, called by FWTS_REGISTER() macro
+ *    register a test, called by FWTS_REGISTER() macro.
+ *    this is called very early, so any errors need to
+ *    be reported to stderr because the logging engine
+ *    is not set up yet.
  */
 void fwts_framework_test_add(const char *name,
 	fwts_framework_ops *ops,
@@ -159,8 +162,17 @@  void fwts_framework_test_add(const char *name,
 	fwts_list_add_ordered(&fwts_framework_test_list, new_test, fwts_framework_compare_priority);
 
 	/* Add any options and handler, if they exists */
-	if (ops->options && ops->options_handler)
-		fwts_args_add_options(ops->options, ops->options_handler, ops->options_check);
+	if (ops->options && ops->options_handler) {
+		int ret;
+
+		ret = fwts_args_add_options(ops->options, ops->options_handler,
+			ops->options_check);
+		if (ret == FWTS_ERROR) {
+			fprintf(stderr, "FATAL: Could not allocate memory "
+				"for getopt options handler.");
+			exit(EXIT_FAILURE);
+		}
+	}
 }
 
 /*
@@ -1059,7 +1071,10 @@  int fwts_framework_args(const int argc, char **argv)
 	if ((fw = (fwts_framework *)calloc(1, sizeof(fwts_framework))) == NULL)
 		return FWTS_ERROR;
 
-	fwts_args_add_options(fwts_framework_options, fwts_framework_options_handler, NULL);
+	ret = fwts_args_add_options(fwts_framework_options,
+		fwts_framework_options_handler, NULL);
+	if (ret == FWTS_ERROR)
+		return ret;
 
 	fw->firmware_type = fwts_firmware_detect();