3 with Interfaces
; use Interfaces
;
6 type t_p_string
is access constant String;
7 subtype t_hash
is Unsigned_32
;
9 -- Return a hash value for a given string
10 function hash
(s
: String) return t_hash
is
15 h
:= Shift_Left
(h
, 4) + t_hash
'(Character'Pos(s(i)));
16 g := h and 16#F000_0000#;
17 if (h and g) /= 0 then
18 h := h xor ((Shift_Right(g, 24) and 16#FF#) or g);
24 type hash_entry is record
27 next: access hash_entry;
30 type hashtable is array(t_hash range <>) of access hash_entry;
33 procedure allocate (sp: out t_p_string; s: String; h: t_hash);
35 tab: hashtable(0..199999-1) := (others => null);
38 protected body pool is
39 procedure allocate(sp: out t_p_string; s: String; h: t_hash) is
43 slot := h mod tab'Length;
46 -- quickly check hash, then length, only then slow comparison
47 if p.hash = h and then p.v.all'Length = s'Length
50 sp := p.v; -- shared string
56 p := new hash_entry'(v
=> new String'(s),
59 tab(slot) := p; -- { dg-warning "accessibility check fails|Program_Error will be raised at run time" }
60 sp := p.v; -- shared string
64 -- Return the pooled string equal to a given String
65 function new_p_string(s: String) return t_p_string is
68 pool.allocate(sp, s, hash(s));
72 foo_string : t_p_string;
74 foo_string := new_p_string("foo");
75 raise Constraint_Error;