Commit 3c8348d3 by Nick Clifton Committed by Nick Clifton

config.gcc (sh-symbianelf): Replace definition of extra_objs with separate…

config.gcc (sh-symbianelf): Replace definition of extra_objs with separate definitions of c_target_objs and...

        * config.gcc (sh-symbianelf): Replace definition of extra_objs
        with separate definitions of c_target_objs and cxx_target_objs.
        * config/sh/t-sh: Add rules to build symbian-cxx.o, symbian-c.o
        and symbian-base.o.
        * config/sh/sh.c (TARGET_CXX_INPUT_EXPORT_CLASS): Use
        sh_symbian_import_export_class.
        * config/sh/sh-protos.h: Fix names of exported symbian functions.
        * config/sh/symbian.c: Delete, moving code into...
        * config/sh/symbian-base.c: ... here
        * config/sh/symbian-c.c: ... and here
        * config/sh/symbian-cxx.c: ... and here.

From-SVN: r152323
parent 08a4a761
2009-09-30 Nick Clifton <nickc@redhat.com>
* config.gcc (sh-symbianelf): Replace definition of extra_objs
with separate definitions of c_target_objs and cxx_target_objs.
* config/sh/t-sh: Add rules to build symbian-cxx.o, symbian-c.o
and symbian-base.o.
* config/sh/sh.c (TARGET_CXX_INPUT_EXPORT_CLASS): Use
sh_symbian_import_export_class.
* config/sh/sh-protos.h: Fix names of exported symbian functions.
* config/sh/symbian.c: Delete, moving code into...
* config/sh/symbian-base.c: ... here
* config/sh/symbian-c.c: ... and here
* config/sh/symbian-cxx.c: ... and here.
2009-09-30 Uros Bizjak <ubizjak@gmail.com> 2009-09-30 Uros Bizjak <ubizjak@gmail.com>
PR target/22093 PR target/22093
...@@ -2184,7 +2184,8 @@ sh-*-symbianelf* | sh[12346l]*-*-symbianelf* | \ ...@@ -2184,7 +2184,8 @@ sh-*-symbianelf* | sh[12346l]*-*-symbianelf* | \
*-*-symbianelf*) *-*-symbianelf*)
tmake_file="sh/t-symbian" tmake_file="sh/t-symbian"
tm_file="sh/symbian-pre.h sh/little.h ${tm_file} sh/symbian-post.h" tm_file="sh/symbian-pre.h sh/little.h ${tm_file} sh/symbian-post.h"
extra_objs="symbian.o" c_target_objs="symbian-base.o symbian-c.o"
cxx_target_objs="symbian-base.o symbian-cxx.o"
extra_parts="crt1.o crti.o crtn.o crtbegin.o crtend.o crtbeginS.o crtendS.o" extra_parts="crt1.o crti.o crtn.o crtbegin.o crtend.o crtbeginS.o crtendS.o"
;; ;;
*-*-elf*) *-*-elf*)
......
...@@ -183,15 +183,15 @@ extern bool sh_hard_regno_mode_ok (unsigned int, enum machine_mode); ...@@ -183,15 +183,15 @@ extern bool sh_hard_regno_mode_ok (unsigned int, enum machine_mode);
#endif /* ! GCC_SH_PROTOS_H */ #endif /* ! GCC_SH_PROTOS_H */
#ifdef SYMBIAN #ifdef SYMBIAN
extern bool sh_symbian_dllimport_name_p (const char *);
extern const char * sh_symbian_strip_name_encoding (const char *); extern const char * sh_symbian_strip_name_encoding (const char *);
extern bool sh_symbian_dllexport_name_p (const char *); extern bool sh_symbian_is_dllexported_name (const char *);
extern int symbian_import_export_class (tree, int);
#ifdef TREE_CODE #ifdef TREE_CODE
extern bool sh_symbian_dllexport_p (tree); extern bool sh_symbian_is_dllexported (tree);
extern int sh_symbian_import_export_class (tree, int);
extern tree sh_symbian_handle_dll_attribute (tree *, tree, tree, int, bool *); extern tree sh_symbian_handle_dll_attribute (tree *, tree, tree, int, bool *);
#ifdef RTX_CODE #ifdef RTX_CODE
extern void sh_symbian_encode_section_info (tree, rtx, int); extern void sh_symbian_encode_section_info (tree, rtx, int);
#endif #endif
#endif #endif
#endif /* SYMBIAN */ #endif /* SYMBIAN */
/* header file for GCC for a Symbian OS targeted SH backend.
Copyright (C) 2004, 2005, 2007, 2009 Free Software Foundation, Inc.
Contributed by RedHat.
Most of this code is stolen from i386/winnt.c.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published
by the Free Software Foundation; either version 3, or (at your
option) any later version.
GCC is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
/* A unique character to encode declspec encoded objects. */
#define SH_SYMBIAN_FLAG_CHAR "$"
/* Unique strings to prefix exported and imported objects. */
#define DLL_IMPORT_PREFIX SH_SYMBIAN_FLAG_CHAR "i."
#define DLL_EXPORT_PREFIX SH_SYMBIAN_FLAG_CHAR "e."
/* Select the level of debugging information to display.
0 for no debugging.
1 for informative messages about decisions to add attributes
2 for verbose information about what is being done. */
#define SYMBIAN_DEBUG 0
/* #define SYMBIAN_DEBUG 1 */
/* #define SYMBIAN_DEBUG 2 */
/* Functions exported from symbian-base.c. */
extern tree sh_symbian_associated_type (tree);
/* Functions exported from symbian-[c|c++].c. */
extern bool sh_symbian_is_dllimported (tree);
...@@ -503,7 +503,7 @@ static const struct attribute_spec sh_attribute_table[] = ...@@ -503,7 +503,7 @@ static const struct attribute_spec sh_attribute_table[] =
#undef TARGET_STRIP_NAME_ENCODING #undef TARGET_STRIP_NAME_ENCODING
#define TARGET_STRIP_NAME_ENCODING sh_symbian_strip_name_encoding #define TARGET_STRIP_NAME_ENCODING sh_symbian_strip_name_encoding
#undef TARGET_CXX_IMPORT_EXPORT_CLASS #undef TARGET_CXX_IMPORT_EXPORT_CLASS
#define TARGET_CXX_IMPORT_EXPORT_CLASS symbian_import_export_class #define TARGET_CXX_IMPORT_EXPORT_CLASS sh_symbian_import_export_class
#endif /* SYMBIAN */ #endif /* SYMBIAN */
......
/* Routines for GCC for a Symbian OS targeted SH backend, shared by
both the C and C++ compilers.
Copyright (C) 2004, 2005, 2007, 2009 Free Software Foundation, Inc.
Contributed by RedHat.
Most of this code is stolen from i386/winnt.c.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published
by the Free Software Foundation; either version 3, or (at your
option) any later version.
GCC is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "tm.h"
#include "rtl.h"
#include "output.h"
#include "flags.h"
#include "tree.h"
#include "expr.h"
#include "tm_p.h"
#include "toplev.h"
#include "sh-symbian.h"
/* Return nonzero if SYMBOL is marked as being dllexport'd. */
bool
sh_symbian_is_dllexported_name (const char *symbol)
{
return strncmp (DLL_EXPORT_PREFIX, symbol,
strlen (DLL_EXPORT_PREFIX)) == 0;
}
/* Return nonzero if SYMBOL is marked as being dllimport'd. */
static bool
sh_symbian_is_dllimported_name (const char *symbol)
{
return strncmp (DLL_IMPORT_PREFIX, symbol,
strlen (DLL_IMPORT_PREFIX)) == 0;
}
/* Return nonzero if DECL is a dllexport'd object. */
bool
sh_symbian_is_dllexported (tree decl)
{
tree exp;
if ( TREE_CODE (decl) != VAR_DECL
&& TREE_CODE (decl) != FUNCTION_DECL)
return false;
exp = lookup_attribute ("dllexport", DECL_ATTRIBUTES (decl));
/* Class members get the dllexport status of their class. */
if (exp == NULL)
{
tree class = sh_symbian_associated_type (decl);
if (class)
exp = lookup_attribute ("dllexport", TYPE_ATTRIBUTES (class));
}
#if SYMBIAN_DEBUG
if (exp)
{
print_node_brief (stderr, "dllexport:", decl, 0);
fprintf (stderr, "\n");
}
else
#if SYMBIAN_DEBUG < 2
if (TREE_CODE (decl) != FUNCTION_DECL)
#endif
{
print_node_brief (stderr, "no dllexport:", decl, 0);
fprintf (stderr, "\n");
}
#endif
return exp ? true : false;
}
/* Mark a DECL as being dllimport'd. */
static void
sh_symbian_mark_dllimport (tree decl)
{
const char *oldname;
char *newname;
tree idp;
rtx rtlname;
rtx newrtl;
rtlname = XEXP (DECL_RTL (decl), 0);
if (MEM_P (rtlname))
rtlname = XEXP (rtlname, 0);
gcc_assert (GET_CODE (rtlname) == SYMBOL_REF);
oldname = XSTR (rtlname, 0);
if (sh_symbian_is_dllexported_name (oldname))
{
error ("%qE declared as both exported to and imported from a DLL",
DECL_NAME (decl));
}
else if (sh_symbian_is_dllimported_name (oldname))
{
/* Already done, but do a sanity check to prevent assembler errors. */
if (!DECL_EXTERNAL (decl) || !TREE_PUBLIC (decl))
error ("failure in redeclaration of %q+D: dllimport'd symbol lacks external linkage",
decl);
}
else
{
newname = (char *) alloca (strlen (DLL_IMPORT_PREFIX) + strlen (oldname) + 1);
sprintf (newname, "%s%s", DLL_IMPORT_PREFIX, oldname);
/* We pass newname through get_identifier to ensure it has a unique
address. RTL processing can sometimes peek inside the symbol ref
and compare the string's addresses to see if two symbols are
identical. */
idp = get_identifier (newname);
newrtl = gen_rtx_SYMBOL_REF (Pmode, IDENTIFIER_POINTER (idp));
XEXP (DECL_RTL (decl), 0) = newrtl;
}
}
/* Mark a DECL as being dllexport'd.
Note that we override the previous setting (e.g.: dllimport). */
static void
sh_symbian_mark_dllexport (tree decl)
{
const char *oldname;
char *newname;
rtx rtlname;
tree idp;
rtlname = XEXP (DECL_RTL (decl), 0);
if (MEM_P (rtlname))
rtlname = XEXP (rtlname, 0);
gcc_assert (GET_CODE (rtlname) == SYMBOL_REF);
oldname = XSTR (rtlname, 0);
if (sh_symbian_is_dllimported_name (oldname))
{
/* Remove DLL_IMPORT_PREFIX.
Note - we do not issue a warning here. In Symbian's environment it
is legitimate for a prototype to be marked as dllimport and the
corresponding definition to be marked as dllexport. The prototypes
are in headers used everywhere and the definition is in a translation
unit which has included the header in order to ensure argument
correctness. */
oldname += strlen (DLL_IMPORT_PREFIX);
DECL_DLLIMPORT_P (decl) = 0;
}
else if (sh_symbian_is_dllexported_name (oldname))
return; /* Already done. */
newname = (char *) alloca (strlen (DLL_EXPORT_PREFIX) + strlen (oldname) + 1);
sprintf (newname, "%s%s", DLL_EXPORT_PREFIX, oldname);
/* We pass newname through get_identifier to ensure it has a unique
address. RTL processing can sometimes peek inside the symbol ref
and compare the string's addresses to see if two symbols are
identical. */
idp = get_identifier (newname);
XEXP (DECL_RTL (decl), 0) =
gen_rtx_SYMBOL_REF (Pmode, IDENTIFIER_POINTER (idp));
}
void
sh_symbian_encode_section_info (tree decl, rtx rtl, int first)
{
default_encode_section_info (decl, rtl, first);
/* Mark the decl so we can tell from the rtl whether
the object is dllexport'd or dllimport'd. */
if (sh_symbian_is_dllexported (decl))
sh_symbian_mark_dllexport (decl);
else if (sh_symbian_is_dllimported (decl))
sh_symbian_mark_dllimport (decl);
/* It might be that DECL has already been marked as dllimport, but a
subsequent definition nullified that. The attribute is gone but
DECL_RTL still has (DLL_IMPORT_PREFIX) prefixed. We need to remove
that. Ditto for the DECL_DLLIMPORT_P flag. */
else if ( (TREE_CODE (decl) == FUNCTION_DECL
|| TREE_CODE (decl) == VAR_DECL)
&& DECL_RTL (decl) != NULL_RTX
&& MEM_P (DECL_RTL (decl))
&& MEM_P (XEXP (DECL_RTL (decl), 0))
&& GET_CODE (XEXP (XEXP (DECL_RTL (decl), 0), 0)) == SYMBOL_REF
&& sh_symbian_is_dllimported_name (XSTR (XEXP (XEXP (DECL_RTL (decl), 0), 0), 0)))
{
const char * oldname = XSTR (XEXP (XEXP (DECL_RTL (decl), 0), 0), 0);
/* Remove DLL_IMPORT_PREFIX. */
tree idp = get_identifier (oldname + strlen (DLL_IMPORT_PREFIX));
rtx newrtl = gen_rtx_SYMBOL_REF (Pmode, IDENTIFIER_POINTER (idp));
warning (0, "%s %q+D %s after being referenced with dllimport linkage",
TREE_CODE (decl) == VAR_DECL ? "variable" : "function",
decl, (DECL_INITIAL (decl) || !DECL_EXTERNAL (decl))
? "defined locally" : "redeclared without dllimport attribute");
XEXP (DECL_RTL (decl), 0) = newrtl;
DECL_DLLIMPORT_P (decl) = 0;
}
}
/* Return the length of a function name prefix
that starts with the character 'c'. */
static int
sh_symbian_get_strip_length (int c)
{
/* XXX Assumes strlen (DLL_EXPORT_PREFIX) == strlen (DLL_IMPORT_PREFIX). */
return (c == SH_SYMBIAN_FLAG_CHAR[0]) ? strlen (DLL_EXPORT_PREFIX) : 0;
}
/* Return a pointer to a function's name with any
and all prefix encodings stripped from it. */
const char *
sh_symbian_strip_name_encoding (const char *name)
{
int skip;
while ((skip = sh_symbian_get_strip_length (*name)))
name += skip;
return name;
}
/* Routines for C compiler part of GCC for a Symbian OS targeted SH backend.
Copyright (C) 2004, 2005, 2007, 2009 Free Software Foundation, Inc.
Contributed by RedHat.
Most of this code is stolen from i386/winnt.c.
This file is part of GCC.
GCC is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published
by the Free Software Foundation; either version 3, or (at your
option) any later version.
GCC is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3. If not see
<http://www.gnu.org/licenses/>. */
#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "tm.h"
#include "rtl.h"
#include "output.h"
#include "flags.h"
#include "tree.h"
#include "expr.h"
#include "tm_p.h"
#include "toplev.h"
#include "sh-symbian.h"
/* Return the type that we should use to determine if DECL is
imported or exported. */
tree
sh_symbian_associated_type (tree decl)
{
tree t = NULL_TREE;
/* We can just take the DECL_CONTEXT as normal. */
if (DECL_CONTEXT (decl) && TYPE_P (DECL_CONTEXT (decl)))
t = DECL_CONTEXT (decl);
return t;
}
/* Return nonzero if DECL is a dllimport'd object. */
bool
sh_symbian_is_dllimported (tree decl)
{
tree imp;
if ( TREE_CODE (decl) != VAR_DECL
&& TREE_CODE (decl) != FUNCTION_DECL)
return false;
imp = lookup_attribute ("dllimport", DECL_ATTRIBUTES (decl));
if (imp)
return true;
/* Class members get the dllimport status of their class. */
imp = sh_symbian_associated_type (decl);
if (! imp)
return false;
imp = lookup_attribute ("dllimport", TYPE_ATTRIBUTES (imp));
if (!imp)
return false;
/* Don't mark defined functions as dllimport. If the definition itself
was marked with dllimport, then sh_symbian_handle_dll_attribute reports
an error. This handles the case when the definition overrides an
earlier declaration. */
if (TREE_CODE (decl) == FUNCTION_DECL
&& DECL_INITIAL (decl)
&& ! DECL_DECLARED_INLINE_P (decl))
{
warning (OPT_Wattributes, "function %q+D is defined after prior "
"declaration as dllimport: attribute ignored",
decl);
return false;
}
/* Don't allow definitions of static data members in dllimport
class. Just ignore the attribute for vtable data. */
else if (TREE_CODE (decl) == VAR_DECL
&& TREE_STATIC (decl)
&& TREE_PUBLIC (decl)
&& !DECL_EXTERNAL (decl))
{
error ("definition of static data member %q+D of dllimport'd class",
decl);
return false;
}
return true;
}
/* Handle a "dllimport" or "dllexport" attribute;
arguments as in struct attribute_spec.handler. */
tree
sh_symbian_handle_dll_attribute (tree *pnode, tree name, tree args,
int flags, bool *no_add_attrs)
{
tree node = *pnode;
const char *attr = IDENTIFIER_POINTER (name);
/* These attributes may apply to structure and union types being
created, but otherwise should pass to the declaration involved. */
if (!DECL_P (node))
{
if (flags & ((int) ATTR_FLAG_DECL_NEXT
| (int) ATTR_FLAG_FUNCTION_NEXT
| (int) ATTR_FLAG_ARRAY_NEXT))
{
warning (OPT_Wattributes, "%qs attribute ignored", attr);
*no_add_attrs = true;
return tree_cons (name, args, NULL_TREE);
}
if (TREE_CODE (node) != RECORD_TYPE && TREE_CODE (node) != UNION_TYPE)
{
warning (OPT_Wattributes, "%qs attribute ignored", attr);
*no_add_attrs = true;
}
return NULL_TREE;
}
/* Report error on dllimport ambiguities
seen now before they cause any damage. */
else if (is_attribute_p ("dllimport", name))
{
if (TREE_CODE (node) == VAR_DECL)
{
if (DECL_INITIAL (node))
{
error ("variable %q+D definition is marked dllimport",
node);
*no_add_attrs = true;
}
/* `extern' needn't be specified with dllimport.
Specify `extern' now and hope for the best. Sigh. */
DECL_EXTERNAL (node) = 1;
/* Also, implicitly give dllimport'd variables declared within
a function global scope, unless declared static. */
if (current_function_decl != NULL_TREE && ! TREE_STATIC (node))
TREE_PUBLIC (node) = 1;
}
}
/* Report error if symbol is not accessible at global scope. */
if (!TREE_PUBLIC (node)
&& ( TREE_CODE (node) == VAR_DECL
|| TREE_CODE (node) == FUNCTION_DECL))
{
error ("external linkage required for symbol %q+D because of %qE attribute",
node, name);
*no_add_attrs = true;
}
#if SYMBIAN_DEBUG
print_node_brief (stderr, "mark node", node, 0);
fprintf (stderr, " as %s\n", attr);
#endif
return NULL_TREE;
}
int
sh_symbian_import_export_class (tree ctype ATTRIBUTE_UNUSED, int import_export)
{
return import_export;
}
...@@ -31,8 +31,8 @@ ...@@ -31,8 +31,8 @@
#define SYMBIAN_EXPORT_NAME(NAME,FILE,DECL) \ #define SYMBIAN_EXPORT_NAME(NAME,FILE,DECL) \
do \ do \
{ \ { \
if ((DECL && sh_symbian_dllexport_p (DECL)) \ if ((DECL && sh_symbian_is_dllexported (DECL)) \
|| sh_symbian_dllexport_name_p (NAME)) \ || sh_symbian_is_dllexported_name (NAME)) \
{ \ { \
fprintf ((FILE), "\t.pushsection .directive\n"); \ fprintf ((FILE), "\t.pushsection .directive\n"); \
fprintf ((FILE), "\t.asciz \"EXPORT %s\\n\"\n", \ fprintf ((FILE), "\t.asciz \"EXPORT %s\\n\"\n", \
......
...@@ -21,6 +21,28 @@ sh-c.o: $(srcdir)/config/sh/sh-c.c \ ...@@ -21,6 +21,28 @@ sh-c.o: $(srcdir)/config/sh/sh-c.c \
$(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) \ $(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) \
$(srcdir)/config/sh/sh-c.c $(srcdir)/config/sh/sh-c.c
symbian-cxx.o: \
$(srcdir)/config/sh/symbian-cxx.c \
$(srcdir)/config/sh/sh-symbian.h \
$(CONFIG_H) $(SYSTEM_H) $(TM_H) $(TREE_H) $(RTL_H) \
toplev.h output.h coretypes.h flags.h expr.h
$(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) $<
symbian-c.o: \
$(srcdir)/config/sh/symbian-c.c \
$(srcdir)/config/sh/sh-symbian.h \
$(CONFIG_H) $(SYSTEM_H) $(TM_H) $(TREE_H) $(RTL_H) \
toplev.h output.h coretypes.h flags.h expr.h
$(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) $<
symbian-base.o: \
$(srcdir)/config/sh/symbian-base.c \
$(srcdir)/config/sh/sh-symbian.h \
$(CONFIG_H) $(SYSTEM_H) $(TM_H) $(TREE_H) $(RTL_H) \
toplev.h output.h coretypes.h flags.h expr.h
$(COMPILER) -c $(ALL_COMPILERFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) $<
LIB1ASMSRC = sh/lib1funcs.asm LIB1ASMSRC = sh/lib1funcs.asm
LIB1ASMFUNCS = _ashiftrt _ashiftrt_n _ashiftlt _lshiftrt _movstr \ LIB1ASMFUNCS = _ashiftrt _ashiftrt_n _ashiftlt _lshiftrt _movstr \
_movstr_i4 _mulsi3 _sdivsi3 _sdivsi3_i4 _udivsi3 _udivsi3_i4 _set_fpscr \ _movstr_i4 _mulsi3 _sdivsi3 _sdivsi3_i4 _udivsi3 _udivsi3_i4 _set_fpscr \
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment