When we first call findall/4 from module(a), we compile a linking shim like this:
a:findall(A,B,C,D):- b:findall(A,B,C,D).
But when we execute this, we get the exception that some_goal/1 is not defined, since we're looking for it in module(b). If we don't change the context to b when executing code exported from b, then findall/4 will complain it cannot find another_goal/0. In other words, logically we have to be able to tell the compiler that what we really want is this:
a:findall(A,B,C,D):- b:findall(A,a:B,C,D).
The way this works in SWI-Prolog, YAP, SICStus and Quintus is to use a declaration like (the specifics vary by system)
To see why this is necessary, consider the following:
Suppose that findall/4 (a variation on findall/3 where the last two args are a difference list) is defined, rather hurriedly, in module(b):
When we first call findall/4 from module(a), we compile a linking shim like this:
But when we execute this, we get the exception that some_goal/1 is not defined, since we're looking for it in module(b). If we don't change the context to b when executing code exported from b, then findall/4 will complain it cannot find another_goal/0. In other words, logically we have to be able to tell the compiler that what we really want is this:
The way this works in SWI-Prolog, YAP, SICStus and Quintus is to use a declaration like (the specifics vary by system)