1*38fd1498Szrj /* Copyright (C) 2013-2018 Free Software Foundation, Inc. 2*38fd1498Szrj 3*38fd1498Szrj This file is part of GCC. 4*38fd1498Szrj 5*38fd1498Szrj GCC is free software; you can redistribute it and/or modify it under 6*38fd1498Szrj the terms of the GNU General Public License as published by the Free 7*38fd1498Szrj Software Foundation; either version 3, or (at your option) any later 8*38fd1498Szrj version. 9*38fd1498Szrj 10*38fd1498Szrj GCC is distributed in the hope that it will be useful, but WITHOUT ANY 11*38fd1498Szrj WARRANTY; without even the implied warranty of MERCHANTABILITY or 12*38fd1498Szrj FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 13*38fd1498Szrj for more details. 14*38fd1498Szrj 15*38fd1498Szrj You should have received a copy of the GNU General Public License 16*38fd1498Szrj along with GCC; see the file COPYING3. If not see 17*38fd1498Szrj <http://www.gnu.org/licenses/>. */ 18*38fd1498Szrj 19*38fd1498Szrj /* Virtual Table Pointer Security. */ 20*38fd1498Szrj 21*38fd1498Szrj #ifndef VTABLE_VERIFY_H 22*38fd1498Szrj #define VTABLE_VERIFY_H 23*38fd1498Szrj 24*38fd1498Szrj #include "sbitmap.h" 25*38fd1498Szrj 26*38fd1498Szrj /* The function decl used to create calls to __VLTVtableVerify. It must 27*38fd1498Szrj be global because it needs to be initialized in the C++ front end, but 28*38fd1498Szrj used in the middle end (in the vtable verification pass). */ 29*38fd1498Szrj 30*38fd1498Szrj extern tree verify_vtbl_ptr_fndecl; 31*38fd1498Szrj 32*38fd1498Szrj /* Global variable keeping track of how many vtable map variables we 33*38fd1498Szrj have created. */ 34*38fd1498Szrj extern unsigned num_vtable_map_nodes; 35*38fd1498Szrj 36*38fd1498Szrj /* Keep track of how many virtual calls we are actually verifying. */ 37*38fd1498Szrj extern int total_num_virtual_calls; 38*38fd1498Szrj extern int total_num_verified_vcalls; 39*38fd1498Szrj 40*38fd1498Szrj /* Each vtable map variable corresponds to a virtual class. Each 41*38fd1498Szrj vtable map variable has a hash table associated with it, that keeps 42*38fd1498Szrj track of the vtable pointers for which we have generated a call to 43*38fd1498Szrj __VLTRegisterPair (with the current vtable map variable). This is 44*38fd1498Szrj the hash table node that is used for each entry in this hash table 45*38fd1498Szrj of vtable pointers. 46*38fd1498Szrj 47*38fd1498Szrj Sometimes there are multiple valid vtable pointer entries that use 48*38fd1498Szrj the same vtable pointer decl with different offsets. Therefore, 49*38fd1498Szrj for each vtable pointer in the hash table, there is also an array 50*38fd1498Szrj of offsets used with that vtable. */ 51*38fd1498Szrj 52*38fd1498Szrj struct vtable_registration 53*38fd1498Szrj { 54*38fd1498Szrj tree vtable_decl; /* The var decl of the vtable. */ 55*38fd1498Szrj vec<unsigned> offsets; /* The offsets array. */ 56*38fd1498Szrj }; 57*38fd1498Szrj 58*38fd1498Szrj struct registration_hasher : nofree_ptr_hash <struct vtable_registration> 59*38fd1498Szrj { 60*38fd1498Szrj static inline hashval_t hash (const vtable_registration *); 61*38fd1498Szrj static inline bool equal (const vtable_registration *, 62*38fd1498Szrj const vtable_registration *); 63*38fd1498Szrj }; 64*38fd1498Szrj 65*38fd1498Szrj typedef hash_table<registration_hasher> register_table_type; 66*38fd1498Szrj typedef register_table_type::iterator registration_iterator_type; 67*38fd1498Szrj 68*38fd1498Szrj /* This struct is used to represent the class hierarchy information 69*38fd1498Szrj that we need. Each vtable map variable has an associated class 70*38fd1498Szrj hierarchy node (struct vtv_graph_node). Note: In this struct, 71*38fd1498Szrj 'children' means immediate descendants in the class hierarchy; 72*38fd1498Szrj 'descendant' means any descendant however many levels deep. */ 73*38fd1498Szrj 74*38fd1498Szrj struct vtv_graph_node { 75*38fd1498Szrj tree class_type; /* The record_type of the class. */ 76*38fd1498Szrj unsigned class_uid; /* A unique, monotonically 77*38fd1498Szrj ascending id for class node. 78*38fd1498Szrj Each vtable map node also has 79*38fd1498Szrj an id. The class uid is the 80*38fd1498Szrj same as the vtable map node id 81*38fd1498Szrj for nodes corresponding to the 82*38fd1498Szrj same class. */ 83*38fd1498Szrj unsigned num_processed_children; /* # of children for whom we have 84*38fd1498Szrj computed the class hierarchy 85*38fd1498Szrj transitive closure. */ 86*38fd1498Szrj vec<struct vtv_graph_node *> parents; /* Vector of parents in the graph. */ 87*38fd1498Szrj vec<struct vtv_graph_node *> children; /* Vector of children in the graph.*/ 88*38fd1498Szrj sbitmap descendants; /* Bitmap representing all this node's 89*38fd1498Szrj descendants in the graph. */ 90*38fd1498Szrj }; 91*38fd1498Szrj 92*38fd1498Szrj /* This is the node used for our hashtable of vtable map variable 93*38fd1498Szrj information. When we create a vtable map variable (var decl) we 94*38fd1498Szrj put it into one of these nodes; create a corresponding 95*38fd1498Szrj vtv_graph_node for our class hierarchy info and store that in this 96*38fd1498Szrj node; generate a unique (monotonically ascending) id for both the 97*38fd1498Szrj vtbl_map_node and the vtv_graph_node; and insert the node into two 98*38fd1498Szrj data structures (to make it easy to find in several different 99*38fd1498Szrj ways): 1). A hash table ("vtbl_map_hash" in vtable-verify.c). 100*38fd1498Szrj This gives us an easy way to check to see if we already have a node 101*38fd1498Szrj for the vtable map variable or not; and 2). An array (vector) of 102*38fd1498Szrj vtbl_map_nodes, where the array index corresponds to the unique id 103*38fd1498Szrj of the vtbl_map_node, which gives us an easy way to use bitmaps to 104*38fd1498Szrj represent and find the vtable map nodes. */ 105*38fd1498Szrj 106*38fd1498Szrj struct vtbl_map_node { 107*38fd1498Szrj tree vtbl_map_decl; /* The var decl for the vtable map 108*38fd1498Szrj variable. */ 109*38fd1498Szrj tree class_name; /* The DECL_ASSEMBLER_NAME of the 110*38fd1498Szrj class. */ 111*38fd1498Szrj struct vtv_graph_node *class_info; /* Our class hierarchy info for the 112*38fd1498Szrj class. */ 113*38fd1498Szrj unsigned uid; /* The unique id for the vtable map 114*38fd1498Szrj variable. */ 115*38fd1498Szrj struct vtbl_map_node *next, *prev; /* Pointers for the linked list 116*38fd1498Szrj structure. */ 117*38fd1498Szrj register_table_type *registered; /* Hashtable of vtable pointers for which 118*38fd1498Szrj we have generated a _VLTRegisterPair 119*38fd1498Szrj call with this vtable map variable. */ 120*38fd1498Szrj bool is_used; /* Boolean indicating if we used this vtable map 121*38fd1498Szrj variable in a call to __VLTVerifyVtablePointer. */ 122*38fd1498Szrj }; 123*38fd1498Szrj 124*38fd1498Szrj /* Controls debugging for vtable verification. */ 125*38fd1498Szrj extern bool vtv_debug; 126*38fd1498Szrj 127*38fd1498Szrj /* The global vector of vtbl_map_nodes. */ 128*38fd1498Szrj extern vec<struct vtbl_map_node *> vtbl_map_nodes_vec; 129*38fd1498Szrj 130*38fd1498Szrj /* The global vectors for mangled class names for anonymous classes. */ 131*38fd1498Szrj extern GTY(()) vec<tree, va_gc> *vtbl_mangled_name_types; 132*38fd1498Szrj extern GTY(()) vec<tree, va_gc> *vtbl_mangled_name_ids; 133*38fd1498Szrj 134*38fd1498Szrj extern void vtbl_register_mangled_name (tree, tree); 135*38fd1498Szrj extern struct vtbl_map_node *vtbl_map_get_node (tree); 136*38fd1498Szrj extern struct vtbl_map_node *find_or_create_vtbl_map_node (tree); 137*38fd1498Szrj extern void vtbl_map_node_class_insert (struct vtbl_map_node *, unsigned); 138*38fd1498Szrj extern bool vtbl_map_node_registration_find (struct vtbl_map_node *, 139*38fd1498Szrj tree, unsigned); 140*38fd1498Szrj extern bool vtbl_map_node_registration_insert (struct vtbl_map_node *, 141*38fd1498Szrj tree, unsigned); 142*38fd1498Szrj 143*38fd1498Szrj #endif /* VTABLE_VERIFY_H */ 144