diff options
| author | Paul Thomas <pault@gcc.gnu.org> | 2006-11-10 21:06:42 +0000 |
|---|---|---|
| committer | Paul Thomas <pault@gcc.gnu.org> | 2006-11-10 21:06:42 +0000 |
| commit | d8d8121add34439d69187182bacea680468270df (patch) | |
| tree | 08f1d1862fcda9270ca787d05266443665ded1d0 /gcc/fortran/check.c | |
| parent | f70d742fc89c922a9ad5508753027eb17827369c (diff) | |
| download | gcc-d8d8121add34439d69187182bacea680468270df.zip gcc-d8d8121add34439d69187182bacea680468270df.tar.gz gcc-d8d8121add34439d69187182bacea680468270df.tar.bz2 | |
re PR fortran/29758 (Runtime segfault in RESHAPE with insufficient elements in SOURCE)
2006-11-10 Paul Thomas <pault@gcc.gnu.org>
PR fortran/29758
* check.c (gfc_check_reshape): Check that there are enough
elements in the source array as to be able to fill an array
defined by shape, when pad is absent.
2006-11-10 Paul Thomas <pault@gcc.gnu.org>
PR fortran/29758
* gfortran.dg/reshape_source_size_1.f90: New test.
From-SVN: r118664
Diffstat (limited to 'gcc/fortran/check.c')
| -rw-r--r-- | gcc/fortran/check.c | 33 |
1 files changed, 33 insertions, 0 deletions
diff --git a/gcc/fortran/check.c b/gcc/fortran/check.c index f8983bd..0c5fc13 100644 --- a/gcc/fortran/check.c +++ b/gcc/fortran/check.c @@ -2110,6 +2110,7 @@ gfc_check_reshape (gfc_expr * source, gfc_expr * shape, gfc_expr * pad, gfc_expr * order) { mpz_t size; + mpz_t nelems; int m; if (array_check (source, 0) == FAILURE) @@ -2149,6 +2150,38 @@ gfc_check_reshape (gfc_expr * source, gfc_expr * shape, if (order != NULL && array_check (order, 3) == FAILURE) return FAILURE; + if (pad == NULL + && shape->expr_type == EXPR_ARRAY + && gfc_is_constant_expr (shape) + && !(source->expr_type == EXPR_VARIABLE + && source->symtree->n.sym->as + && source->symtree->n.sym->as->type == AS_ASSUMED_SIZE)) + { + /* Check the match in size between source and destination. */ + if (gfc_array_size (source, &nelems) == SUCCESS) + { + gfc_constructor *c; + bool test; + + c = shape->value.constructor; + mpz_init_set_ui (size, 1); + for (; c; c = c->next) + mpz_mul (size, size, c->expr->value.integer); + + test = mpz_cmp (nelems, size) < 0 && mpz_cmp_ui (size, 0) > 0; + mpz_clear (nelems); + mpz_clear (size); + + if (test) + { + gfc_error ("Without padding, there are not enough elements in the " + "intrinsic RESHAPE source at %L to match the shape", + &source->where); + return FAILURE; + } + } + } + return SUCCESS; } |
