yuce / pyswip

PySwip is a Python - SWI-Prolog bridge enabling to query SWI-Prolog in your Python programs. It features an (incomplete) SWI-Prolog foreign language interface, a utility class that makes it easy querying with Prolog and also a Pythonic interface.
MIT License
465 stars 96 forks source link

FATAL ERROR: Too many stacked strings #102

Closed vakker closed 3 years ago

vakker commented 4 years ago

I have a large database (817718 facts) in the form of:

actor(actor_519105,m).
actor(actor_524655,m).
actor(actor_475182,m).
actor(actor_370794,m).
actor(actor_389977,m).
actor(actor_213427,m).
actor(actor_380131,m).
actor(actor_302008,m).
actor(actor_171966,m).
actor(actor_291,m).
...

When I try to run:

from pyswip import Prolog

prolog = Prolog()
prolog.consult('test.pl')
for r in prolog.query('actor(A,_)'):
    print(r)

then is crashes with:

{'A': 'actor_44508'}
{'A': 'actor_60096'}
{'A': 'actor_66141'}
{'A': 'actor_95401'}
....
[FATAL ERROR: at Thu Aug 27 17:32:11 2020
        Too many stacked strings]

Also, if instead of print(r) I just put pass, it crashes as well.

If I do the same in Prolog then is succeeds without any issues:

['test.pl'].
set_prolog_flag(answer_write_options,[max_depth(0)]).
findall(A, actor(A,_), L).

If I use findall in Python, like:

L = list(prolog.query('findall(A, actor(A,_), L)'))[0]['L']
for r in L:
    print(r.value)

then it crashes as well.

With a smaller database this doesn't happen. Any ideas?

vakker commented 4 years ago

I traced the issue to PL_get_chars, which crashes after a large number of query results. Does that come from libswipl?

Edit: Yes, and it crashes at this line.

EricGT commented 3 years ago

Saw this, don't know if it is relevant but better to have seen it and decide than not.

https://github.com/SWI-Prolog/swipl-devel/commit/ab1a13845ef5ff8c7797c2c6c7d4a86890311e99