1persistent_term(3)         Erlang Module Definition         persistent_term(3)
2
3
4

NAME

6       persistent_term - Persistent terms.
7

DESCRIPTION

9       This  module is similar to ets in that it provides a storage for Erlang
10       terms that can be accessed in constant time, but  with  the  difference
11       that persistent_term has been highly optimized for reading terms at the
12       expense of writing and  updating  terms.  When  a  persistent  term  is
13       updated or deleted, a global garbage collection pass is run to scan all
14       processes for the deleted term, and to copy it into each  process  that
15       still  uses  it.  Therefore,  persistent_term  is  suitable for storing
16       Erlang terms that are frequently accessed  but  never  or  infrequently
17       updated.
18
19   Warning:
20       Persistent  terms  is an advanced feature and is not a general replace‐
21       ment for ETS tables. Before using persistent terms, make sure to  fully
22       understand  the  consequence  to  system  performance  when updating or
23       deleting persistent terms.
24
25
26       Term lookup (using get/1), is done in constant time and without  taking
27       any locks, and the term is not  copied to the heap (as is the case with
28       terms stored in ETS tables).
29
30       Storing or updating a term (using put/2) is proportional to the  number
31       of  already created persistent terms because the hash table holding the
32       keys will be copied. In addition, the term itself will be copied.
33
34       When a (complex) term is deleted (using erase/1) or replaced by another
35       (using  put/2), a global garbage collection is initiated. It works like
36       this:
37
38         * All processes in the system will be scheduled  to  run  a  scan  of
39           their  heaps for the term that has been deleted. While such scan is
40           relatively light-weight, if there are many  processes,  the  system
41           can  become  less  responsive  until all process have scanned their
42           heaps.
43
44         * If the deleted term (or any part of it) is still used by a process,
45           that  process  will  do  a major (fullsweep) garbage collection and
46           copy the term into the process. However, at most two processes at a
47           time will be scheduled to do that kind of garbage collection.
48
49       Deletion  of atoms and other terms that fit in one machine word is spe‐
50       cially optimized to avoid doing a global GC. It  is  still  not  recom‐
51       mended  to  update  persistent  terms  with  such values too frequently
52       because the hash table holding the keys is copied every time a  persis‐
53       tent term is updated.
54
55       Some examples are suitable uses for persistent terms are:
56
57         * Storing of configuration data that must be easily accessible by all
58           processes.
59
60         * Storing of references for NIF resources.
61
62         * Storing of references for efficient counters.
63
64         * Storing an atom to indicate a logging level or whether debugging is
65           turned on.
66

STORING HUGE PERSISTENT TERMS

68       The current implementation of persistent terms uses the literal alloca‐
69       tor also used for literals (constant terms) in BEAM code. By default, 1
70       GB  of  virtual address space is reserved for literals in BEAM code and
71       persistent terms. The amount of virtual address space reserved for lit‐
72       erals  can be changed by using the +MIscs option when starting the emu‐
73       lator.
74
75       Here is an example how the reserved virtual address space for  literals
76       can be raised to 2 GB (2048 MB):
77
78           erl +MIscs 2048
79

BEST PRACTICES FOR USING PERSISTENT TERMS

81       It is recommended to use keys like ?MODULE or {?MODULE,SubKey} to avoid
82       name collisions.
83
84       Prefer creating a few large persistent terms  to  creating  many  small
85       persistent  terms.  The execution time for storing a persistent term is
86       proportional to the number of already existing terms.
87
88       Updating a persistent term with the same value as  it  already  has  is
89       specially  optimized to do nothing quickly; thus, there is no need com‐
90       pare the old and new values and avoid calling put/2 if the  values  are
91       equal.
92
93       When  atoms or other terms that fit in one machine word are deleted, no
94       global GC is needed. Therefore, persistent terms  that  have  atoms  as
95       their  values  can  be  updated more frequently, but note that updating
96       such persistent terms is still much more expensive than reading them.
97
98       Updating or deleting a persistent term will trigger a global GC if  the
99       term  does  not fit in one machine word. Processes will be scheduled as
100       usual, but all processes will be made runnable at once, which will make
101       the system less responsive until all process have run and scanned their
102       heaps for the deleted terms. One way to minimize the effects on respon‐
103       siveness  could  be  to  minimize  the  number of processes on the node
104       before updating or deleting a persistent term. It would also be wise to
105       avoid updating terms when the system is at peak load.
106
107       Avoid  storing a retrieved persistent term in a process if that persis‐
108       tent term could be deleted or updated in the future. If a process holds
109       a  reference to a persistent term when the term is deleted, the process
110       will be garbage collected and the term copied to process.
111
112       Avoid updating or deleting more than one persistent  term  at  a  time.
113       Each  deleted  term  will  trigger  its  own global GC. That means that
114       deleting N terms will make the system less responsive  N  times  longer
115       than deleting a single persistent term. Therefore, terms that are to be
116       updated at the same time should be collected into a  larger  term,  for
117       example, a map or a tuple.
118

EXAMPLE

120       The  following  example shows how lock contention for ETS tables can be
121       minimized by having one ETS table for each scheduler. The table identi‐
122       fiers for the ETS tables are stored as a single persistent term:
123
124           %% There is one ETS table for each scheduler.
125           Sid = erlang:system_info(scheduler_id),
126           Tid = element(Sid, persistent_term:get(?MODULE)),
127           ets:update_counter(Tid, Key, 1).
128

DATA TYPES

130       key() = term()
131
132              Any Erlang term.
133
134       value() = term()
135
136              Any Erlang term.
137

EXPORTS

139       erase(Key) -> Result
140
141              Types:
142
143                 Key = key()
144                 Result = boolean()
145
146              Erase  the name for the persistent term with key Key. The return
147              value will be true if there was a persistent term with  the  key
148              Key,  and  false if there was no persistent term associated with
149              the key.
150
151              If there existed a previous persistent term associated with  key
152              Key,  a  global  GC has been initiated when erase/1 returns. See
153              Description.
154
155       get() -> List
156
157              Types:
158
159                 List = [{key(), value()}]
160
161              Retrieve the keys and values for all persistent terms. The  keys
162              will  be  copied  to the heap for the process calling get/0, but
163              the values will not.
164
165       get(Key) -> Value
166
167              Types:
168
169                 Key = key()
170                 Value = value()
171
172              Retrieve the value for the persistent term associated  with  the
173              key  Key. The lookup will be made in constant time and the value
174              will not be copied to the heap of the calling process.
175
176              This function fails with a badarg exception if no term has  been
177              stored with the key Key.
178
179              If  the  calling process holds on to the value of the persistent
180              term and the persistent term is deleted in the future, the  term
181              will be copied to the process.
182
183       get(Key, Default) -> Value
184
185              Types:
186
187                 Key = key()
188                 Default = Value = value()
189
190              Retrieve  the  value for the persistent term associated with the
191              key Key. The lookup will be made in constant time and the  value
192              will not be copied to the heap of the calling process.
193
194              This  function  returns  Default if no term has been stored with
195              the key Key.
196
197              If the calling process holds on to the value of  the  persistent
198              term  and the persistent term is deleted in the future, the term
199              will be copied to the process.
200
201       info() -> Info
202
203              Types:
204
205                 Info = #{count := Count, memory := Memory}
206                 Count = Memory = integer() >= 0
207
208              Return information about persistent terms in a map. The map  has
209              the following keys:
210
211                count:
212                  The number of persistent terms.
213
214                memory:
215                  The  total  amount of memory (measured in bytes) used by all
216                  persistent terms.
217
218       put(Key, Value) -> ok
219
220              Types:
221
222                 Key = key()
223                 Value = value()
224
225              Store the value Value as a persistent term and associate it with
226              the key Key.
227
228              If  the  value Value is equal to the value previously stored for
229              the key, put/2 will do nothing and return quickly.
230
231              If there existed a previous persistent term associated with  key
232              Key,  a  global  GC  has  been initiated when put/2 returns. See
233              Description.
234
235
236
237Ericsson AB                       erts 10.7.1               persistent_term(3)
Impressum