/* File: flrstoragebase.P - access to base facts
**
** Author(s): Michael Kifer
**
** Contact: flora-users@lists.sourceforge.net
**
** Copyright (C) The Research Foundation of SUNY, 1999-2001
**
** FLORA-2 is free software; you can redistribute it and/or modify it under the
** terms of the GNU Library General Public License as published by the Free
** Software Foundation; either version 2 of the License, or (at your option)
** any later version.
**
** FLORA-2 is distributed in the hope that it will be useful, but WITHOUT ANY
** WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
** FOR A PARTICULAR PURPOSE. See the GNU Library General Public License for
** more details.
**
** You should have received a copy of the GNU Library General Public License
** along with FLORA-2; if not, write to the Free Software Foundation,
** Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
**
**
*/
%% This file exists in order to isolate Flora's access to base facts
%% and make it possible to easily switch the access methods
:- compiler_options([xpp_on]).
#include "flora_terms.flh"
#include "flora_porting.flh"
:- export
flora_db_insert_base/2,
flora_db_delete_base/2,
flora_db_insert_base_bt/2,
flora_db_delete_base_bt/2,
flora_db_find_base/2,
flora_db_commit/1,
flora_db_reclaim_space/1.
#define FLORA_USE_TRIES
#ifdef FLORA_USE_TRIES
:- import
storage_find_fact/2,
storage_insert_fact/3,
storage_delete_fact/3,
storage_insert_fact_bt/3,
storage_delete_fact_bt/3,
storage_commit/1,
storage_reclaim_space/1
from storage.
flora_db_insert_base(StorageName,Call) :-
storage_insert_fact(StorageName,Call,_ResultFlag).
flora_db_delete_base(StorageName,Call) :-
storage_delete_fact(StorageName,Call,_ResultFlag).
flora_db_insert_base_bt(StorageName,Call) :-
storage_insert_fact_bt(StorageName,Call,_ResultFlag).
flora_db_delete_base_bt(StorageName,Call) :-
storage_delete_fact_bt(StorageName,Call,_ResultFlag).
flora_db_find_base(StorageName,Call) :-
storage_find_fact(StorageName,Call).
flora_db_commit(StorageName) :-
storage_commit(StorageName).
flora_db_reclaim_space(StorageName) :-
storage_reclaim_space(StorageName).
#else
%% Here we need to implement backtrackable updates using assert and retract_nr
#include "storage_xsb_defs.h"
#include "builtin.h"
storage_builtin(_BuiltinNumber,_StorageName,_Handle,_Snapshot,_Changed) :-
'_$builtin'(STORAGE_BUILTIN).
%% Inserts facts. On backtracking, the fact is deleted.
storage_insert_fact_bt(StorageName,Fact,Inserted) :-
triehandle_for_storage(StorageName,H,Snapshot),
trie_intern(Fact, H, Leaf, New, _),
(New == 0
-> Inserted=1, % new fact inserted
mark_storage_changed_bt(StorageName),
( true
; %% On backtracking
triehandle_for_storage(StorageName,_,NewSnapshot),
(NewSnapshot =< Snapshot
-> trie_unintern_nr(H, Leaf), fail
)
)
; Inserted=0 % fact was already there: no action
).
%% Nonbacktrackable insert
storage_insert_fact(StorageName,Fact,Inserted) :-
triehandle_for_storage(StorageName,H,_),
trie_intern(Fact, H, _Leaf, New, _),
(New == 0
-> Inserted=1 % new fact inserted
; Inserted=0 % fact was already there: no action
).
%% Backtrackable delete.
%% Doesn't remove anything, but instead "marks" for deletion.
%% On backtracking: unmarks facts that are marked for deletion
storage_delete_fact_bt(StorageName,Fact,Deleted) :-
triehandle_for_storage(StorageName,H,Snapshot),
(trie_interned(Fact, H, Leaf, _)
-> Deleted=1, % existing fact deleted
mark_storage_changed_bt(StorageName),
( trie_unintern_nr(H, Leaf)
; %% On backtracking
triehandle_for_storage(StorageName,_,NewSnapshot),
(NewSnapshot =< Snapshot
-> unmark_uninterned_nr(H, Leaf), fail
)
)
; Deleted=0 % non-existing fact: no action
).
%% Nonbacktrackable delete
storage_delete_fact(StorageName,Fact,Deleted) :-
triehandle_for_storage(StorageName,H,_),
(trie_interned(Fact, H, Leaf, _)
-> Deleted=1, % existing fact deleted
trie_unintern_nr(H, Leaf)
; Deleted=0 % non-existing fact: no action
).
%% deletes the whole trie
storage_delete_all(StorageName) :-
triehandle_for_storage(StorageName,H,_),
storage_builtin(DESTROY_STORAGE_HANDLE,StorageName,_,_,_),
delete_trie(H).
%% Find fact in storage
storage_find_fact(StorageName,Fact) :-
triehandle_for_storage(StorageName,H,_),
trie_interned(Fact, H, _, _).
%% Commit changes to the storage trie associated with StorageName
%% (only if storage has been changed)
storage_commit(StorageName) :-
( storage_builtin(INCREMENT_STORAGE_SNAPSHOT,StorageName,_,_,_),
!
%% don't backtrack over it
; fail
).
%% Reclaims space by removing nodes from the backtrackable insert/keypair trie
%% which were marked for deletion. This should be done only at the top
%% level of a query.
storage_reclaim_space(StorageName) :-
triehandle_for_storage(StorageName,H,_),
trie_reclaim_uninterned_nr(H).
%% Create a new trie or use an existing one
%% that is already saved as a property of StorageName
triehandle_for_storage(StorageName,Handle,Snapshot) :-
storage_builtin(GET_STORAGE_HANDLE,StorageName,Handle,Snapshot,_).
%% This one seems no longer used. Check!!!
mark_storage_changed_bt(StorageName) :-
storage_builtin(MARK_STORAGE_CHANGED,StorageName,_,_,_).
#endif
syntax highlighted by Code2HTML, v. 0.9.1