# "No permission to append findall-bag"

**URL:** <https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845>\
**Category:** General\
**Created:** [February 7, 2020, 10:56am UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845 "2020-02-07T10:56:30Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![volker-wysk](https://avatars.discourse-cdn.com/v4/letter/v/858c86/32.png) [@volker-wysk](https://swi-prolog.discourse.group/u/volker-wysk)\
**Post date:** [February 7, 2020, 10:56am UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/1 "2020-02-07T10:56:30Z")

</div>

Hi!

I’m trying out tabling, but I get an unintelligible error:

```prolog
ERROR: -g main: No permission to append findall-bag `[...]' (continuation in findall/3 generator?)
ERROR: In:
ERROR: [13] throw(error(permission_error(append,'findall-bag',...),context(...,'continuation in findall/3 generator?')))
ERROR: [12] '$tabling':start_tabling(user:auswerten(jm,_2980),user:'auswerten tabled'(jm,_2992)) at /usr/lib/swi-prolog/boot/tabling.pl:98
ERROR: [10] auswerten1(jm,_3018) at /home/v/src/tt/tt2.pl:207
ERROR: [9] main at /home/v/src/tt/tt2.pl:80
ERROR: [8] catch(user:main,error(permission_error(append,'findall-bag',...),context(...,'continuation in findall/3 generator?')),'$toplevel':true) at /usr/lib/swi-prolog/boot/init.pl:386
ERROR: [7] catch_with_backtrace(user:main,error(permission_error(append,'findall-bag',...),context(...,'continuation in findall/3 generator?')),'$toplevel':true) at /usr/lib/swi-prolog/boot/init.pl:436
ERROR: 
ERROR: Note: some frames are missing due to last-call optimization.
ERROR: Re-run your program in debug mode (:- debug.) to get more detail.

```

I’ve no idea what that means. Does someone have a hint?

Cheers,  
Volker

---

<div class="post-metadata">

**Author:** ![jan](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/jan/32/4_2.png) [@jan](https://swi-prolog.discourse.group/u/jan)\
**Post date:** [February 7, 2020, 11:48am UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/2 "2020-02-07T11:48:48Z")

</div>

That is a complicated way to tell that you have a recursive tabled loop through findall/3. That is not possible.

Well, maybe it is different. If you are on 8.0.x tabling and findall do not combine at all. Using a not-too-old 8.1.x tabling and findall/3 work fine, provided that the goal called by findall does not (indirectly) call any tabled variant that calls the findall/3.

Does that make sense?

---

<div class="post-metadata">

**Author:** ![volker-wysk](https://avatars.discourse-cdn.com/v4/letter/v/858c86/32.png) [@volker-wysk](https://swi-prolog.discourse.group/u/volker-wysk)\
**Post date:** [February 7, 2020, 1:28pm UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/3 "2020-02-07T13:28:16Z")

</div>

> [@jan](#):
>
> That is a complicated way to tell that you have a recursive tabled loop through findall/3. That is not possible.
> 
> Well, maybe it is different. If you are on 8.0.x tabling and findall do not combine at all.

Yes, I am. I’ll install the current development version.

> [@jan](#):
>
> Using a not-too-old 8.1.x tabling and findall/3 work fine, provided that the goal called by findall does not (indirectly) call any tabled variant that calls the findall/3.
> 
> Does that make sense?

Somewhat. I don’t understand the “not (indirectly) call any tabled variant” part. Call a tabled variant of what?

Bye,  
Volker

---

<div class="post-metadata">

**Author:** ![jan](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/jan/32/4_2.png) [@jan](https://swi-prolog.discourse.group/u/jan)\
**Post date:** [February 7, 2020, 2:19pm UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/4 "2020-02-07T14:19:31Z")

</div>

> [@volker-wysk](#):
>
> Somewhat. I don’t understand the “not (indirectly) call any tabled variant” part. Call a tabled variant of what?

Tabling is (by default) based on _variants_ (see =@=/2). The problem arises when variant V calls findall/3, which in turn calls V. For example:

```prolog
p(X,Y) :-
      findall(Z, p(X,Z), Zs).

```

If we call this is `p(1, X)`, the findall/3 goal is `p(1,Z)` and as X and Z are unbound, this is a variant. Now we get a child call of findall/3 being dependent on a caller of findall/3. That leads to this error.

---

<div class="post-metadata">

**Author:** ![volker-wysk](https://avatars.discourse-cdn.com/v4/letter/v/858c86/32.png) [@volker-wysk](https://swi-prolog.discourse.group/u/volker-wysk)\
**Post date:** [February 7, 2020, 3:08pm UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/5 "2020-02-07T15:08:56Z")

</div>

> [@jan](#):
>
> > Somewhat. I don’t understand the “not (indirectly) call any tabled variant” part. Call a tabled variant of what?
> 
> Tabling is (by default) based on _variants_ (see =@=/2). The problem arises when variant V calls findall/3, which in turn calls V. For example:
> 
> ```prolog
> p(X,Y) :-
> findall(Z, p(X,Z), Zs).
> 
> ```
> 
> If we call this is `p(1, X)` , the findall/3 goal is `p(1,Z)` and as X and Z are unbound, this is a variant. Now we get a child call of findall/3 being dependent on a caller of findall/3. That leads to this error.

That’s what I have here… Also, I’ve tried SWI-Prolog version 8.1.21. It’s the same.

Thanks for the explanation.

Volker

---

<div class="post-metadata">

**Author:** ![jan](https://yyz2.discourse-cdn.com/free1/user_avatar/swi-prolog.discourse.group/jan/32/4_2.png) [@jan](https://swi-prolog.discourse.group/u/jan)\
**Post date:** [February 7, 2020, 3:28pm UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/6 "2020-02-07T15:28:29Z")

</div>

> [@volker-wysk](#):
>
> That’s what I have here… Also, I’ve tried SWI-Prolog version 8.1.21. It’s the same.

Imagine what needs to happen. The findall goal needs to complete before we can create the list. I don’t see how this should work …

Note that the same applies the ! and -\>, although here you currently get incomplete results. So this doesn’t work:

```prolog
p(X) :- ( p(X) -> x; y ).

```

If the if-then-else has no dependency on any parent goal all goes fine as its tabling component is completed before the → commit happens.

---

<div class="post-metadata">

**Author:** ![volker-wysk](https://avatars.discourse-cdn.com/v4/letter/v/858c86/32.png) [@volker-wysk](https://swi-prolog.discourse.group/u/volker-wysk)\
**Post date:** [February 7, 2020, 4:36pm UTC](https://swi-prolog.discourse.group/t/no-permission-to-append-findall-bag/1845/7 "2020-02-07T16:36:45Z")

</div>

> [@jan](#):
>
> Imagine what needs to happen. The findall goal needs to complete before we can create the list. I don’t see how this should work …
> 
> Note that the same applies the ! and -\>, although here you currently get incomplete results. So this doesn’t work:
> 
> ```prolog
> p(X) :- ( p(X) -> x; y ).
> 
> ```
> 
> If the if-then-else has no dependency on any parent goal all goes fine as its tabling component is completed before the → commit happens.

I’ve rearranged my program, and now it works. I’m building a sort of miniature expert system, and am using tabling to accomplish termination. Thanks for your help!

Bye,  
Volker
