2 * CDE - Common Desktop Environment
4 * Copyright (c) 1993-2012, The Open Group. All rights reserved.
6 * These libraries and programs are free software; you can
7 * redistribute them and/or modify them under the terms of the GNU
8 * Lesser General Public License as published by the Free Software
9 * Foundation; either version 2 of the License, or (at your option)
12 * These libraries and programs are distributed in the hope that
13 * they will be useful, but WITHOUT ANY WARRANTY; without even the
14 * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU Lesser General Public License for more
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with these librararies and programs; if not, write
20 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21 * Floor, Boston, MA 02110-1301 USA
24 * $XConsortium: fast_mphf.cc /main/5 1996/07/18 14:35:57 drk $
26 * Copyright (c) 1992 HAL Computer Systems International, Ltd.
27 * All rights reserved. Unpublished -- rights reserved under
28 * the Copyright Laws of the United States. USE OF A COPYRIGHT
29 * NOTICE IS PRECAUTIONARY ONLY AND DOES NOT IMPLY PUBLICATION
32 * THIS SOFTWARE CONTAINS CONFIDENTIAL INFORMATION AND TRADE
33 * SECRETS OF HAL COMPUTER SYSTEMS INTERNATIONAL, LTD. USE,
34 * DISCLOSURE, OR REPRODUCTION IS PROHIBITED WITHOUT THE
35 * PRIOR EXPRESS WRITTEN PERMISSION OF HAL COMPUTER SYSTEMS
38 * RESTRICTED RIGHTS LEGEND
39 * Use, duplication, or disclosure by the Government is subject
40 * to the restrictions as set forth in subparagraph (c)(l)(ii)
41 * of the Rights in Technical Data and Computer Software clause
42 * at DFARS 252.227-7013.
44 * HAL COMPUTER SYSTEMS INTERNATIONAL, LTD.
51 #define NUM_BITS_INCREASES 5
53 #include "index/fast_mphf.h"
56 tbl_cache *fast_mphf::v_tbl_cache_ptr = 0;
57 #define v_tbl_cache (*v_tbl_cache_ptr)
59 tbl_cache fast_mphf::v_tbl_cache;
62 tbl_record::~tbl_record()
68 tbl_cache::tbl_cache() : f_array(10)
72 tbl_cache::~tbl_cache()
74 for ( int v=0; v<f_array.no_elmts(); v++ ) {
75 delete (tbl_record*)f_array[v];
80 void tbl_cache::init_table(int hash_tbl_sz, int seed, atoi_pearson*& t1, atoi_pearson*& t2)
82 int x = f_array.no_elmts();
85 for ( int v=0; v<x; v++ ) {
86 y = (tbl_record*)f_array[v];
88 if ( y -> v_tbl0 != 0 && y -> v_seed == seed )
95 MESSAGE(cerr, "USE cached TABLE!");
96 debug(cerr, int(v_tbl0));
97 debug(cerr, int(v_tbl1));
104 t1 = new atoi_pearson(hash_tbl_sz, 128, z);
105 t2 = new atoi_pearson(hash_tbl_sz, 128, z);
107 y = new tbl_record(seed, t1, t2);
108 f_array.insert(y, x);
109 f_array.reset_elmts(x+1);
112 fast_mphf::fast_mphf(c_code_t c_cd): long_pstring(c_cd),
113 v_long_string_core_indexed(false),
114 v_no_ps(0), v_p1(0), v_p2(0),
115 r(0), v_seed(0), t(0)
118 if ( v_tbl_cache_ptr == 0 ) {
119 v_tbl_cache_ptr = new tbl_cache;
127 void fast_mphf::init_persistent_info(persistent_info* x)
129 long_pstring::init_persistent_info(x);
130 if ( get_mode(OLD_OBJECT) == false ) {
138 hash::init_data_member();
142 fast_mphf::~fast_mphf()
149 if ( v_tbl_cache_ptr ) {
150 for (int i=0; i<10; i++ )
151 delete v_tbl_cache_ptr[i];
152 delete v_tbl_cache_ptr;
159 io_status fast_mphf::asciiIn(istream& in)
169 MESSAGE(cerr, "in fast_mphf::asciiIn()");
170 debug(cerr, my_oid());
171 debug(cerr, v_hash_tbl_sz);
172 debug(cerr, v_no_ps);
179 v_key_set_sz = v_hash_tbl_sz ;
181 in.get(); // skip the '\n' after seed
183 long_pstring::asciiIn(in);
185 if ( v_key_set_sz > 0 ) {
186 t = (int)(flog2(v_key_set_sz)) + 1; // bits of each g value.
187 if ( floor(flog2(v_key_set_sz)) < flog2(v_key_set_sz) )
190 //MESSAGE(cerr, "compacted array:");
191 //debug(cerr, long_pstring::size());
193 //for (int z=0; z<long_pstring::size()/4; z++) {
194 // cerr << ((unsigned*)long_pstring::get())[z] << " ";
199 v_hash_func_sz = v_no_ps*sizeof(unsigned)+128*2+6*sizeof(int);
208 set_mode(UPDATE, true);
213 Boolean fast_mphf::init_map_tbls()
216 MESSAGE(cerr, "in fast_mphf::init_map_tbls()");
217 debug(cerr, (void*)this);
218 debug(cerr, my_oid());
219 debug(cerr, v_key_set_sz);
220 debug(cerr, v_hash_tbl_sz);
221 debug(cerr, int(this));
222 debug(cerr, v_no_ps);
228 //debug(cerr, (void*)&v_tbl_cache);
233 if ( v_key_set_sz > 0 ) {
234 v_tbl_cache.init_table(v_hash_tbl_sz, v_seed, v_tbl0, v_tbl1);
237 //long_pstring::init_run_data();
242 int fast_mphf::hashTo(const key_type& k)
244 if ( v_long_string_core_indexed == false ) {
245 v_long_string_core_indexed = true;
249 MESSAGE(cerr, "fast_mphf:: hashTO()");
254 if ( v_hash_tbl_sz == 0 ) {
255 throw(stringException("hash table empty"));
258 int i = v_tbl0 -> atoi(k.get(), k.size(), r, v_key_set_sz); // for halmphf
269 gValue(i, gv, c_bit);
273 //i = v_tbl1 -> atoi(k, c_bit+r+1) + gv;
274 //debug(cerr, c_bit+r);
276 i = v_tbl1 -> atoi(k.get(), k.size(), c_bit+r+1, v_hash_tbl_sz) + gv; // for halmphf
279 return i % v_hash_tbl_sz;
282 int fast_mphf::gValue(int i, int& gvalue, int& ctl_bit)
284 if ( !INRANGE(i, 0, v_no_ps-1) ) {
285 throw(boundaryException(0, v_no_ps-1, i));
289 unsigned un_compacted, un_compacted1;
292 a /= BITS_IN(unsigned);
293 b %= BITS_IN(unsigned);
295 unsigned value_at_a, value_at_a_plus;
304 long_pstring::extract(a*sizeof(a), (a+1)*sizeof(a), x_buf);
306 memcpy((char*)&value_at_a, x_buf, sizeof(value_at_a));
309 //cerr << "Extract: at " << a << "; the int =" << value_at_a << endl;
311 if ( swap_order() == true )
312 ORDER_SWAP_UINT(value_at_a);
314 //cerr << "after swap " << a << "; the int =" << value_at_a << endl;
316 //debug(cerr, hex(value_at_a));
319 if ( BITS_IN(unsigned) - b >= t ) {
321 un_compacted = getbits(value_at_a, BITS_IN(unsigned) - b, t);
325 long_pstring::extract((a+1)*sizeof(a), (a+2)*sizeof(a), x_buf);
327 memcpy((char*)&value_at_a_plus, x_buf, sizeof(value_at_a_plus));
329 //cerr << "Extract+1: at " << (a+1) << "; the int =" << value_at_a_plus << endl;
331 if ( swap_order() == true )
332 ORDER_SWAP_UINT(value_at_a_plus);
334 //cerr << "after swap " << (a+1) << "; the int =" << value_at_a_plus << endl;
336 //debug(cerr, hex(value_at_a_plus));
339 getbits(value_at_a, BITS_IN(unsigned) - b, BITS_IN(unsigned) - b);
341 getbits(value_at_a_plus, BITS_IN(unsigned), t - BITS_IN(unsigned) + b);
342 un_compacted1 <<= ( t - BITS_IN(unsigned) + b);
343 un_compacted |= un_compacted1;
345 //debug(cerr, hex(un_compacted));
347 ctl_bit = un_compacted & (unsigned)1;
348 gvalue = un_compacted >> 1;
352 Boolean fast_mphf::build(const char *from)
354 fstream in(from, ios::in);
359 Boolean fast_mphf::build(istream& in)
367 pms.v_n = stor.no_unique_keys();
371 buffer mphf_spec(LBUFSIZ);
372 //buffer& mphf_spec = get_store() -> aux_buf();
373 mphf_spec.set_swap_order(swap_order());
376 while ( i<NUM_BITS_INCREASES && ok != 0 ) {
378 ok = compute_a_mphf(stor.unique_keys(), pms, mphf_spec);
386 pms.re_select_value();
390 throw(stringException("finding a mphf failed"));
397 set_mode(HEALTH, false);
398 throw(stringException("finding a mphf failed"));
401 istrstream strin(mphf_spec.get_base(), mphf_spec.content_sz());
404 throw(streamException(strin.rdstate()));
409 set_mode(HEALTH, true);
415 fast_mphf::print_mapping(const char *key_file, int option)
417 //debug(cerr, option);
418 MESSAGE(cerr, "print_mapping()");
420 char string[LBUFSIZ];
421 fstream in(key_file, ios::in);
424 throw(streamException(in.rdstate()));
427 char *hash_table = new char[v_hash_tbl_sz];
428 for (int i = 0; i < v_hash_tbl_sz; hash_table[i++] = 0 );
430 ostring lbuf(LBUFSIZ);
433 while ( in.getline(string, LBUFSIZ, '\n') ) {
435 // string[strlen(string)-1] = '\0';
437 //debug(cerr, string);
438 //debug(cerr, strlen(string));
441 lbuf.set(string, strlen(string));
443 int hash = hashTo(lbuf) ;
446 cout << " string = " << string;
447 cout << ", hash = " << hash << "\n";
450 if ( hash_table[hash] == 1 )
451 MESSAGE(cerr, "mapping_print(): panic: mphf hash collision");
453 hash_table[hash] = 1;
455 in.getline(string, LBUFSIZ, '\n');
458 MESSAGE(cerr, "print_mapping() done");
461 void fast_mphf::print_tbls(ostream& out)
467 void fast_mphf::print_gvalues(ostream& out)
470 for (int i = 0; i<v_no_ps; i++ ) {
473 out << " " << gv << " " << cbit << "\n";
477 int fast_mphf::print_bits(unsigned x, ostream& out)
479 for ( int i=0; i<8*sizeof(unsigned); i++ ) {
480 if ( BIT_TEST(x, 0x80000000) )
491 int fast_mphf::cdr_sizeof()
493 return long_pstring::cdr_sizeof() + hash::cdr_sizeof() +
494 6*sizeof(unsigned int);
497 io_status fast_mphf::cdrOut(buffer& buf)
499 long_pstring::cdrOut(buf);
512 io_status fast_mphf::cdrIn(buffer& buf)
514 long_pstring::cdrIn(buf);
531 MMDB_BODIES(fast_mphf)
532 HANDLER_BODIES(fast_mphf)