mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-10-15 22:35:43 +00:00
652 lines
22 KiB
C
652 lines
22 KiB
C
/* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
|
*
|
|
* The contents of this file are subject to the Netscape Public License
|
|
* Version 1.0 (the "NPL"); you may not use this file except in
|
|
* compliance with the NPL. You may obtain a copy of the NPL at
|
|
* http://www.mozilla.org/NPL/
|
|
*
|
|
* Software distributed under the NPL is distributed on an "AS IS" basis,
|
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
|
|
* for the specific language governing rights and limitations under the
|
|
* NPL.
|
|
*
|
|
* The Initial Developer of this code under the NPL is Netscape
|
|
* Communications Corporation. Portions created by Netscape are
|
|
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
|
|
* Reserved.
|
|
*/
|
|
|
|
/*
|
|
This file implements query support for the rdf data model.
|
|
For more information on this file, contact rjc or guha
|
|
For more information on RDF, look at the RDF section of www.mozilla.org
|
|
*/
|
|
|
|
#ifdef XP_PC
|
|
#define strcasecomp strcmp
|
|
#endif
|
|
|
|
#include "query.h"
|
|
#include "rdf-int.h"
|
|
|
|
/* prototypes */
|
|
PRBool variableTermp(TermStruc term);
|
|
PRBool resourceTermp(TermStruc term);
|
|
PRBool constantTermp(TermStruc term);
|
|
RDF_Error addVariableToList(RDF_Variable variable, RDF_VariableList *list);
|
|
void destroyVariableList(RDF_VariableList list, PRBool destroyVariables);
|
|
void destroyLiteralList(RDF_LiteralList list, PRBool destroyLiterals);
|
|
PRBool comparisonp(RDF_Resource r);
|
|
PRBool specialResourcePredicate(RDF_Resource r);
|
|
PRBool findLiteral(RDF_Literal target, RDF_LiteralList list);
|
|
RDF_Literal getNthLiteral(RDF_Query q, uint16 index);
|
|
PRBool constantp(TermStruc term, RDF_VariableList knownVars);
|
|
RDF_Literal oneUnknownAs(RDF_Query q, RDF_LiteralList orderedLiterals, RDF_VariableList knownVars);
|
|
RDF_Literal noUnknownAs(RDF_Query q, RDF_LiteralList orderedLiterals, RDF_VariableList knownVars);
|
|
PRBool orderConjuncts(RDF_Query q);
|
|
PRBool processNextLiteral(RDF_Query q, RDF_Literal literal);
|
|
void addLiteral(RDF_Query q, RDF_Literal literal);
|
|
|
|
/* Variable API */
|
|
PR_PUBLIC_API(PRBool) RDF_IsResultVariable(RDF_Variable var) {
|
|
return var->isResult;
|
|
}
|
|
|
|
PR_PUBLIC_API(void) RDF_SetResultVariable(RDF_Variable var, PRBool isResult) {
|
|
var->isResult = isResult;
|
|
}
|
|
|
|
PR_PUBLIC_API(void*) RDF_GetVariableValue(RDF_Variable var) {
|
|
if (var->query->queryRunning)
|
|
return var->value;
|
|
else return NULL;
|
|
}
|
|
|
|
PR_PUBLIC_API(void) RDF_SetVariableValue(RDF_Variable var, void* value, RDF_ValueType type) {
|
|
if (!var->query->queryRunning) var->query->conjunctsOrdered = false;
|
|
var->value = value;
|
|
var->type = type;
|
|
}
|
|
|
|
PRBool variableTermp(TermStruc term) {
|
|
return term.type == RDF_VARIABLE_TERM_TYPE;
|
|
}
|
|
|
|
PRBool resourceTermp(TermStruc term) {
|
|
return term.type == RDF_RESOURCE_TERM_TYPE;
|
|
}
|
|
|
|
PRBool constantTermp(TermStruc term) {
|
|
return term.type == RDF_CONSTANT_TERM_TYPE;
|
|
}
|
|
|
|
/* Adds the variable to the variable list if it isn't already on the list. */
|
|
RDF_Error addVariableToList(RDF_Variable variable, RDF_VariableList *list) {
|
|
PRBool found = false;
|
|
RDF_VariableList current = *list;
|
|
while (current != NULL) {
|
|
if (current->element == variable) {
|
|
found = true;
|
|
break;
|
|
}
|
|
current = current->next;
|
|
}
|
|
if (!found) {
|
|
RDF_VariableList newlist = (RDF_VariableList)getMem(sizeof(RDF_VariableListStruc));
|
|
if (newlist == NULL) return RDF_NO_MEMORY;
|
|
newlist->element = variable;
|
|
newlist->next = *list;
|
|
*list = newlist;
|
|
}
|
|
return noRDFErr;
|
|
}
|
|
|
|
void destroyVariableList(RDF_VariableList list, PRBool destroyVariables) {
|
|
if (list != NULL) {
|
|
destroyVariableList(list->next, destroyVariables);
|
|
if (destroyVariables) freeMem(list->element); /* free the variable */
|
|
freeMem(list); /* free the list structure */
|
|
}
|
|
}
|
|
|
|
void destroyLiteralList(RDF_LiteralList list, PRBool destroyLiterals) {
|
|
if (list != NULL) {
|
|
destroyLiteralList(list->next, destroyLiterals);
|
|
if (destroyLiterals) {
|
|
RDF_Literal literal = list->element;
|
|
if (literal->c != NULL) RDF_DisposeCursor(literal->c);
|
|
if (literal->valueType == RDF_STRING_TYPE) {
|
|
int i;
|
|
for (i = 0; i < literal->valueCount; i++) {
|
|
TermStruc term = *(literal->v + i);
|
|
if (constantTermp(term)) freeMem(term.value);
|
|
}
|
|
}
|
|
freeMem(literal->v);
|
|
freeMem(list->element); /* free the literal */
|
|
}
|
|
freeMem(list); /* free the list structure */
|
|
}
|
|
}
|
|
|
|
PRBool comparisonp(RDF_Resource r) {
|
|
return (r == gCoreVocab->RDF_substring ||
|
|
r == gCoreVocab->RDF_notSubstring ||
|
|
r == gCoreVocab->RDF_lessThan ||
|
|
r == gCoreVocab->RDF_greaterThan ||
|
|
r == gCoreVocab->RDF_lessThanOrEqual ||
|
|
r == gCoreVocab->RDF_greaterThanOrEqual ||
|
|
r == gCoreVocab->RDF_equals ||
|
|
r == gCoreVocab->RDF_notEquals ||
|
|
r == gCoreVocab->RDF_stringEquals ||
|
|
r == gCoreVocab->RDF_notStringEquals);
|
|
}
|
|
|
|
PRBool specialResourcePredicate(RDF_Resource r) {
|
|
return (r == gCoreVocab->RDF_notInstanceOf || r == gCoreVocab->RDF_notParent);
|
|
}
|
|
|
|
/* Creates and initializes a query. Returns NULL if not enough memory. */
|
|
PR_PUBLIC_API(RDF_Query) RDF_CreateQuery(RDF rdf) {
|
|
RDF_Query q = (RDF_Query)getMem(sizeof(RDF_QueryStruc));
|
|
if (q == NULL) return q;
|
|
q->variables = NULL;
|
|
q->literals = NULL;
|
|
q->numLiterals = 0;
|
|
q->index = 0;
|
|
q->conjunctsOrdered = false;
|
|
q->queryRunning = false;
|
|
q->rdf = rdf;
|
|
return q;
|
|
}
|
|
|
|
/* Destroys a query. */
|
|
PR_PUBLIC_API(void) RDF_DestroyQuery(RDF_Query q) {
|
|
destroyLiteralList(q->literals, true); /* free the literals */
|
|
q->literals = NULL;
|
|
destroyVariableList(q->variables, true); /* free the variables */
|
|
q->variables = NULL;
|
|
freeMem(q); /* free the query */
|
|
q = NULL;
|
|
}
|
|
|
|
/* Returns the variable with the given name in the query.
|
|
If not found:
|
|
if the query is running, return NULL
|
|
otherwise create a new variable with the given name.
|
|
if there isn't enough memory, return NULL.
|
|
*/
|
|
PR_PUBLIC_API(RDF_Variable) RDF_GetVariable(RDF_Query q, char* name) {
|
|
RDF_Variable newvar;
|
|
RDF_VariableList newlist;
|
|
RDF_VariableList current = q->variables;
|
|
while (current != NULL) {
|
|
if (stringEquals(current->element->id, name)) return current->element;
|
|
if (current->next == NULL) break;
|
|
else current = current->next;
|
|
}
|
|
if (q->queryRunning) return NULL;
|
|
newvar = (RDF_Variable)getMem(sizeof(RDF_VariableStruc));
|
|
if (newvar == NULL) return NULL;
|
|
newvar->id = copyString(name);
|
|
newvar->query = q;
|
|
/* create a list containing the variable and append it to the front of the variable list */
|
|
newlist = (RDF_VariableList)getMem(sizeof(RDF_VariableListStruc));
|
|
if (newlist == NULL) {
|
|
freeMem(newvar);
|
|
return NULL;
|
|
}
|
|
newlist->element = newvar;
|
|
newlist->next = q->variables;
|
|
q->variables = newlist;
|
|
return newvar;
|
|
}
|
|
|
|
/* Returns the number of variables in the query. */
|
|
PR_PUBLIC_API(uint16) RDF_GetVariableListCount(RDF_Query q) {
|
|
RDF_VariableList current = q->variables;
|
|
uint16 count = 0;
|
|
while (current != NULL) {
|
|
current = current->next;
|
|
count++;
|
|
}
|
|
return count;
|
|
}
|
|
|
|
/* Returns the variables belonging to the query at the given index. */
|
|
PR_PUBLIC_API(RDF_Variable) RDF_GetNthVariable(RDF_Query q, uint16 index) {
|
|
RDF_VariableList current = q->variables;
|
|
uint16 count = 0;
|
|
while (current != NULL) {
|
|
if (count == index)
|
|
return current->element;
|
|
else {
|
|
current = current->next;
|
|
count++;
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
/* Returns true if target is found in literal */
|
|
PRBool findLiteral(RDF_Literal target, RDF_LiteralList list) {
|
|
while (list != NULL) {
|
|
if (list->element == target) return true;
|
|
else list = list->next;
|
|
}
|
|
return false;
|
|
}
|
|
|
|
/* Returns the literal belonging to the query at the given index. */
|
|
RDF_Literal getNthLiteral(RDF_Query q, uint16 index) {
|
|
RDF_LiteralList current = q->literals;
|
|
uint16 count = 0;
|
|
while (current != NULL) {
|
|
if (count == index)
|
|
return current->element;
|
|
else {
|
|
current = current->next;
|
|
count++;
|
|
}
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
/* A term is constant if it is not a variable, if it is a variable with
|
|
a non-null value, or if it is a known variable.
|
|
*/
|
|
PRBool constantp(TermStruc term, RDF_VariableList knownVars) {
|
|
if (term.type != RDF_VARIABLE_TERM_TYPE) return true;
|
|
else {
|
|
RDF_Variable var = (RDF_Variable)term.value;
|
|
if (var->value != NULL) return true;
|
|
else {
|
|
while (knownVars != NULL) {
|
|
if (knownVars->element == var) return true;
|
|
knownVars = knownVars->next;
|
|
}
|
|
return false;
|
|
}
|
|
}
|
|
}
|
|
|
|
/* Returns a literal with a constant term which has not been ordered yet. */
|
|
RDF_Literal oneUnknownAs(RDF_Query q, RDF_LiteralList orderedLiterals, RDF_VariableList knownVars) {
|
|
RDF_LiteralList list = q->literals;
|
|
RDF_Literal answer = NULL;
|
|
while (list != NULL) {
|
|
RDF_Literal current = list->element;
|
|
if (!findLiteral(current, orderedLiterals)) {
|
|
if (((constantp(current->u, knownVars)) || (constantp(*current->v, knownVars))) &&
|
|
current->valueCount == 1 && /* no disjunctions */
|
|
!comparisonp(current->s) && /* comparisons must have constant terms */
|
|
!specialResourcePredicate(current->s) /* notTypeOf and notParent must have constant terms */
|
|
/* && current->tv == true */) {
|
|
if (answer == NULL) {
|
|
answer = current;
|
|
} else {
|
|
/* fix me - deal with branching factor */
|
|
answer = current;
|
|
}
|
|
}
|
|
}
|
|
list = list->next;
|
|
}
|
|
return answer;
|
|
}
|
|
|
|
/* Returns a literal with both terms constant which has not been ordered yet. */
|
|
RDF_Literal noUnknownAs(RDF_Query q, RDF_LiteralList orderedLiterals, RDF_VariableList knownVars) {
|
|
RDF_LiteralList list = q->literals;
|
|
while (list != NULL) {
|
|
RDF_Literal current = list->element;
|
|
if (!findLiteral(current, orderedLiterals) &&
|
|
constantp(current->u, knownVars)) {
|
|
int i;
|
|
PRBool foundNonConstant = false;
|
|
for (i = 0; i < current->valueCount; i++) { /* all values constant? */
|
|
TermStruc term = *(current->v + i);
|
|
if (!constantp(term, knownVars)) foundNonConstant = true;
|
|
}
|
|
if (foundNonConstant) list = list->next;
|
|
else return current;
|
|
}
|
|
else list = list->next;
|
|
}
|
|
return NULL;
|
|
}
|
|
|
|
/* Returns true if the conjuncts were ordered succesfully.
|
|
*/
|
|
PRBool orderConjuncts(RDF_Query q) {
|
|
uint16 numOrdered = 0;
|
|
RDF_Error err = noRDFErr;
|
|
RDF_LiteralList orderedLiterals = NULL;
|
|
RDF_LiteralList orderedLiteralsTail = orderedLiterals;
|
|
RDF_VariableList knownVars = NULL;
|
|
|
|
if (q->conjunctsOrdered) return true;
|
|
|
|
while (numOrdered < q->numLiterals) {
|
|
RDF_Literal lit1 = noUnknownAs(q, orderedLiterals, knownVars);
|
|
if (lit1 != NULL) {
|
|
/* add literal to ordered list */
|
|
RDF_LiteralList newlist = (RDF_LiteralList)getMem(sizeof(RDF_LiteralListStruc));
|
|
if (newlist == NULL) break;
|
|
newlist->element = lit1;
|
|
newlist->next = NULL;
|
|
if (orderedLiterals == NULL)
|
|
orderedLiterals = orderedLiteralsTail = newlist;
|
|
else {
|
|
orderedLiteralsTail->next = newlist;
|
|
orderedLiteralsTail = orderedLiteralsTail->next;
|
|
}
|
|
numOrdered++;
|
|
} else {
|
|
RDF_Literal lit2 = oneUnknownAs(q, orderedLiterals, knownVars);
|
|
if (lit2 != NULL) {
|
|
RDF_LiteralList newlist = (RDF_LiteralList)getMem(sizeof(RDF_LiteralListStruc));
|
|
if (newlist == NULL) break;
|
|
/* add unit and value as known variables */
|
|
lit2->variable = (RDF_Variable) (constantp(lit2->u, knownVars) ? lit2->v->value : lit2->u.value);
|
|
if (variableTermp(lit2->u)) {
|
|
err = addVariableToList((RDF_Variable)lit2->u.value, &knownVars);
|
|
if (err != noRDFErr) break;
|
|
}
|
|
if (variableTermp(*lit2->v)) {
|
|
err = addVariableToList((RDF_Variable)lit2->v->value, &knownVars);
|
|
if (err != noRDFErr) break;
|
|
}
|
|
/* add literal to ordered list */
|
|
newlist->element = lit2;
|
|
newlist->next = NULL;
|
|
if (orderedLiterals == NULL)
|
|
orderedLiterals = orderedLiteralsTail = newlist;
|
|
else {
|
|
orderedLiteralsTail->next = newlist;
|
|
orderedLiteralsTail = orderedLiteralsTail->next;
|
|
}
|
|
numOrdered++;
|
|
} else break;
|
|
}
|
|
}
|
|
if (numOrdered == q->numLiterals) { /* ordered all succesfully so replace literals */
|
|
RDF_LiteralList old = q->literals;
|
|
q->literals = orderedLiterals;
|
|
destroyLiteralList(old, false);
|
|
q->conjunctsOrdered = true;
|
|
} else { /* unsuccessful so destroy ordered list structure */
|
|
destroyLiteralList(orderedLiterals, false);
|
|
q->conjunctsOrdered = false;
|
|
}
|
|
destroyVariableList(knownVars, false); /* free the knownVars list structure */
|
|
return q->conjunctsOrdered;
|
|
}
|
|
|
|
PRBool processNextLiteral(RDF_Query q, RDF_Literal literal) {
|
|
if (literal->c != NULL) {
|
|
RDF_SetVariableValue(literal->variable, RDF_NextValue(literal->c), literal->valueType);
|
|
return (RDF_GetVariableValue(literal->variable) != NULL);
|
|
} else {
|
|
RDF_Resource u; /* unit is a resource except for the comparison case so don't set it yet. */
|
|
RDF_Resource s = literal->s;
|
|
void* v;
|
|
if (literal->variable == NULL) {
|
|
PRBool result = false;
|
|
PRBool ans = false;
|
|
int i;
|
|
if (literal->bt) return false;
|
|
/* find a value that satisfies predicate */
|
|
for (i = 0; i < literal->valueCount; i++) {
|
|
TermStruc valueTerm = *(literal->v + i);
|
|
if (comparisonp(s)) {
|
|
/* unit is a variable in all comparisons.
|
|
value may be a variable or a constant.
|
|
*/
|
|
switch (literal->valueType) {
|
|
char *str, *pattern;
|
|
int i, j;
|
|
case RDF_STRING_TYPE:
|
|
if (literal->u.type != RDF_VARIABLE_TERM_TYPE) return false; /* error */
|
|
if (((RDF_Variable)literal->u.value)->type != RDF_STRING_TYPE) return false;
|
|
str = (char*)RDF_GetVariableValue((RDF_Variable)literal->u.value);
|
|
switch (valueTerm.type) {
|
|
case RDF_VARIABLE_TERM_TYPE:
|
|
pattern = (char*)RDF_GetVariableValue((RDF_Variable)valueTerm.value);
|
|
break;
|
|
case RDF_CONSTANT_TERM_TYPE:
|
|
pattern = (char*)valueTerm.value;
|
|
break;
|
|
default:
|
|
/* should blow up */
|
|
return false;
|
|
break;
|
|
}
|
|
if (s == gCoreVocab->RDF_stringEquals) {
|
|
ans = stringEquals(pattern, str);
|
|
} else if (s == gCoreVocab->RDF_substring) {
|
|
ans = substring(pattern, str);
|
|
} else if (s == gCoreVocab->RDF_notStringEquals) {
|
|
ans = !stringEquals(pattern, str);
|
|
} else if (s == gCoreVocab->RDF_notSubstring) {
|
|
ans = !substring(pattern, str);
|
|
} else return false; /* error */
|
|
break;
|
|
case RDF_INT_TYPE:
|
|
if (literal->u.type != RDF_VARIABLE_TERM_TYPE) return false; /* error */
|
|
if (((RDF_Variable)literal->u.value)->type != RDF_INT_TYPE) return false;
|
|
i = (int)RDF_GetVariableValue((RDF_Variable)literal->u.value);
|
|
switch (valueTerm.type) {
|
|
case RDF_VARIABLE_TERM_TYPE:
|
|
j = (int)RDF_GetVariableValue((RDF_Variable)valueTerm.value);
|
|
break;
|
|
case RDF_CONSTANT_TERM_TYPE:
|
|
j = (int)valueTerm.value;
|
|
break;
|
|
default:
|
|
/* should blow up */
|
|
return false;
|
|
break;
|
|
}
|
|
if (s == gCoreVocab->RDF_equals) {
|
|
ans = (i == j);
|
|
} else if (s == gCoreVocab->RDF_notEquals) {
|
|
ans = (i != j);
|
|
} else if (s == gCoreVocab->RDF_lessThan) {
|
|
ans = (i < j);
|
|
} else if (s == gCoreVocab->RDF_greaterThan) {
|
|
ans = (i > j);
|
|
} else if (s == gCoreVocab->RDF_lessThanOrEqual) {
|
|
ans = (i <= j);
|
|
} else if (s == gCoreVocab->RDF_greaterThanOrEqual) {
|
|
ans = (i >= j);
|
|
} else return false;
|
|
break;
|
|
default:
|
|
return false;
|
|
break;
|
|
}
|
|
}
|
|
else {
|
|
u = (RDF_Resource)((variableTermp(literal->u)) ? ((RDF_Variable)literal->u.value)->value : literal->u.value);
|
|
/* special predicates */
|
|
if (s == gCoreVocab->RDF_notInstanceOf) {
|
|
ans = !RDF_HasAssertion(q->rdf, u, gCoreVocab->RDF_instanceOf, valueTerm.value, literal->valueType, true);
|
|
} else if (s == gCoreVocab->RDF_notParent) {
|
|
ans = !RDF_HasAssertion(q->rdf, u, gCoreVocab->RDF_parent, valueTerm.value, literal->valueType, true);
|
|
} else ans = RDF_HasAssertion(q->rdf, u, s, valueTerm.value, literal->valueType, true);
|
|
}
|
|
literal->bt = true;
|
|
/* result = ((literal->tv == true) ? ans : !ans); */
|
|
result = ans;
|
|
if (result) return result; /* otherwise try next value */
|
|
}
|
|
return result;
|
|
}
|
|
u = (RDF_Resource)((variableTermp(literal->u)) ? ((RDF_Variable)literal->u.value)->value : literal->u.value);
|
|
v = (variableTermp(*literal->v)) ? ((RDF_Variable)literal->v->value)->value : literal->v->value;
|
|
if ((u == NULL) && variableTermp(literal->u) && resourceTermp(*literal->v)) {
|
|
literal->c = RDF_GetSources(q->rdf, (RDF_Resource)v, s, literal->valueType, true);
|
|
if (literal->c == NULL) return false;
|
|
RDF_SetVariableValue(literal->variable, RDF_NextValue(literal->c), literal->valueType);
|
|
return (RDF_GetVariableValue(literal->variable) != NULL);
|
|
} else if ((v == NULL) && variableTermp(*literal->v) && (u != NULL)) {
|
|
literal->c = RDF_GetTargets(q->rdf, u, s, literal->valueType, true); /* note arg order differs from java implementation */
|
|
if (literal->c == NULL) return false;
|
|
RDF_SetVariableValue(literal->variable, RDF_NextValue(literal->c), literal->valueType);
|
|
return (RDF_GetVariableValue(literal->variable) != NULL);
|
|
} else return false;
|
|
}
|
|
}
|
|
|
|
PR_PUBLIC_API(PRBool) RDF_RunQuery (RDF_Query q) {
|
|
q->queryRunning = true;
|
|
orderConjuncts(q);
|
|
if (q->conjunctsOrdered)
|
|
return true;
|
|
else return false;
|
|
}
|
|
|
|
PR_PUBLIC_API(PRBool) RDF_GetNextElement(RDF_Query q) {
|
|
if (!q->queryRunning) RDF_RunQuery(q);
|
|
if (q->index == q->numLiterals) q->index--;
|
|
while (q->index < q->numLiterals) {
|
|
RDF_Literal lit = getNthLiteral(q, q->index); /* we know it's it range so don't have to check for NULL */
|
|
if (!processNextLiteral(q, lit)) {
|
|
if (q->index == 0) return false;
|
|
lit->c = NULL;
|
|
if (lit->variable != NULL) RDF_SetVariableValue(lit->variable, (void*)NULL, RDF_RESOURCE_TYPE);
|
|
lit->bt = false;
|
|
q->index--;
|
|
} else {
|
|
q->index++;
|
|
}
|
|
}
|
|
return true;
|
|
}
|
|
|
|
PR_PUBLIC_API(void) RDF_EndQuery (RDF_Query q) {
|
|
q->queryRunning = false;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_VariableList) RDF_GetVariableList(RDF_Query q) {
|
|
return q->variables;
|
|
}
|
|
|
|
/* Note: should put a test for overflow of numLiterals */
|
|
|
|
/* Adds a literal to the query. */
|
|
void addLiteral(RDF_Query q, RDF_Literal literal) {
|
|
RDF_LiteralList newlist = (RDF_LiteralList)getMem(sizeof(RDF_LiteralListStruc));
|
|
if (newlist == NULL) return;
|
|
newlist->element = literal;
|
|
newlist->next = q->literals;
|
|
q->literals = newlist;
|
|
q->numLiterals++;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_Error) RDF_AddConjunctVRV(RDF_Query q, RDF_Variable arg1, RDF_Resource s, RDF_Variable arg2, RDF_ValueType type) {
|
|
RDF_Literal literal = (RDF_Literal)getMem(sizeof(LiteralStruc));
|
|
if (literal == NULL) return RDF_NO_MEMORY;
|
|
literal->u.value = (void*)arg1;
|
|
literal->u.type = RDF_VARIABLE_TERM_TYPE;
|
|
((RDF_Variable)literal->u.value)->type = RDF_RESOURCE_TYPE;
|
|
literal->s = s;
|
|
literal->valueCount = 1;
|
|
literal->v = (TermStruc*)getMem(sizeof(TermStruc));
|
|
literal->v->value = (void*)arg2;
|
|
literal->v->type = RDF_VARIABLE_TERM_TYPE;
|
|
((RDF_Variable)literal->v->value)->type = literal->valueType = type;
|
|
literal->tv = true;
|
|
addLiteral(q, literal);
|
|
q->conjunctsOrdered = false;
|
|
return noRDFErr;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_Error) RDF_AddConjunctVRO(RDF_Query q, RDF_Variable arg1, RDF_Resource s, void* arg2, RDF_ValueType type) {
|
|
RDF_Literal literal = (RDF_Literal)getMem(sizeof(LiteralStruc));
|
|
if (literal == NULL) return RDF_NO_MEMORY;
|
|
literal->u.value = (void*)arg1;
|
|
literal->u.type = RDF_VARIABLE_TERM_TYPE;
|
|
((RDF_Variable)literal->u.value)->type = type;
|
|
literal->s = s;
|
|
literal->valueCount = 1;
|
|
literal->v = (TermStruc*)getMem(sizeof(TermStruc));
|
|
literal->v->value = (type == RDF_STRING_TYPE) ? (void*)copyString((char*)arg2) : (void*)arg2;
|
|
literal->v->type = RDF_CONSTANT_TERM_TYPE;
|
|
literal->valueType = type;
|
|
literal->tv = true;
|
|
addLiteral(q, literal);
|
|
q->conjunctsOrdered = false;
|
|
return noRDFErr;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_Error) RDF_AddConjunctRRO(RDF_Query q, RDF_Resource arg1, RDF_Resource s, void* arg2, RDF_ValueType type) {
|
|
RDF_Literal literal = (RDF_Literal)getMem(sizeof(LiteralStruc));
|
|
if (literal == NULL) return RDF_NO_MEMORY;
|
|
literal->u.value = (void*)arg1;
|
|
literal->u.type = RDF_RESOURCE_TERM_TYPE;
|
|
literal->s = s;
|
|
literal->valueCount = 1;
|
|
literal->v = (TermStruc*)getMem(sizeof(TermStruc));
|
|
literal->v->value = (type == RDF_STRING_TYPE) ? (void*)copyString((char*)arg2) : (void*)arg2;
|
|
literal->v->type = RDF_CONSTANT_TERM_TYPE;
|
|
literal->valueType = type;
|
|
literal->tv = true;
|
|
addLiteral(q, literal);
|
|
q->conjunctsOrdered = false;
|
|
return noRDFErr;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_Error) RDF_AddConjunctVRR(RDF_Query q, RDF_Variable arg1, RDF_Resource s, RDF_Resource arg2) {
|
|
RDF_Literal literal = (RDF_Literal)getMem(sizeof(LiteralStruc));
|
|
if (literal == NULL) return RDF_NO_MEMORY;
|
|
literal->u.value = (void*)arg1;
|
|
literal->u.type = RDF_VARIABLE_TERM_TYPE;
|
|
((RDF_Variable)literal->u.value)->type = RDF_RESOURCE_TYPE;
|
|
literal->s = s;
|
|
literal->valueCount = 1;
|
|
literal->v = (TermStruc*)getMem(sizeof(TermStruc));
|
|
literal->v->value = (void*)arg2;
|
|
literal->v->type = RDF_RESOURCE_TERM_TYPE;
|
|
literal->valueType = RDF_RESOURCE_TYPE;
|
|
literal->tv = true;
|
|
addLiteral(q, literal);
|
|
q->conjunctsOrdered = false;
|
|
return noRDFErr;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_Error) RDF_AddConjunctRRV(RDF_Query q, RDF_Resource arg1, RDF_Resource s, RDF_Variable arg2, RDF_ValueType type) {
|
|
RDF_Literal literal = (RDF_Literal)getMem(sizeof(LiteralStruc));
|
|
if (literal == NULL) return RDF_NO_MEMORY;
|
|
literal->u.value = arg1;
|
|
literal->u.type = RDF_RESOURCE_TERM_TYPE;
|
|
literal->s = s;
|
|
literal->valueCount = 1;
|
|
literal->v = (TermStruc*)getMem(sizeof(TermStruc));
|
|
literal->v->value = (void*)arg2;
|
|
literal->v->type = RDF_VARIABLE_TERM_TYPE;
|
|
((RDF_Variable)literal->v->value)->type = literal->valueType = type;
|
|
literal->tv = true;
|
|
addLiteral(q, literal);
|
|
q->conjunctsOrdered = false;
|
|
return noRDFErr;
|
|
}
|
|
|
|
PR_PUBLIC_API(RDF_Error) RDF_AddConjunctVRL(RDF_Query q, RDF_Variable arg1, RDF_Resource s, RDF_Term arg2, RDF_ValueType type, uint8 count) {
|
|
RDF_Literal literal = (RDF_Literal)getMem(sizeof(LiteralStruc));
|
|
if (literal == NULL) return RDF_NO_MEMORY;
|
|
literal->u.value = (void*)arg1;
|
|
literal->u.type = RDF_VARIABLE_TERM_TYPE;
|
|
((RDF_Variable)literal->u.value)->type = type;
|
|
literal->s = s;
|
|
literal->valueCount = count;
|
|
literal->v = (void*)arg2;
|
|
/* value and type of each term already assigned */
|
|
literal->valueType = type;
|
|
literal->tv = true;
|
|
addLiteral(q, literal);
|
|
q->conjunctsOrdered = false;
|
|
return noRDFErr;
|
|
}
|