[prev in list] [next in list] [prev in thread] [next in thread]
List: gcc-patches
Subject: Re: *revised* PATCH: named address space support (1/2: target-independent parts)
From: "Joseph S. Myers" <joseph () codesourcery ! com>
Date: 2008-08-31 17:07:29
Message-ID: Pine.LNX.4.64.0808311641540.12423 () digraph ! polyomino ! org ! uk
[Download RAW message or body]
On Fri, 29 Aug 2008, Ben Elliston wrote:
> + if (!flag_iso)
> + {
> + addr_space_t as1 = declspecs->address_space;
> + addr_space_t as2 = TYPE_ADDR_SPACE (element_type);
> +
> + if (as1 > 0 && as2 > 0 && as1 != as2)
> + error ("incompatible address space qualifiers %qs and %qs",
> + targetm.addr_space_name (as1),
> + targetm.addr_space_name (as2));
> + }
I see no reason for this to be !flag_iso. If address spaces are in use,
the error should be given for incompatible address spaces and this is
outside the scope of ISO C.
> /* Warn about storage classes that are invalid for certain
> kinds of declarations (parameters, typenames, etc.). */
>
> + if (((declarator->kind == cdk_pointer
> + && (DECODE_QUAL_ADDR_SPACE (declarator->u.pointer_quals)) != 0)
> + || addr_space_p)
> + && targetm.addr_space_name == default_addr_space_name)
> + {
> + /* A mere warning is sure to result in improper semantics
> + at runtime. Don't bother to allow this to compile. */
> + error ("extended address space not supported for this target");
> + return 0;
> + }
This is not the right check. You should check for address spaces in the
declaration specifiers and in the qualifiers in any nested pointer
declarator, rather than arbitrarily only for a toplevel pointer
declarator as here. That probably means a check in the loop going down
through the nested declarators.
> + if (declarator->kind == cdk_pointer
> + ? (DECODE_QUAL_ADDR_SPACE (declarator->u.pointer_quals)) != 0
> + : addr_space_p)
> + {
> + const char *addrspace_name;
> +
> + /* Either declspecs or the declarator identifies the address space. */
> + if (declspecs->address_space)
> + addrspace_name = targetm.addr_space_name (declspecs->address_space);
> + else
> + addrspace_name = targetm.addr_space_name (DECODE_QUAL_ADDR_SPACE \
> (declarator->u.pointer_quals)); +
> + if (decl_context == NORMAL)
> + {
> + if (declarator->kind == cdk_function)
> + error ("%qs specified for function %qs", addrspace_name, name);
The right check is not whether the top declarator (corresponding to the
*innermost* part of the type described by the full declarator) is a
function declarator. It is whether, at any level of nested declarators,
an address space is being applied to a function type. In each place where
there is a pedwarn "ISO C forbids qualified function types", or in one
place "ISO C forbids const or volatile function types", there should be a
check for address space qualifiers (if not more generally disallowed in
that case) and this error. (There should be a testcase for each such
diagnostic.)
> + else
> + {
> + switch (storage_class)
> + {
> + case csc_auto:
> + error ("%qs combined with %<auto%> qualifier for %qs", addrspace_name, name);
> + break;
> + case csc_register:
> + error ("%qs combined with %<register%> qualifier for %qs", addrspace_name, \
> name); + break;
> + case csc_none:
> + if (current_function_scope)
> + {
> + error ("%<__ea%> specified for auto variable %qs", name);
> + break;
> + }
> + break;
For these, again the question is whether the qualifier would finally end
up applied to the variable. If you have "register int **__ea x;" you
should get the error; you should not get it for "register int *__ea *x;".
You're checking the toplevel declarator for being a pointer, but it's the
*innermost* declarator that ends up specifying the toplevel type, while
the toplevel declarator specifies the innermost type. There should be
tests for both those examples. I think this check needs to go later,
somewhere at or after
/* Now TYPE has the actual type, apart from any qualifiers in
TYPE_QUALS. */
so TYPE + TYPE_QUALS gives the final type that will be used.
> + else if (decl_context == PARM
> + && declarator->kind != cdk_array)
> + error ("%qs specified for parameter %qs", addrspace_name, name);
> + else if (decl_context == FIELD)
> + error ("%qs specified for structure field %qs", addrspace_name, name);
Likewise, you need to know if the qualifiers will end up on the parameter
or field or not (and to have associated testcases).
> diff -N -p --exclude=spu --exclude=config/spu --exclude=ea --exclude=LAST_UPDATED \
> --exclude=REVISION --exclude=ChangeLog --exclude=ChangeLog.named -r -u \
> --exclude=.svn gcc-clean/gcc/c-typeck.c gcc-nas/gcc/c-typeck.c
> --- gcc-clean/gcc/c-typeck.c 2008-08-29 11:32:47.000000000 +1000
> +++ gcc-nas/gcc/c-typeck.c 2008-08-27 12:04:08.000000000 +1000
I do not see any sign of my previous comments on the changes to this file
having been addressed, so I repeat them here:
For both places comparison operators are handled, the relevant check is
not whether an address space is other than generic, it is whether the
address spaces overlap. If not, an error must be given. If they do
overlap, both must be converted to whichever is the larger address space
(not whichever is the smaller).
Conditional expressions need similar handling.
I don't see any changes to convert_for_assignment to check the constraints
on pointer assignment (and argument passing, function return,
initialization) and address spaces.
--
Joseph S. Myers
joseph@codesourcery.com
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic