/**
 * Warranty & Liability
 * To the extent permitted by applicable law and unless explicitly
 * otherwise agreed upon, XLOG Technologies AG makes no warranties
 * regarding the provided information. XLOG Technologies AG assumes
 * no liability that any problems might be solved with the information
 * provided by XLOG Technologies AG.
 *
 * Rights & License
 * All industrial property rights regarding the information - copyright
 * and patent rights in particular - are the sole property of XLOG
 * Technologies AG. If the company was not the originator of some
 * excerpts, XLOG Technologies AG has at least obtained the right to
 * reproduce, change and translate the information.
 *
 * Reproduction is restricted to the whole unaltered document. Reproduction
 * of the information is only allowed for non-commercial uses. Selling,
 * giving away or letting of the execution of the library is prohibited.
 * The library can be distributed as part of your applications and libraries
 * for execution provided this comment remains unchanged.
 *
 * Restrictions
 * Only to be distributed with programs that add significant and primary
 * functionality to the library. Not to be distributed with additional
 * software intended to replace any components of the library.
 *
 * Trademarks
 * Jekejeke is a registered trademark of XLOG Technologies AG.
 */

/**
 * deref(S, T):
 * The predicate succeeds in T with the value of the term S.
 */
% deref(+Term, -Term)
deref('$ATTR'(V,_), W) :- !, V = W.
deref(V, V).

/**
 * freeze(T, G):
 * The predicate delays the goal G on the term T.
 */
% freeze(+Term, +Goal)
freeze('$ATTR'(V,L), G) :- var(V), !, sys_attr_freeze(L, G).
freeze(_, G) :- G.

% sys_attr_freeze(+List, +Goal)
sys_attr_freeze(V, G) :- var(V), !, V = [G|_].
sys_attr_freeze([_|L], G) :- sys_attr_freeze(L, G).

/**
 * bind(T, S):
 * The predicate succeeds when the frozen goals of T
 * succeed after binding S to T.
 */
% bind(+Term, +Term)
bind('$ATTR'(V,L), W) :- var(V), !,
   sys_attr_bind(L, R),
   '$SEQ'(nothing,[V = W|R]).
bind(V, W) :-
   deref(V, W).

% sys_attr_bind(+List)
sys_attr_bind(V, []) :- var(V), !.
sys_attr_bind([G|L], [H|R]) :- ir_site_new(G, H), sys_attr_bind(L, R).

