mirror of
git://gcc.gnu.org/git/gcc.git
synced 2025-04-13 21:01:29 +08:00
2009-05-13 Taras Glek <tglek@mozilla.com>
gcc/ * attribs.c moved out attribute registration into register_attribute * doc/plugins.texi Documented register_attribute and PLUGIN_ATTRIBUTES * gcc-plugin.h Added forward decl for register_attribute * plugin.c Added PLUGIN_ATTRIBUTES boilerplate * plugin.h Added PLUGIN_ATTRIBUTES gcc/testsuite/ * g++.dg/plugin/attribute_plugin-test-1.C Testcase input for custom attributes and decl smashing * g++.dg/plugin/attribute_plugin.c Testcase plugin to test user attributes * g++.dg/plugin/dumb_plugin.c Fixed typo * g++.dg/plugin/plugin.exp Added attribute_plugin test From-SVN: r147516
This commit is contained in:
parent
1806edae58
commit
d1c8e08a0c
@ -1,3 +1,11 @@
|
||||
2009-05-13 Taras Glek <tglek@mozilla.com>
|
||||
|
||||
* attribs.c moved out attribute registration into register_attribute
|
||||
* doc/plugins.texi Documented register_attribute and PLUGIN_ATTRIBUTES
|
||||
* gcc-plugin.h Added forward decl for register_attribute
|
||||
* plugin.c Added PLUGIN_ATTRIBUTES boilerplate
|
||||
* plugin.h Added PLUGIN_ATTRIBUTES
|
||||
|
||||
2009-05-14 Dave Korn <dave.korn.cygwin@gmail.com>
|
||||
|
||||
* config/i386/msformat-c.c (ms_printf_length_specs): Use enumeration
|
||||
|
@ -33,6 +33,7 @@ along with GCC; see the file COPYING3. If not see
|
||||
#include "target.h"
|
||||
#include "langhooks.h"
|
||||
#include "hashtab.h"
|
||||
#include "plugin.h"
|
||||
|
||||
static void init_attributes (void);
|
||||
|
||||
@ -182,18 +183,27 @@ init_attributes (void)
|
||||
for (i = 0; i < ARRAY_SIZE (attribute_tables); i++)
|
||||
for (k = 0; attribute_tables[i][k].name != NULL; k++)
|
||||
{
|
||||
register_attribute (&attribute_tables[i][k]);
|
||||
}
|
||||
invoke_plugin_callbacks (PLUGIN_ATTRIBUTES, NULL);
|
||||
attributes_initialized = true;
|
||||
}
|
||||
|
||||
/* Insert a single ATTR into the attribute table. */
|
||||
|
||||
void
|
||||
register_attribute (const struct attribute_spec *attr)
|
||||
{
|
||||
struct substring str;
|
||||
const void **slot;
|
||||
|
||||
str.str = attribute_tables[i][k].name;
|
||||
str.length = strlen (attribute_tables[i][k].name);
|
||||
str.str = attr->name;
|
||||
str.length = strlen (str.str);
|
||||
slot = (const void **)htab_find_slot_with_hash (attribute_hash, &str,
|
||||
substring_hash (str.str, str.length),
|
||||
INSERT);
|
||||
gcc_assert (!*slot);
|
||||
*slot = &attribute_tables[i][k];
|
||||
}
|
||||
attributes_initialized = true;
|
||||
*slot = attr;
|
||||
}
|
||||
|
||||
/* Return the spec for the attribute named NAME. */
|
||||
|
@ -71,6 +71,7 @@ enum plugin_event
|
||||
PLUGIN_FINISH_UNIT, /* Useful for summary processing. */
|
||||
PLUGIN_CXX_CP_PRE_GENERICIZE, /* Allows to see low level AST in C++ FE. */
|
||||
PLUGIN_FINISH, /* Called before GCC exits. */
|
||||
PLUGIN_ATTRIBUTES, /* Called during attribute registration */
|
||||
PLUGIN_EVENT_LAST /* Dummy event used for indexing callback
|
||||
array. */
|
||||
@};
|
||||
@ -135,3 +136,35 @@ plugin_init (const char *plugin_name, int argc, struct plugin_argument *argv)
|
||||
...
|
||||
@}
|
||||
@end smallexample
|
||||
@section Registering custom attributes
|
||||
|
||||
For analysis purposes it is useful to be able to add custom attributes.
|
||||
|
||||
The @code{PLUGIN_ATTRIBUTES} callback is called during attribute
|
||||
registration. Use the @code{register_attribute} function to register
|
||||
custom attributes.
|
||||
|
||||
@smallexample
|
||||
/* Attribute handler callback */
|
||||
static tree
|
||||
handle_user_attribute (tree *node, tree name, tree args,
|
||||
int flags, bool *no_add_attrs)
|
||||
@{
|
||||
return NULL_TREE;
|
||||
@}
|
||||
|
||||
/* Attribute definition */
|
||||
static struct attribute_spec user_attr =
|
||||
@{ "user", 1, 1, false, false, false, handle_user_attribute @};
|
||||
|
||||
/* Plugin callback called during attribute registration.
|
||||
Registered with register_callback (plugin_name, PLUGIN_ATTRIBUTES, register_attributes, NULL)
|
||||
*/
|
||||
static void
|
||||
register_attributes (void *event_data, void *data)
|
||||
@{
|
||||
warning (0, G_("Callback to register attributes"));
|
||||
register_attribute (&user_attr);
|
||||
@}
|
||||
|
||||
@end smallexample
|
||||
|
@ -29,6 +29,7 @@ enum plugin_event
|
||||
PLUGIN_CXX_CP_PRE_GENERICIZE, /* Allows to see low level AST in C++ FE. */
|
||||
PLUGIN_FINISH, /* Called before GCC exits. */
|
||||
PLUGIN_INFO, /* Information about the plugin */
|
||||
PLUGIN_ATTRIBUTES, /* Called during attribute registration. */
|
||||
PLUGIN_EVENT_LAST /* Dummy event used for indexing callback
|
||||
array. */
|
||||
};
|
||||
|
@ -493,6 +493,7 @@ register_callback (const char *plugin_name,
|
||||
case PLUGIN_FINISH_TYPE:
|
||||
case PLUGIN_FINISH_UNIT:
|
||||
case PLUGIN_CXX_CP_PRE_GENERICIZE:
|
||||
case PLUGIN_ATTRIBUTES:
|
||||
case PLUGIN_FINISH:
|
||||
{
|
||||
struct callback_info *new_callback;
|
||||
@ -534,6 +535,7 @@ invoke_plugin_callbacks (enum plugin_event event, void *gcc_data)
|
||||
case PLUGIN_FINISH_TYPE:
|
||||
case PLUGIN_FINISH_UNIT:
|
||||
case PLUGIN_CXX_CP_PRE_GENERICIZE:
|
||||
case PLUGIN_ATTRIBUTES:
|
||||
case PLUGIN_FINISH:
|
||||
{
|
||||
/* Iterate over every callback registered with this event and
|
||||
|
@ -22,6 +22,8 @@ along with GCC; see the file COPYING3. If not see
|
||||
|
||||
#include "gcc-plugin.h"
|
||||
|
||||
struct attribute_spec;
|
||||
|
||||
extern void add_new_plugin (const char *);
|
||||
extern void parse_plugin_arg_opt (const char *);
|
||||
extern void invoke_plugin_callbacks (enum plugin_event, void *);
|
||||
@ -33,4 +35,8 @@ extern void print_plugins_versions (FILE *file, const char *indent);
|
||||
extern void print_plugins_help (FILE *file, const char *indent);
|
||||
extern void finalize_plugins (void);
|
||||
|
||||
/* In attribs.c. */
|
||||
|
||||
extern void register_attribute (const struct attribute_spec *attr);
|
||||
|
||||
#endif /* PLUGIN_H */
|
||||
|
@ -1,3 +1,9 @@
|
||||
2009-05-13 Taras Glek <tglek@mozilla.com>
|
||||
* g++.dg/plugin/attribute_plugin-test-1.C Testcase input for custom attributes and decl smashing
|
||||
* g++.dg/plugin/attribute_plugin.c Testcase plugin to test user attributes
|
||||
* g++.dg/plugin/dumb_plugin.c Fixed typo
|
||||
* g++.dg/plugin/plugin.exp Added attribute_plugin test
|
||||
|
||||
2009-05-14 Jakub Jelinek <jakub@redhat.com>
|
||||
|
||||
PR fortran/39865
|
||||
|
16
gcc/testsuite/g++.dg/plugin/attribute_plugin-test-1.C
Normal file
16
gcc/testsuite/g++.dg/plugin/attribute_plugin-test-1.C
Normal file
@ -0,0 +1,16 @@
|
||||
// { dg-warning "Callback to register attributes" }
|
||||
|
||||
void normal_func (char c, char c2);
|
||||
void normal_func (char __attribute__((user("param"))) c, char);
|
||||
void normal_func (char c, char __attribute__((user("param"))) c2)
|
||||
{
|
||||
} // { dg-warning "attribute 'user' on param 'c' of function normal_func" }
|
||||
// { dg-warning "attribute 'user' on param 'c2' of function normal_func" "" { target *-*-* } 7 }
|
||||
|
||||
class Foo {
|
||||
void method (char __attribute__((user("param"))) c);
|
||||
};
|
||||
|
||||
void Foo::method(char c)
|
||||
{
|
||||
} // { dg-warning "attribute 'user' on param 'c' of function method" }
|
66
gcc/testsuite/g++.dg/plugin/attribute_plugin.c
Normal file
66
gcc/testsuite/g++.dg/plugin/attribute_plugin.c
Normal file
@ -0,0 +1,66 @@
|
||||
/* Demonstrates how to add custom attributes */
|
||||
|
||||
#include <stdlib.h>
|
||||
#include "config.h"
|
||||
#include "system.h"
|
||||
#include "coretypes.h"
|
||||
#include "tree.h"
|
||||
#include "tree-pass.h"
|
||||
#include "intl.h"
|
||||
#include "gcc-plugin.h"
|
||||
|
||||
/* Attribute handler callback */
|
||||
|
||||
static tree
|
||||
handle_user_attribute (tree *node, tree name, tree args,
|
||||
int flags, bool *no_add_attrs)
|
||||
{
|
||||
return NULL_TREE;
|
||||
}
|
||||
|
||||
/* Attribute definition */
|
||||
|
||||
static struct attribute_spec user_attr =
|
||||
{ "user", 1, 1, false, false, false, handle_user_attribute };
|
||||
|
||||
/* Plugin callback called during attribute registration */
|
||||
|
||||
static void
|
||||
register_attributes (void *event_data, void *data)
|
||||
{
|
||||
warning (0, G_("Callback to register attributes"));
|
||||
register_attribute (&user_attr);
|
||||
}
|
||||
|
||||
/* Callback function to invoke before the function body is genericized. */
|
||||
|
||||
void
|
||||
handle_pre_generic (void *event_data, void *data)
|
||||
{
|
||||
tree fndecl = (tree) event_data;
|
||||
tree arg;
|
||||
for (arg = DECL_ARGUMENTS(fndecl); arg; arg = TREE_CHAIN (arg)) {
|
||||
tree attr;
|
||||
for (attr = DECL_ATTRIBUTES (arg); attr; attr = TREE_CHAIN (attr)) {
|
||||
tree attrname = TREE_PURPOSE (attr);
|
||||
tree attrargs = TREE_VALUE (attr);
|
||||
warning (0, G_("attribute '%s' on param '%s' of function %s"),
|
||||
IDENTIFIER_POINTER (attrname),
|
||||
IDENTIFIER_POINTER (DECL_NAME (arg)),
|
||||
IDENTIFIER_POINTER (DECL_NAME (fndecl))
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int
|
||||
plugin_init (const char *plugin_name,
|
||||
struct plugin_gcc_version *version,
|
||||
int argc, struct plugin_argument *argv)
|
||||
{
|
||||
register_callback (plugin_name, PLUGIN_CXX_CP_PRE_GENERICIZE,
|
||||
handle_pre_generic, NULL);
|
||||
|
||||
register_callback (plugin_name, PLUGIN_ATTRIBUTES, register_attributes, NULL);
|
||||
return 0;
|
||||
}
|
@ -21,7 +21,7 @@ handle_struct (void *event_data, void *data)
|
||||
IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (type))));
|
||||
}
|
||||
|
||||
/* Callback function to invoke before the program is genericized. */
|
||||
/* Callback function to invoke before the function body is genericized. */
|
||||
|
||||
void
|
||||
handle_pre_generic (void *event_data, void *data)
|
||||
|
@ -47,6 +47,7 @@ load_lib plugin-support.exp
|
||||
# Specify the plugin source file and the associated test files in a list.
|
||||
# plugin_test_list={ {plugin1 test1 test2 ...} {plugin2 test1 ...} ... }
|
||||
set plugin_test_list [list \
|
||||
{ attribute_plugin.c attribute_plugin-test-1.C } \
|
||||
{ selfassign.c self-assign-test-1.C self-assign-test-2.C self-assign-test-3.C } \
|
||||
{ dumb_plugin.c dumb-plugin-test-1.C } ]
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user