konclude / Konclude

Konclude: A parallel, tableau-based, high-performance reasoner for the Description Logic SROIQV(D)/the Web Ontology Language (OWL) 2 DL
http://konclude.com
35 stars 4 forks source link

Konclude crashes on OWLlink GetSubClasses #20

Closed mrnolte closed 1 year ago

mrnolte commented 2 years ago

Hi, I loaded this example ontology and tried to query the subclasses of not Nothing via OWLLink GetSubClasses. Konclude 0.7.0 crashed without an error message or any other output. This is especially weird since querying the equivalent classes of not Nothing via OWLLink GetEquivalentClasses works just fine.

mpomarlan commented 2 years ago

I have a small update on this issue. The error manifests into a crash at the following lines from CConcreteOntologyQueryBasicBuilder::generateQuerys

foreach (CQueryGetSubClassesExpression* subClassesExp, mSubClassesExpList) {
    QString queryName = subClassesExp->getName();
    CClassTermExpression* classExp = subClassesExp->getClassTermExpression();
    if (classExp) {
        CConcept* concept = getConceptFromBuildExpression(classExp);
        QString iriClassNameString = CIRIName::getRecentIRIName(concept->getClassNameLinker());
        // ...
    }
    //...
}

The crash happens because the variable concept is set to a null pointer and method calls from null pointers crash.

This however is merely the manifestation of the error. The error itself happens earlier, and it is whatever causes the class expression to not produce a valid value via getConceptFromBuildExpression.

Will keep hunting.

mpomarlan commented 2 years ago

Another update, this time about why the concept variable above gets set to a null pointer. This happens because what CConcreteOntologyQueryBasicBuilder::getConceptFromBuildExpression does is to look in a hash table, and there is no key corresponding to the class expression from the query in this hash table.

The hash table has as keys pointers to class expressions (this is somewhat suspicious I think), and as values pointers to variables of type CConcept. It is possible to get string versions of these CConcept variables and they correspond to the concepts defined/declared in the abc.owl file.

So in short:

There is a hash table constructed with "class expression pointers" as keys and values (corresponding to) all the concepts defined/declared in abc.owl.

This hash table does NOT contain a class expression (pointer) corresponding to the concept from the query ("not Nothing"). Therefore, the hash table fails to find the association needed by the code to proceed, a null pointer gets followed, and Konclude crashes.

I would pause my bug hunt for now and ask, what was the intended behavior? Should the query concept have been added to the hash table at some point? Should it not have been looked for in the hash table at all? Should an extra test be added about whether a class expression has, or not, an entry in the hash table?

EDIT, PS:

Assuming the intended behavior is described correctly by other queries such as EquivalentClasses or SuperClasses, then the fix is simple:

foreach (CQueryGetSubClassesExpression* subClassesExp, mSubClassesExpList) {
    QString queryName = subClassesExp->getName();
    CClassTermExpression* classExp = subClassesExp->getClassTermExpression();
    if (classExp) {
        CConcept* concept = getConceptFromBuildExpression(classExp);
        if (concept) {
            QString iriClassNameString = CIRIName::getRecentIRIName(concept->getClassNameLinker());
            // ...
        }
    }
    //...
}
andreas-steigmiller commented 2 years ago

Thanks, I merged the pull request such that the crash will be avoided. Konclude does not really support querying complex concept expressions via OWLlink. The class expressions are from parsing the ontology/query, but they are currently not compiled into the internal representation (i.e., into these CConcept objects). It is also fine to use pointers in the hash table since the expressions are resolved recursively (i.e., based on the object pointers of the children and the type of the expression, we uniquely identify the expression object). I'm not completely sure why the EquivalentClasses is working or whether it produces the expected result, but as mentioned, such queries are not supported via the OWLlink interface. For the SPARQL interface, it may work since there is a step that compiles such new expressions to the internal respresentation, but it has other limitations.

mrnolte commented 1 year ago

The merged PR indeed fixed this issue, thank you @mpomarlan !