1@section Hash Tables 2@cindex Hash tables 3BFD provides a simple set of hash table functions. Routines 4are provided to initialize a hash table, to free a hash table, 5to look up a string in a hash table and optionally create an 6entry for it, and to traverse a hash table. There is 7currently no routine to delete an string from a hash table. 8 9The basic hash table does not permit any data to be stored 10with a string. However, a hash table is designed to present a 11base class from which other types of hash tables may be 12derived. These derived types may store additional information 13with the string. Hash tables were implemented in this way, 14rather than simply providing a data pointer in a hash table 15entry, because they were designed for use by the linker back 16ends. The linker may create thousands of hash table entries, 17and the overhead of allocating private data and storing and 18following pointers becomes noticeable. 19 20The basic hash table code is in @code{hash.c}. 21 22@menu 23* Creating and Freeing a Hash Table:: 24* Looking Up or Entering a String:: 25* Traversing a Hash Table:: 26* Deriving a New Hash Table Type:: 27@end menu 28 29@node Creating and Freeing a Hash Table, Looking Up or Entering a String, Hash Tables, Hash Tables 30@subsection Creating and freeing a hash table 31@findex bfd_hash_table_init 32@findex bfd_hash_table_init_n 33To create a hash table, create an instance of a @code{struct 34bfd_hash_table} (defined in @code{bfd.h}) and call 35@code{bfd_hash_table_init} (if you know approximately how many 36entries you will need, the function @code{bfd_hash_table_init_n}, 37which takes a @var{size} argument, may be used). 38@code{bfd_hash_table_init} returns @code{FALSE} if some sort of 39error occurs. 40 41@findex bfd_hash_newfunc 42The function @code{bfd_hash_table_init} take as an argument a 43function to use to create new entries. For a basic hash 44table, use the function @code{bfd_hash_newfunc}. @xref{Deriving 45a New Hash Table Type}, for why you would want to use a 46different value for this argument. 47 48@findex bfd_hash_allocate 49@code{bfd_hash_table_init} will create an objalloc which will be 50used to allocate new entries. You may allocate memory on this 51objalloc using @code{bfd_hash_allocate}. 52 53@findex bfd_hash_table_free 54Use @code{bfd_hash_table_free} to free up all the memory that has 55been allocated for a hash table. This will not free up the 56@code{struct bfd_hash_table} itself, which you must provide. 57 58@node Looking Up or Entering a String, Traversing a Hash Table, Creating and Freeing a Hash Table, Hash Tables 59@subsection Looking up or entering a string 60@findex bfd_hash_lookup 61The function @code{bfd_hash_lookup} is used both to look up a 62string in the hash table and to create a new entry. 63 64If the @var{create} argument is @code{FALSE}, @code{bfd_hash_lookup} 65will look up a string. If the string is found, it will 66returns a pointer to a @code{struct bfd_hash_entry}. If the 67string is not found in the table @code{bfd_hash_lookup} will 68return @code{NULL}. You should not modify any of the fields in 69the returns @code{struct bfd_hash_entry}. 70 71If the @var{create} argument is @code{TRUE}, the string will be 72entered into the hash table if it is not already there. 73Either way a pointer to a @code{struct bfd_hash_entry} will be 74returned, either to the existing structure or to a newly 75created one. In this case, a @code{NULL} return means that an 76error occurred. 77 78If the @var{create} argument is @code{TRUE}, and a new entry is 79created, the @var{copy} argument is used to decide whether to 80copy the string onto the hash table objalloc or not. If 81@var{copy} is passed as @code{FALSE}, you must be careful not to 82deallocate or modify the string as long as the hash table 83exists. 84 85@node Traversing a Hash Table, Deriving a New Hash Table Type, Looking Up or Entering a String, Hash Tables 86@subsection Traversing a hash table 87@findex bfd_hash_traverse 88The function @code{bfd_hash_traverse} may be used to traverse a 89hash table, calling a function on each element. The traversal 90is done in a random order. 91 92@code{bfd_hash_traverse} takes as arguments a function and a 93generic @code{void *} pointer. The function is called with a 94hash table entry (a @code{struct bfd_hash_entry *}) and the 95generic pointer passed to @code{bfd_hash_traverse}. The function 96must return a @code{boolean} value, which indicates whether to 97continue traversing the hash table. If the function returns 98@code{FALSE}, @code{bfd_hash_traverse} will stop the traversal and 99return immediately. 100 101@node Deriving a New Hash Table Type, , Traversing a Hash Table, Hash Tables 102@subsection Deriving a new hash table type 103Many uses of hash tables want to store additional information 104which each entry in the hash table. Some also find it 105convenient to store additional information with the hash table 106itself. This may be done using a derived hash table. 107 108Since C is not an object oriented language, creating a derived 109hash table requires sticking together some boilerplate 110routines with a few differences specific to the type of hash 111table you want to create. 112 113An example of a derived hash table is the linker hash table. 114The structures for this are defined in @code{bfdlink.h}. The 115functions are in @code{linker.c}. 116 117You may also derive a hash table from an already derived hash 118table. For example, the a.out linker backend code uses a hash 119table derived from the linker hash table. 120 121@menu 122* Define the Derived Structures:: 123* Write the Derived Creation Routine:: 124* Write Other Derived Routines:: 125@end menu 126 127@node Define the Derived Structures, Write the Derived Creation Routine, Deriving a New Hash Table Type, Deriving a New Hash Table Type 128@subsubsection Define the derived structures 129You must define a structure for an entry in the hash table, 130and a structure for the hash table itself. 131 132The first field in the structure for an entry in the hash 133table must be of the type used for an entry in the hash table 134you are deriving from. If you are deriving from a basic hash 135table this is @code{struct bfd_hash_entry}, which is defined in 136@code{bfd.h}. The first field in the structure for the hash 137table itself must be of the type of the hash table you are 138deriving from itself. If you are deriving from a basic hash 139table, this is @code{struct bfd_hash_table}. 140 141For example, the linker hash table defines @code{struct 142bfd_link_hash_entry} (in @code{bfdlink.h}). The first field, 143@code{root}, is of type @code{struct bfd_hash_entry}. Similarly, 144the first field in @code{struct bfd_link_hash_table}, @code{table}, 145is of type @code{struct bfd_hash_table}. 146 147@node Write the Derived Creation Routine, Write Other Derived Routines, Define the Derived Structures, Deriving a New Hash Table Type 148@subsubsection Write the derived creation routine 149You must write a routine which will create and initialize an 150entry in the hash table. This routine is passed as the 151function argument to @code{bfd_hash_table_init}. 152 153In order to permit other hash tables to be derived from the 154hash table you are creating, this routine must be written in a 155standard way. 156 157The first argument to the creation routine is a pointer to a 158hash table entry. This may be @code{NULL}, in which case the 159routine should allocate the right amount of space. Otherwise 160the space has already been allocated by a hash table type 161derived from this one. 162 163After allocating space, the creation routine must call the 164creation routine of the hash table type it is derived from, 165passing in a pointer to the space it just allocated. This 166will initialize any fields used by the base hash table. 167 168Finally the creation routine must initialize any local fields 169for the new hash table type. 170 171Here is a boilerplate example of a creation routine. 172@var{function_name} is the name of the routine. 173@var{entry_type} is the type of an entry in the hash table you 174are creating. @var{base_newfunc} is the name of the creation 175routine of the hash table type your hash table is derived 176from. 177 178 179@example 180struct bfd_hash_entry * 181@var{function_name} (entry, table, string) 182 struct bfd_hash_entry *entry; 183 struct bfd_hash_table *table; 184 const char *string; 185@{ 186 struct @var{entry_type} *ret = (@var{entry_type} *) entry; 187 188 /* Allocate the structure if it has not already been allocated by a 189 derived class. */ 190 if (ret == (@var{entry_type} *) NULL) 191 @{ 192 ret = ((@var{entry_type} *) 193 bfd_hash_allocate (table, sizeof (@var{entry_type}))); 194 if (ret == (@var{entry_type} *) NULL) 195 return NULL; 196 @} 197 198 /* Call the allocation method of the base class. */ 199 ret = ((@var{entry_type} *) 200 @var{base_newfunc} ((struct bfd_hash_entry *) ret, table, string)); 201 202 /* Initialize the local fields here. */ 203 204 return (struct bfd_hash_entry *) ret; 205@} 206@end example 207@strong{Description}@* 208The creation routine for the linker hash table, which is in 209@code{linker.c}, looks just like this example. 210@var{function_name} is @code{_bfd_link_hash_newfunc}. 211@var{entry_type} is @code{struct bfd_link_hash_entry}. 212@var{base_newfunc} is @code{bfd_hash_newfunc}, the creation 213routine for a basic hash table. 214 215@code{_bfd_link_hash_newfunc} also initializes the local fields 216in a linker hash table entry: @code{type}, @code{written} and 217@code{next}. 218 219@node Write Other Derived Routines, , Write the Derived Creation Routine, Deriving a New Hash Table Type 220@subsubsection Write other derived routines 221You will want to write other routines for your new hash table, 222as well. 223 224You will want an initialization routine which calls the 225initialization routine of the hash table you are deriving from 226and initializes any other local fields. For the linker hash 227table, this is @code{_bfd_link_hash_table_init} in @code{linker.c}. 228 229You will want a lookup routine which calls the lookup routine 230of the hash table you are deriving from and casts the result. 231The linker hash table uses @code{bfd_link_hash_lookup} in 232@code{linker.c} (this actually takes an additional argument which 233it uses to decide how to return the looked up value). 234 235You may want a traversal routine. This should just call the 236traversal routine of the hash table you are deriving from with 237appropriate casts. The linker hash table uses 238@code{bfd_link_hash_traverse} in @code{linker.c}. 239 240These routines may simply be defined as macros. For example, 241the a.out backend linker hash table, which is derived from the 242linker hash table, uses macros for the lookup and traversal 243routines. These are @code{aout_link_hash_lookup} and 244@code{aout_link_hash_traverse} in aoutx.h. 245 246