/** * rasqal_reset_triple_meta: * @m: Triple pattern metadata * * INTERNAL - reset the metadata associated with a triple pattern * * Return value: number of parts of the triple that were reset (0..4) **/ int rasqal_reset_triple_meta(rasqal_triple_meta* m) { int resets = 0; if(m->triples_match) { rasqal_free_triples_match(m->triples_match); m->triples_match = NULL; } if(m->bindings[0] && (m->parts & RASQAL_TRIPLE_SUBJECT)) { rasqal_variable_set_value(m->bindings[0], NULL); resets++; } if(m->bindings[1] && (m->parts & RASQAL_TRIPLE_PREDICATE)) { rasqal_variable_set_value(m->bindings[1], NULL); resets++; } if(m->bindings[2] && (m->parts & RASQAL_TRIPLE_OBJECT)) { rasqal_variable_set_value(m->bindings[2], NULL); resets++; } if(m->bindings[3] && (m->parts & RASQAL_TRIPLE_ORIGIN)) { rasqal_variable_set_value(m->bindings[3], NULL); resets++; } m->executed = 0; return resets; }
static void rasqal_query_results_update_bindings(rasqal_query_results* query_results) { int i; int size; RASQAL_ASSERT_OBJECT_POINTER_RETURN(query_results, rasqal_query_results); /* bind the construct variables again if running through a sequence */ size = rasqal_variables_table_get_named_variables_count(query_results->vars_table); for(i = 0; i< size; i++) { rasqal_variable* v; rasqal_row* row; rasqal_literal* value = NULL; v = rasqal_variables_table_get(query_results->vars_table, i); rasqal_query_results_ensure_have_row_internal(query_results); row = query_results->row; if(row) { if (i >= row->size) continue; value = row->values[i]; } else query_results->finished = 1; rasqal_variable_set_value(v, rasqal_new_literal_from_literal(value)); } }
/** * rasqal_row_bind_variables: * @row: Result row * @vars_table: Variables table * * INTERNAL - Bind the variable table vars withvalues in the row * * Return value: non-0 on failure */ int rasqal_row_bind_variables(rasqal_row* row, rasqal_variables_table* vars_table) { int i; for(i = 0; i < row->size; i++) { rasqal_variable* v; v = rasqal_rowsource_get_variable_by_offset(row->rowsource, i); if(v) { rasqal_literal *value = row->values[i]; if(value) { value = rasqal_new_literal_from_literal(value); if(!value) return 1; } /* it is OK to bind to NULL */ rasqal_variable_set_value(v, value); } } return 0; }
int rasqal_variables_table_set(rasqal_variables_table* vt, const unsigned char *name, rasqal_literal* value) { rasqal_variable* v; v = rasqal_variables_table_get_by_name(vt, name); if(!v) return 1; rasqal_variable_set_value(v, value); return 0; }
static int rasqal_graph_rowsource_finish(rasqal_rowsource* rowsource, void *user_data) { rasqal_graph_rowsource_context *con; con = (rasqal_graph_rowsource_context*)user_data; if(con->rowsource) rasqal_free_rowsource(con->rowsource); rasqal_variable_set_value(con->var, NULL); RASQAL_FREE(rasqal_graph_rowsource_context, con); return 0; }
static int rasqal_graph_next_dg(rasqal_graph_rowsource_context *con) { rasqal_query *query = con->rowsource->query; rasqal_data_graph *dg; con->finished = 0; while(1) { rasqal_literal *o; con->dg_offset++; dg = rasqal_query_get_data_graph(query, con->dg_offset); if(!dg) { con->finished = 1; break; } if(!dg->name_uri) continue; o = rasqal_new_uri_literal(query->world, raptor_uri_copy(dg->name_uri)); if(!o) { RASQAL_DEBUG1("Failed to create new URI literal\n"); con->finished = 1; break; } RASQAL_DEBUG2("Using data graph URI literal <%s>\n", rasqal_literal_as_string(o)); rasqal_rowsource_set_origin(con->rowsource, o); /* this passes ownership of o to con->var */ rasqal_variable_set_value(con->var, o); break; } return con->finished; }
static rasqal_row* rasqal_aggregation_rowsource_read_row(rasqal_rowsource* rowsource, void *user_data) { rasqal_aggregation_rowsource_context* con; rasqal_row* row; int error = 0; con = (rasqal_aggregation_rowsource_context*)user_data; if(con->finished) return NULL; /* Iterate over input rows until last row seen or group done */ while(1) { error = 0; if(con->saved_row) row = con->saved_row; else row = rasqal_rowsource_read_row(con->rowsource); if(!row) { /* End of input - calculate last aggregation result */ con->finished = 1; break; } if(con->last_group_id != row->group_id) { int i; if(!con->saved_row && con->last_group_id >= 0) { /* Existing aggregation is done - return result */ /* save current row for next time this function is called */ con->saved_row = row; row = NULL; #ifdef RASQAL_DEBUG RASQAL_DEBUG2("Aggregation ending group %d", con->last_group_id); fputc('\n', DEBUG_FH); #endif /* Empty distinct maps */ for(i = 0; i < con->expr_count; i++) { rasqal_agg_expr_data* expr_data = &con->expr_data[i]; if(expr_data->map) { rasqal_free_map(expr_data->map); expr_data->map = NULL; } } break; } /* reference is now in 'row' variable */ con->saved_row = NULL; #ifdef RASQAL_DEBUG RASQAL_DEBUG2("Aggregation starting group %d", row->group_id); fputc('\n', DEBUG_FH); #endif /* next time this function is called we continue here */ for(i = 0; i < con->expr_count; i++) { rasqal_agg_expr_data* expr_data = &con->expr_data[i]; if(!expr_data->agg_user_data) { /* init once */ expr_data->agg_user_data = rasqal_builtin_agg_expression_execute_init(rowsource->world, expr_data->expr); if(!expr_data->agg_user_data) { error = 1; break; } } /* Init map for each group */ if(expr_data->expr->flags & RASQAL_EXPR_FLAG_DISTINCT) { expr_data->map = rasqal_new_literal_sequence_sort_map(1 /* is_distinct */, 0 /* compare_flags */); if(!expr_data->map) { error = 1; break; } } } if(error) break; con->last_group_id = row->group_id; } /* end if handling change of group ID */ /* Bind the values in the input row to the variables in the table */ rasqal_row_bind_variables(row, rowsource->query->vars_table); /* Evaluate the expressions giving a sequence of literals to * run the aggregation step over. */ if(1) { int i; if(!con->step_count) { /* copy first value row from input rowsource */ for(i = 0; i < con->input_values_count; i++) { rasqal_literal* value; value = rasqal_new_literal_from_literal(row->values[i]); raptor_sequence_set_at(con->input_values, i, value); } } con->step_count++; for(i = 0; i < con->expr_count; i++) { rasqal_agg_expr_data* expr_data = &con->expr_data[i]; raptor_sequence* seq; /* SPARQL Aggregation uses ListEvalE() to evaluate - ignoring * errors and filtering out expressions that fail */ seq = rasqal_expression_sequence_evaluate(rowsource->query, expr_data->exprs_seq, /* ignore_errors */ 1, &error); if(error) continue; if(expr_data->map) { if(rasqal_literal_sequence_sort_map_add_literal_sequence(expr_data->map, seq)) { /* duplicate found * * The above function just freed seq so no data is lost */ continue; } } #ifdef RASQAL_DEBUG RASQAL_DEBUG1("Aggregation step over literals: "); raptor_sequence_print(seq, DEBUG_FH); fputc('\n', DEBUG_FH); #endif error = rasqal_builtin_agg_expression_execute_step(expr_data->agg_user_data, seq); /* when DISTINCTing, seq remains owned by the map * otherwise seq is local and must be freed */ if(!expr_data->map) raptor_free_sequence(seq); if(error) break; } } rasqal_free_row(row); row = NULL; if(error) break; } /* end while reading rows */ if(error) { /* Discard row on error */ if(row) { rasqal_free_row(row); row = NULL; } } else if (con->last_group_id >= 0) { int offset = 0; int i; /* Generate result row and reset for next group */ row = rasqal_new_row(rowsource); /* Copy scalar results through */ for(i = 0; i < con->input_values_count; i++) { rasqal_literal* result; /* Reset: get and delete any stored input rowsource literal */ result = (rasqal_literal*)raptor_sequence_delete_at(con->input_values, i); rasqal_row_set_value_at(row, offset, result); rasqal_free_literal(result); offset++; } /* Set aggregate results */ for(i = 0; i < con->expr_count; i++) { rasqal_literal* result; rasqal_agg_expr_data* expr_data = &con->expr_data[i]; rasqal_variable* v; /* Calculate the result because the input ended or a new group started */ result = rasqal_builtin_agg_expression_execute_result(expr_data->agg_user_data); #ifdef RASQAL_DEBUG RASQAL_DEBUG1("Aggregation ending group with result: "); if(result) rasqal_literal_print(result, DEBUG_FH); else fputs("NULL", DEBUG_FH); fputc('\n', DEBUG_FH); #endif v = rasqal_rowsource_get_variable_by_offset(rowsource, offset); result = rasqal_new_literal_from_literal(result); /* it is OK to bind to NULL */ rasqal_variable_set_value(v, result); rasqal_row_set_value_at(row, offset, result); if(result) rasqal_free_literal(result); offset++; if(rasqal_builtin_agg_expression_execute_reset(expr_data->agg_user_data)) { rasqal_free_row(row); row = NULL; break; } } con->step_count = 0; if(row) row->offset = con->offset++; } return row; }
static rasqal_triple_parts rasqal_redland_bind_match(struct rasqal_triples_match_s* rtm, void *user_data, rasqal_variable* bindings[4], rasqal_triple_parts parts) { rasqal_redland_triples_match_context* rtmc=(rasqal_redland_triples_match_context*)rtm->user_data; rasqal_literal* l; librdf_statement* statement; rasqal_triple_parts result=(rasqal_triple_parts)0; librdf_world *world = rtmc->stream->world; statement=librdf_stream_get_object(rtmc->stream); if(!statement) return (rasqal_triple_parts)0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1(" matched statement "); librdf_statement_print(statement, stderr); fputc('\n', stderr); #endif /* set 1 or 2 variable values from the fields of statement */ if(bindings[0] && (parts & RASQAL_TRIPLE_SUBJECT)) { #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("binding subject to variable\n"); #endif l = redland_node_to_rasqal_literal(world, librdf_statement_get_subject(statement)); rasqal_variable_set_value(bindings[0], l); result= RASQAL_TRIPLE_SUBJECT; } if(bindings[1] && (parts & RASQAL_TRIPLE_PREDICATE)) { if(bindings[0] == bindings[1]) { /* check matching(?x, ?x, ...) / subject=predicate */ if(!librdf_node_equals(librdf_statement_get_subject(statement), librdf_statement_get_predicate(statement))) return (rasqal_triple_parts)0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("subject and predicate values match\n"); #endif } else { #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("binding predicate to variable\n"); #endif l = redland_node_to_rasqal_literal(world, librdf_statement_get_predicate(statement)); rasqal_variable_set_value(bindings[1], l); result= (rasqal_triple_parts)(result | RASQAL_TRIPLE_PREDICATE); } } if(bindings[2] && (parts & RASQAL_TRIPLE_OBJECT)) { int bind=1; if(bindings[0] == bindings[2]) { /* check matching (?x, ..., ?x) / subject=object */ if(!librdf_node_equals(librdf_statement_get_subject(statement), librdf_statement_get_object(statement))) return (rasqal_triple_parts)0; bind=0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("subject and object values match\n"); #endif } if((bindings[1] == bindings[2]) && !(bindings[0] == bindings[1])) { /* check matching (..., ?x, ?x) / predicate=object * Don't do this if matching (?x, ?x, ...) / subject=predicate * was already done since that would mean the match was (?x, ?x, ?x) */ if(!librdf_node_equals(librdf_statement_get_predicate(statement), librdf_statement_get_object(statement))) return (rasqal_triple_parts)0; bind=0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("predicate and object values match\n"); #endif } if(bind) { #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("binding object to variable\n"); #endif l = redland_node_to_rasqal_literal(world, librdf_statement_get_object(statement)); rasqal_variable_set_value(bindings[2], l); result= (rasqal_triple_parts)(result | RASQAL_TRIPLE_OBJECT); } } /* Contexts */ if(bindings[3] && (parts & RASQAL_TRIPLE_ORIGIN)) { int bind=1; librdf_node* context_node = librdf_stream_get_context2(rtmc->stream); if(bindings[0] == bindings[3]) { /* check matching (?x, ..., ...) in context ?x */ if(!librdf_node_equals(librdf_statement_get_subject(statement), context_node)) return (rasqal_triple_parts)0; bind=0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("subject and context values match\n"); #endif } if(bindings[1] == bindings[3]) { /* check matching (..., ?x, ...) in context ?x */ if(!librdf_node_equals(librdf_statement_get_predicate(statement), context_node)) return (rasqal_triple_parts)0; bind=0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("predicate and context values match\n"); #endif } if(bindings[2] == bindings[3]) { /* check matching (..., ..., ?x) in context ?x */ if(!librdf_node_equals(librdf_statement_get_object(statement), context_node)) return (rasqal_triple_parts)0; bind=0; #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("object and context values match\n"); #endif } if(bind) { #if defined(LIBRDF_DEBUG) && LIBRDF_DEBUG > 1 LIBRDF_DEBUG1("binding origin to variable\n"); #endif if(context_node) l = redland_node_to_rasqal_literal(world, context_node); else l=NULL; rasqal_variable_set_value(bindings[3], l); result= (rasqal_triple_parts)(result | RASQAL_TRIPLE_ORIGIN); } } return result; }