From 0ab6149067a82d89e584f862604c1c63578fd5fa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bj=C3=B6rn=20Gustavsson?= Date: Wed, 13 Feb 2019 08:29:51 +0100 Subject: Add persistent_term:get(Key, DefaultValue) https://bugs.erlang.org/browse/ERL-843 --- erts/doc/src/persistent_term.xml | 16 ++++++++++++++++ erts/emulator/beam/bif.tab | 1 + erts/emulator/beam/erl_bif_persistent.c | 17 +++++++++++++++++ erts/emulator/test/persistent_term_SUITE.erl | 5 +++-- erts/preloaded/ebin/persistent_term.beam | Bin 1692 -> 1836 bytes erts/preloaded/src/persistent_term.erl | 9 ++++++++- 6 files changed, 45 insertions(+), 3 deletions(-) diff --git a/erts/doc/src/persistent_term.xml b/erts/doc/src/persistent_term.xml index 1eda7f8d76..9d3c9afd80 100644 --- a/erts/doc/src/persistent_term.xml +++ b/erts/doc/src/persistent_term.xml @@ -255,6 +255,22 @@ will be slower as the number of persistent terms increases. + + + Get the value for a persistent term. + +

Retrieve the value for the persistent term associated with + the key Key. The lookup will be made in + constant time and the value will not be copied to the heap + of the calling process.

+

This function returns Default if no + term has been stored with the key Key.

+

If the calling process holds on to the value of the + persistent term and the persistent term is deleted in the future, + the term will be copied to the process.

+
+
+ Get information about persistent terms. diff --git a/erts/emulator/beam/bif.tab b/erts/emulator/beam/bif.tab index c96278b10c..8419244832 100644 --- a/erts/emulator/beam/bif.tab +++ b/erts/emulator/beam/bif.tab @@ -738,3 +738,4 @@ bif erts_internal:spawn_system_process/3 bif erlang:integer_to_list/2 bif erlang:integer_to_binary/2 +bif persistent_term:get/2 diff --git a/erts/emulator/beam/erl_bif_persistent.c b/erts/emulator/beam/erl_bif_persistent.c index 9dca768a18..5a78a043ce 100644 --- a/erts/emulator/beam/erl_bif_persistent.c +++ b/erts/emulator/beam/erl_bif_persistent.c @@ -332,6 +332,23 @@ BIF_RETTYPE persistent_term_get_1(BIF_ALIST_1) BIF_ERROR(BIF_P, BADARG); } +BIF_RETTYPE persistent_term_get_2(BIF_ALIST_2) +{ + Eterm key = BIF_ARG_1; + Eterm result = BIF_ARG_2; + HashTable* hash_table = (HashTable *) erts_atomic_read_nob(&the_hash_table); + Uint entry_index; + Eterm term; + + entry_index = lookup(hash_table, key); + term = hash_table->term[entry_index]; + if (is_boxed(term)) { + ASSERT(is_tuple_arity(term, 2)); + result = tuple_val(term)[2]; + } + BIF_RET(result); +} + BIF_RETTYPE persistent_term_erase_1(BIF_ALIST_1) { Eterm key = BIF_ARG_1; diff --git a/erts/emulator/test/persistent_term_SUITE.erl b/erts/emulator/test/persistent_term_SUITE.erl index 58038e24b7..93eb026ced 100644 --- a/erts/emulator/test/persistent_term_SUITE.erl +++ b/erts/emulator/test/persistent_term_SUITE.erl @@ -6,7 +6,7 @@ %% Licensed under the Apache License, Version 2.0 (the "License"); %% you may not use this file except in compliance with the License. %% You may obtain a copy of the License at -%5 +%% %% http://www.apache.org/licenses/LICENSE-2.0 %% %% Unless required by applicable law or agreed to in writing, software @@ -60,7 +60,8 @@ basic(_Config) -> Key = {?MODULE,{key,I}}, true = persistent_term:erase(Key), false = persistent_term:erase(Key), - {'EXIT',{badarg,_}} = (catch persistent_term:get(Key)) + {'EXIT',{badarg,_}} = (catch persistent_term:get(Key)), + {not_present,Key} = persistent_term:get(Key, {not_present,Key}) end || I <- Seq], [] = [P || {{?MODULE,_},_}=P <- pget(Chk)], chk(Chk). diff --git a/erts/preloaded/ebin/persistent_term.beam b/erts/preloaded/ebin/persistent_term.beam index e94ef983be..c882e4fad4 100644 Binary files a/erts/preloaded/ebin/persistent_term.beam and b/erts/preloaded/ebin/persistent_term.beam differ diff --git a/erts/preloaded/src/persistent_term.erl b/erts/preloaded/src/persistent_term.erl index 5d0c266127..ee7e49b6cb 100644 --- a/erts/preloaded/src/persistent_term.erl +++ b/erts/preloaded/src/persistent_term.erl @@ -19,7 +19,7 @@ %% -module(persistent_term). --export([erase/1,get/0,get/1,info/0,put/2]). +-export([erase/1,get/0,get/1,get/2,info/0,put/2]). -type key() :: term(). -type value() :: term(). @@ -41,6 +41,13 @@ get() -> get(_Key) -> erlang:nif_error(undef). +-spec get(Key, Default) -> Value when + Key :: key(), + Default :: value(), + Value :: value(). +get(_Key, _Default) -> + erlang:nif_error(undef). + -spec info() -> Info when Info :: #{'count':=Count,'memory':=Memory}, Count :: non_neg_integer(), -- cgit v1.2.3