static int create_filepath_sexpr(char *arg_operation, char *arg_argument, SEXP_t **result) { *result = NULL; /* non-fatal error */ if (strlen(arg_operation) == 0 && strlen(arg_argument) == 0) { return 0; } int operation_number = oval_operation_from_text(arg_operation); if (operation_number <= 0 || operation_number > 255) { fprintf(stderr, "Error parsing path->operation number -- not a valid OVAL_OPERATION enum string: %s\n", arg_operation); return 1; } uint8_t operation_value = (uint8_t)(operation_number & 0xFF); SEXP_t *s_filepath_str = SEXP_string_new("filepath", 8); SEXP_t *s_operation_str = SEXP_string_new(":operation", 10); SEXP_t *s_operation_number = SEXP_number_new(SEXP_NUM_UINT8, &operation_value); SEXP_t *s_filepath_argument = SEXP_string_new(arg_argument, strlen(arg_argument)); SEXP_t *s_inner_list = SEXP_list_new(NULL); SEXP_list_add(s_inner_list, s_filepath_str); SEXP_list_add(s_inner_list, s_operation_str); SEXP_list_add(s_inner_list, s_operation_number); *result = SEXP_list_new(NULL); SEXP_list_add(*result, s_inner_list); SEXP_list_add(*result, s_filepath_argument); return 0; }
static SEXP_t *oval_behaviors_to_sexp(struct oval_behavior_iterator *bit) { char *attr_name, *attr_val; SEXP_t *elm_name; SEXP_t *r0; struct oval_behavior *behavior; elm_name = SEXP_list_new(r0 = SEXP_string_newf("behaviors"), NULL); SEXP_free(r0); while (oval_behavior_iterator_has_more(bit)) { behavior = oval_behavior_iterator_next(bit); attr_name = oval_behavior_get_key(behavior); attr_val = oval_behavior_get_value(behavior); SEXP_list_add(elm_name, r0 = SEXP_string_newf(":%s", attr_name)); SEXP_free(r0); if (attr_val != NULL) { SEXP_list_add(elm_name, r0 = SEXP_string_new(attr_val, strlen(attr_val))); SEXP_free(r0); } } r0 = SEXP_list_new(elm_name, NULL); SEXP_free(elm_name); return (r0); }
static SEXP_t *oval_probe_cmd_obj_eval(SEXP_t *sexp, void *arg) { char *id_str; struct oval_definition_model *defs; struct oval_object *obj; struct oval_syschar *res; oval_pext_t *pext = (oval_pext_t *) arg; SEXP_t *ret, *ret_code; int r; if (sexp == NULL || arg == NULL) { return NULL; } if (!SEXP_stringp(sexp)) { dE("Invalid argument: type=%s.", SEXP_strtype(sexp)); return (NULL); } id_str = SEXP_string_cstr(sexp); defs = oval_syschar_model_get_definition_model(*(pext->model)); obj = oval_definition_model_get_object(defs, id_str); ret = SEXP_list_new (sexp, NULL); dI("Get_object: %s.", id_str); if (obj == NULL) { dE("Can't find obj: id=%s.", id_str); free(id_str); SEXP_free(ret); return (NULL); } oscap_clearerr(); r = oval_probe_query_object(pext->sess_ptr, obj, OVAL_PDFLAG_NOREPLY|OVAL_PDFLAG_SLAVE, &res); if (r < 0) ret_code = SEXP_number_newu((unsigned int) SYSCHAR_FLAG_COMPLETE); else ret_code = SEXP_number_newu((unsigned int) oval_syschar_get_flag(res)); SEXP_list_add(ret, ret_code); SEXP_free(ret_code); if (oscap_err()) { dE("Failed: id: %s, err: %d, %s.", id_str, oscap_err_family(), oscap_err_desc()); oscap_clearerr(); free(id_str); SEXP_free(ret); return (NULL); } free(id_str); return (ret); }
static int oval_varref_elm_to_sexp(void *sess, struct oval_variable *var, oval_datatype_t dt, SEXP_t **out_sexp, struct oval_syschar *syschar) { SEXP_t *val_lst; struct oval_value_iterator *val_itr; oval_syschar_collection_flag_t flag; if (oval_probe_query_variable(sess, var) != 0) return -1; flag = oval_variable_get_collection_flag(var); if (flag == SYSCHAR_FLAG_DOES_NOT_EXIST) { char msg[100]; snprintf(msg, sizeof(msg), "Referenced variable has no values (%s).", oval_variable_get_id(var)); dI("%s", msg); if (syschar != NULL) { oval_syschar_add_new_message(syschar, msg, OVAL_MESSAGE_LEVEL_WARNING); oval_syschar_set_flag(syschar, SYSCHAR_FLAG_DOES_NOT_EXIST); } return 1; } if (flag != SYSCHAR_FLAG_COMPLETE && flag != SYSCHAR_FLAG_INCOMPLETE) { *out_sexp = SEXP_list_new(NULL); return 0; } val_lst = SEXP_list_new(NULL); val_itr = oval_variable_get_values(var); while (oval_value_iterator_has_more(val_itr)) { struct oval_value *val; SEXP_t *vs; val = oval_value_iterator_next(val_itr); vs = oval_value_to_sexp(val, dt); if (vs == NULL) { oscap_seterr(OSCAP_EFAMILY_OVAL, "Failed to convert OVAL value to SEXP: " "datatype: %s, text: %s.", oval_datatype_get_text(dt), oval_value_get_text(val)); oval_value_iterator_free(val_itr); SEXP_free(val_lst); return -1; } SEXP_list_add(val_lst, vs); SEXP_free(vs); } oval_value_iterator_free(val_itr); *out_sexp = val_lst; return 0; }
static SEXP_t *oval_probe_cmd_ste_fetch(SEXP_t *sexp, void *arg) { SEXP_t *id, *ste_list, *ste_sexp; char *id_str; struct oval_state *ste; struct oval_definition_model *definition_model; oval_pext_t *pext = (oval_pext_t *)arg; int ret; if (sexp == NULL || arg == NULL) { return NULL; } ste_list = SEXP_list_new(NULL); SEXP_list_foreach(id, sexp) { if (SEXP_stringp(id)) { id_str = SEXP_string_cstr(id); definition_model = oval_syschar_model_get_definition_model(*(pext->model)); ste = oval_definition_model_get_state(definition_model, id_str); if (ste == NULL) { dE("Can't find ste: id: %s.", id_str); SEXP_list_free(ste_list); free(id_str); SEXP_free(id); return (NULL); } ret = oval_state_to_sexp(pext->sess_ptr, ste, &ste_sexp); if (ret !=0) { dE("Failed to convert OVAL state to SEXP, id: %s.", id_str); SEXP_list_free(ste_list); free(id_str); SEXP_free(id); return (NULL); } SEXP_list_add(ste_list, ste_sexp); SEXP_free(ste_sexp); free(id_str); } } return (ste_list); }
static int create_behaviors_sexpr(char *arg_max_depth, char *arg_recurse, char *arg_recurse_direction, char *arg_recurse_file_system, SEXP_t **result) { *result = NULL; /* non-fatal error */ if (strlen(arg_max_depth) == 0 && strlen(arg_recurse) == 0 && strlen(arg_recurse_direction) == 0 && strlen(arg_recurse_file_system) == 0) { return 0; } SEXP_t *s_behaviors_str = SEXP_string_new("behaviors", 9); SEXP_t *s_max_depth_str = SEXP_string_new(":max_depth", 10); SEXP_t *s_max_depth_argument = SEXP_string_new(arg_max_depth, strlen(arg_max_depth)); SEXP_t *s_recurse_str = SEXP_string_new(":recurse", 8); SEXP_t *s_recurse_argument = SEXP_string_new(arg_recurse, strlen(arg_recurse)); SEXP_t *s_recurse_direction_str = SEXP_string_new(":recurse_direction", 18); SEXP_t *s_recurse_direction_argument = SEXP_string_new(arg_recurse_direction, strlen(arg_recurse_direction)); SEXP_t *s_recurse_file_system_str = SEXP_string_new(":recurse_file_system", 20); SEXP_t *s_recurse_file_system_argument = SEXP_string_new(arg_recurse_file_system, strlen(arg_recurse_file_system)); SEXP_t *s_inner_list = SEXP_list_new(NULL); SEXP_list_add(s_inner_list, s_behaviors_str); SEXP_list_add(s_inner_list, s_max_depth_str); SEXP_list_add(s_inner_list, s_max_depth_argument); SEXP_list_add(s_inner_list, s_recurse_str); SEXP_list_add(s_inner_list, s_recurse_argument); SEXP_list_add(s_inner_list, s_recurse_direction_str); SEXP_list_add(s_inner_list, s_recurse_direction_argument); SEXP_list_add(s_inner_list, s_recurse_file_system_str); SEXP_list_add(s_inner_list, s_recurse_file_system_argument); *result = SEXP_list_new(NULL); SEXP_list_add(*result, s_inner_list); return 0; }
static SEXP_t *oval_entity_to_sexp(struct oval_entity *ent) { SEXP_t *elm, *elm_name; SEXP_t *r0, *r1, *r2; oval_datatype_t datatype; oval_entity_varref_type_t vr_type; elm_name = SEXP_list_new(r0 = SEXP_string_newf("%s", oval_entity_get_name(ent)), /* operation */ r1 = SEXP_string_new(":operation", 10), r2 = SEXP_number_newu_32(oval_entity_get_operation(ent)), NULL); SEXP_vfree(r0, r1, r2, NULL); if (oval_entity_get_mask(ent)) { SEXP_list_add(elm_name, r0 = SEXP_string_new("mask", 4)); SEXP_free(r0); } elm = SEXP_list_new(NULL); datatype = oval_entity_get_datatype(ent); probe_ent_setdatatype(elm, datatype); vr_type = oval_entity_get_varref_type(ent); if (vr_type == OVAL_ENTITY_VARREF_ATTRIBUTE || vr_type == OVAL_ENTITY_VARREF_ELEMENT) { /* var_ref */ struct oval_variable *var; var = oval_entity_get_variable(ent); SEXP_list_add(elm_name, r0 = SEXP_string_new(":var_ref", 8)); SEXP_list_add(elm_name, r1 = SEXP_string_newf("%s", oval_variable_get_id(var))); SEXP_list_add(elm, elm_name); SEXP_vfree(r0, r1, elm_name, NULL); } else { /* value */ struct oval_value *val; SEXP_list_add(elm, elm_name); SEXP_free(elm_name); val = oval_entity_get_value(ent); if (datatype != OVAL_DATATYPE_RECORD && val != NULL) { SEXP_t *val_sexp; val_sexp = oval_value_to_sexp(val, datatype); if (val_sexp != NULL) { SEXP_list_add(elm, val_sexp); SEXP_free(val_sexp); } } } return (elm); }
static oval_result_t _probe_entste_cmp_record(SEXP_t *ent_ste, SEXP_t *ent_itm) { oval_result_t res; oval_operation_t op; oval_check_t ochk; SEXP_t *stmp, *ste_res, *ste_record_fields, *ste_rf, *itm_record_fields; int val_cnt; stmp = probe_ent_getattrval(ent_ste, "operation"); if (stmp == NULL) { op = OVAL_OPERATION_EQUALS; } else { op = SEXP_number_getu(stmp); SEXP_free(stmp); if (op != OVAL_OPERATION_EQUALS) return OVAL_RESULT_ERROR; } val_cnt = probe_ent_getvals(ent_ste, &ste_record_fields); if (val_cnt <= 0) { SEXP_free(ste_record_fields); return OVAL_RESULT_ERROR; } val_cnt = probe_ent_getvals(ent_itm, &itm_record_fields); if (val_cnt <= 0) { SEXP_free(ste_record_fields); SEXP_free(itm_record_fields); return OVAL_RESULT_ERROR; } ste_res = SEXP_list_new(NULL); SEXP_list_foreach(ste_rf, ste_record_fields) { SEXP_t *itm_rf, *itm_res; const char *sname; bool matched; sname = probe_ent_getname(ste_rf); itm_res = SEXP_list_new(NULL); matched = false; SEXP_list_foreach(itm_rf, itm_record_fields) { const char *iname; iname = probe_ent_getname(itm_rf); if (strcmp(sname, iname)) { oscap_free(iname); continue; } oscap_free(iname); matched = true; res = probe_entste_cmp(ste_rf, itm_rf); /* todo: _oval_result_to_sexp() */ stmp = SEXP_number_newu(res); SEXP_list_add(itm_res, stmp); SEXP_free(stmp); } oscap_free(sname); if (!matched) { stmp = SEXP_number_newu(OVAL_RESULT_ERROR); SEXP_list_add(itm_res, stmp); SEXP_free(stmp); } stmp = probe_ent_getattrval(ste_rf, "entity_check"); if (stmp == NULL) { ochk = OVAL_CHECK_ALL; } else { ochk = SEXP_number_getu(stmp); SEXP_free(stmp); } res = probe_ent_result_bychk(itm_res, ochk); SEXP_free(itm_res); stmp = SEXP_number_newu(res); SEXP_list_add(ste_res, stmp); SEXP_free(stmp); }
static oval_result_t probe_ent_cmp(SEXP_t * ent, SEXP_t * val2) { oval_operation_t op; oval_datatype_t dtype; SEXP_t *stmp, *val1, *vals, *res_lst, *r0; int val_cnt, is_var; oval_check_t ochk; oval_result_t ores, result; ores = OVAL_RESULT_ERROR; result = OVAL_RESULT_ERROR; vals = NULL; val_cnt = probe_ent_getvals(ent, &vals); if (probe_ent_attrexists(ent, "var_ref")) { is_var = 1; } else { if (val_cnt != 1) { SEXP_free(vals); return OVAL_RESULT_ERROR; } is_var = 0; } dtype = probe_ent_getdatatype(ent); stmp = probe_ent_getattrval(ent, "operation"); if (stmp == NULL) op = OVAL_OPERATION_EQUALS; else op = SEXP_number_geti_32(stmp); SEXP_free(stmp); res_lst = SEXP_list_new(NULL); SEXP_list_foreach(val1, vals) { if (SEXP_typeof(val1) != SEXP_typeof(val2)) { dI("Types of values to compare don't match: val1: %d, val2: %d\n", SEXP_typeof(val1), SEXP_typeof(val2)); SEXP_free(vals); SEXP_free(val1); SEXP_free(res_lst); return OVAL_RESULT_ERROR; } ores = probe_ent_cmp_single(val1, dtype, val2, op); SEXP_list_add(res_lst, r0 = SEXP_number_newi_32(ores)); SEXP_free(r0); } if (is_var) { stmp = probe_ent_getattrval(ent, "var_check"); if (stmp == NULL) { ochk = OVAL_CHECK_ALL; } else { ochk = SEXP_number_geti_32(stmp); SEXP_free(stmp); } result = probe_ent_result_bychk(res_lst, ochk); } else { result = ores; } SEXP_free(res_lst); SEXP_free(vals); return result; }
int probe_main(probe_ctx *ctx, void *mutex) { LDAP *ldp; LDAPMessage *ldpres, *entry; SEXP_t *se_ldap_behaviors = NULL, *se_relative_dn = NULL; SEXP_t *se_suffix = NULL, *se_attribute = NULL; SEXP_t *sa_scope, *sv_op; SEXP_t *item; SEXP_t *probe_in; char *relative_dn = NULL; char *suffix = NULL, *xattribute = NULL; char *uri_list, *uri, *uri_save, *attr; int scope; char base[2048]; char *attrs[3]; bool a_pattern_match = false, rdn_pattern_match = false; /* runtime */ #if defined(PROBE_LDAP_MUTEX) assume_r(mutex != NULL, PROBE_EINIT); #endif probe_in = probe_ctx_getobject(ctx); se_ldap_behaviors = probe_obj_getent(probe_in, "behaviors", 1); if (se_ldap_behaviors != NULL) { sa_scope = probe_ent_getattrval(se_ldap_behaviors, "scope"); SEXP_free(se_ldap_behaviors); if (sa_scope == NULL) { dE("Atrribute `scope' is missing!"); return (PROBE_ENOATTR); } if (!SEXP_stringp(sa_scope)) { dE("Invalid value type of the `scope' attribute."); SEXP_free(sa_scope); return (PROBE_EINVAL); } if (SEXP_strcmp(sa_scope, "ONE") == 0) scope = LDAP_SCOPE_ONELEVEL; else if (SEXP_strcmp(sa_scope, "BASE") == 0) scope = LDAP_SCOPE_BASE; else if (SEXP_strcmp(sa_scope, "SUBTREE") == 0) scope = LDAP_SCOPE_SUBTREE; else { dE("Invalid value of the `scope' attribute."); SEXP_free(sa_scope); return (PROBE_EINVAL); } SEXP_free(sa_scope); } else scope = LDAP_SCOPE_BASE; #define get_string(dst, se_dst, obj, ent_name) \ do { \ SEXP_t *__sval; \ \ __sval = probe_obj_getentval (obj, ent_name, 1); \ \ if (__sval != NULL) { \ (dst) = SEXP_string_cstr (__sval); \ \ if ((dst) == NULL) { \ SEXP_free(__sval); \ return (PROBE_EINVAL); \ } \ \ (se_dst) = __sval; \ } else { \ return (PROBE_ENOATTR); \ } \ } while (0) get_string(suffix, se_suffix, probe_in, "suffix"); get_string(relative_dn, se_relative_dn, probe_in, "relative_dn"); get_string(xattribute, se_attribute, probe_in, "attribute"); if ((sv_op = probe_ent_getattrval(se_relative_dn, "operation")) != NULL) { if (SEXP_number_geti_32(sv_op) == OVAL_OPERATION_PATTERN_MATCH) rdn_pattern_match = true; SEXP_free(sv_op); } if ((sv_op = probe_ent_getattrval(se_attribute, "operation")) != NULL) { if (SEXP_number_geti_32(sv_op) == OVAL_OPERATION_PATTERN_MATCH) a_pattern_match = true; SEXP_free(sv_op); } /* * Construct the attribute array for ldap_search_* * * nil -> "1.1" * .* -> "*" * "foo" -> "foo" */ attrs[0] = "objectClass"; if (xattribute == NULL) attrs[1] = strdup("1.1"); /* no attibutes */ else if (a_pattern_match) attrs[1] = strdup("*"); /* collect all, we'll filter them afterwards */ else attrs[1] = xattribute; /* no pattern match, use the string directly */ attrs[2] = NULL; /* * Construct `base' */ assume_r(((relative_dn ? strlen(relative_dn) : 0) + ( suffix ? strlen(suffix) : 0) + 2) < (sizeof base/sizeof(char)), PROBE_ERANGE); if (relative_dn != NULL) { strcpy(base, relative_dn); strcat(base, ","); strcat(base, suffix); } else strcpy(base, suffix); /* * Get URIs */ if (ldap_get_option(NULL, LDAP_OPT_URI, &uri_list) != LDAP_OPT_SUCCESS) { item = probe_item_creat("ldap57_item", NULL, NULL); probe_item_setstatus(item, SYSCHAR_STATUS_ERROR); probe_item_collect(ctx, item); dE("ldap_get_option failed"); goto fail0; } /* * Query each URI */ for (;;) { char *entry_dn = NULL; if ((uri = strtok_r(uri_list, " ,", &uri_save)) == NULL) break; ldp = NULL; if (ldap_initialize(&ldp, uri) != LDAP_SUCCESS) continue; if (ldap_search_ext_s(ldp, base, scope, NULL, attrs, 0, NULL /* serverctrls */, NULL /* clientctrls */, NULL /* timeout */, 0, &ldpres) != LDAP_SUCCESS) { item = probe_item_creat("ldap57_item", NULL, NULL); probe_item_setstatus(item, SYSCHAR_STATUS_ERROR); probe_item_collect(ctx, item); dE("ldap_search_ext_s failed"); goto fail0; } entry = ldap_first_entry(ldp, ldpres); entry_dn = ldap_get_dn(ldp, entry); while (entry != NULL) { BerElement *berelm = NULL; attr = ldap_first_attribute(ldp, entry, &berelm); /* XXX: pattern match filter */ while (attr != NULL) { SEXP_t *se_value = NULL; ber_tag_t bertag = LBER_DEFAULT; ber_len_t berlen = 0; Sockbuf *berbuf = NULL; SEXP_t se_tmp_mem; berbuf = ber_sockbuf_alloc(); /* * Prepare the value (record) entity. Collect only * primitive (i.e. simple) types. */ se_value = probe_ent_creat1("value", NULL, NULL); probe_ent_setdatatype(se_value, OVAL_DATATYPE_RECORD); /* * XXX: does ber_get_next() return LBER_ERROR after the last value? */ while ((bertag = ber_get_next(berbuf, &berlen, berelm)) != LBER_ERROR) { SEXP_t *field = NULL; oval_datatype_t field_type = OVAL_DATATYPE_UNKNOWN; switch(bertag & LBER_ENCODING_MASK) { case LBER_PRIMITIVE: dI("Found primitive value, bertag = %u", bertag); break; case LBER_CONSTRUCTED: dW("Don't know how to handle LBER_CONSTRUCTED values"); /* FALLTHROUGH */ default: dW("Skipping attribute value, bertag = %u", bertag); continue; } assume_d(bertag & LBER_PRIMITIVE, NULL); switch(bertag & LBER_BIG_TAG_MASK) { case LBER_BOOLEAN: { /* LDAPTYPE_BOOLEAN */ ber_int_t val = -1; if (ber_get_boolean(berelm, &val) == LBER_ERROR) { dW("ber_get_boolean: LBER_ERROR"); /* XXX: set error status on field */ continue; } assume_d(val != -1, NULL); field = probe_ent_creat1("field", NULL, SEXP_number_newb_r(&se_tmp_mem, (bool)val)); field_type = OVAL_DATATYPE_BOOLEAN; SEXP_free_r(&se_tmp_mem); } break; case LBER_INTEGER: { /* LDAPTYPE_INTEGER */ ber_int_t val = -1; if (ber_get_int(berelm, &val) == LBER_ERROR) { dW("ber_get_int: LBER_ERROR"); /* XXX: set error status on field */ continue; } field = probe_ent_creat1("field", NULL, SEXP_number_newi_r(&se_tmp_mem, (int)val)); field_type = OVAL_DATATYPE_INTEGER; SEXP_free_r(&se_tmp_mem); } break; case LBER_BITSTRING: /* LDAPTYPE_BIT_STRING */ dW("LBER_BITSTRING: not implemented"); continue; case LBER_OCTETSTRING: { /* * LDAPTYPE_PRINTABLE_STRING * LDAPTYPE_NUMERIC_STRING * LDAPTYPE_DN_STRING * LDAPTYPE_BINARY (?) */ char *val = NULL; if (ber_get_stringa(berelm, &val) == LBER_ERROR) { dW("ber_get_stringa: LBER_ERROR"); /* XXX: set error status on field */ continue; } assume_d(val != NULL, NULL); field = probe_ent_creat1("field", NULL, SEXP_string_new_r(&se_tmp_mem, val, strlen(val))); field_type = OVAL_DATATYPE_STRING; SEXP_free_r(&se_tmp_mem); ber_memfree(val); } break; case LBER_NULL: /* XXX: no equivalent LDAPTYPE_? or empty */ dI("LBER_NULL: skipped"); continue; case LBER_ENUMERATED: /* XXX: no equivalent LDAPTYPE_? */ dW("Don't know how to handle LBER_ENUMERATED type"); continue; default: dW("Unknown attribute value type, bertag = %u", bertag); continue; } if (field != NULL) { assume_d(field_type != OVAL_DATATYPE_UNKNOWN, NULL); probe_ent_setdatatype(field, field_type); probe_ent_attr_add(field, "name", SEXP_string_new_r(&se_tmp_mem, attr, strlen(attr))); SEXP_list_add(se_value, field); SEXP_free_r(&se_tmp_mem); SEXP_free(field); } } ber_sockbuf_free(berbuf); /* * Create the item */ item = probe_item_create(OVAL_INDEPENDENT_LDAP57, NULL, "suffix", OVAL_DATATYPE_STRING, suffix, "relative_dn", OVAL_DATATYPE_STRING, relative_dn, /* XXX: pattern match */ "attribute", OVAL_DATATYPE_STRING, attr, "object_class", OVAL_DATATYPE_STRING, "", "ldaptype", OVAL_DATATYPE_STRING, "", NULL); SEXP_list_add(item, se_value); SEXP_free(se_value); probe_item_collect(ctx, item); attr = ldap_next_attribute(ldp, entry, berelm); } ber_free(berelm, 0); ldap_memfree(entry_dn); entry = ldap_next_entry(ldp, entry); entry_dn = ldap_get_dn(ldp, entry); } /* * Close the LDAP connection and free resources */ ldap_unbind_ext_s(ldp, NULL, NULL); } ldap_memfree(uri_list); fail0: SEXP_free(se_suffix); SEXP_free(se_relative_dn); SEXP_free(se_attribute); free(suffix); free(relative_dn); free(attrs[1]); /* attribute */ return (0); }
int oval_state_to_sexp(void *sess, struct oval_state *state, SEXP_t **out_sexp) { SEXP_t *ste, *ste_name, *ste_ent; SEXP_t *r0, *r1, *r2, *r3, *r4; char buffer[128]; size_t buflen; const char *subtype_name; struct oval_state_content_iterator *contents; subtype_name = oval_subtype_to_str(oval_state_get_subtype(state)); if (subtype_name == NULL) { dI("FAIL: unknown subtype: %d", oval_state_get_subtype(state)); return (-1); } buflen = snprintf(buffer, sizeof buffer, "%s_state", subtype_name); _A(buflen < sizeof buffer); ste_name = SEXP_list_new(r0 = SEXP_string_new(buffer, buflen), r1 = SEXP_string_new(":id", 3), r2 = SEXP_string_newf("%s", oval_state_get_id(state)), r3 = SEXP_string_new(":operator", 9), r4 = SEXP_number_newu(oval_state_get_operator(state)), NULL); ste = SEXP_list_new(ste_name, NULL); SEXP_vfree(r0, r1, r2, r3, r4, ste_name, NULL); contents = oval_state_get_contents(state); while (oval_state_content_iterator_has_more(contents)) { oval_check_t ochk; oval_existence_t oext; oval_entity_varref_type_t vr_type; struct oval_entity *ent; struct oval_state_content *content = oval_state_content_iterator_next(contents); struct oval_record_field_iterator *rf_itr; ent = oval_state_content_get_entity(content); ste_ent = oval_entity_to_sexp(ent); if (ste_ent == NULL) { goto fail; } rf_itr = oval_state_content_get_record_fields(content); while (oval_record_field_iterator_has_more(rf_itr)) { struct oval_record_field *rf; SEXP_t *rf_sexp; rf = oval_record_field_iterator_next(rf_itr); rf_sexp = oval_record_field_STATE_to_sexp(rf); SEXP_list_add(ste_ent, rf_sexp); SEXP_free(rf_sexp); } oval_record_field_iterator_free(rf_itr); ochk = oval_state_content_get_var_check(content); if (ochk != OVAL_CHECK_UNKNOWN) { probe_ent_attr_add(ste_ent, "var_check", r0 = SEXP_number_newu_32(ochk)); SEXP_free(r0); } ochk = oval_state_content_get_ent_check(content); if (ochk != OVAL_CHECK_UNKNOWN) { probe_ent_attr_add(ste_ent, "entity_check", r0 = SEXP_number_newu_32(ochk)); SEXP_free(r0); } oext = oval_state_content_get_check_existence(content); if (oext != OVAL_EXISTENCE_UNKNOWN) { probe_ent_attr_add(ste_ent, "check_existence", r0 = SEXP_number_newu_32(oext)); SEXP_free(r0); } vr_type = oval_entity_get_varref_type(ent); if (vr_type == OVAL_ENTITY_VARREF_ATTRIBUTE || vr_type == OVAL_ENTITY_VARREF_ELEMENT) { SEXP_t *val_lst; struct oval_variable *var; oval_datatype_t dt; var = oval_entity_get_variable(ent); dt = oval_entity_get_datatype(ent); if (oval_varref_elm_to_sexp(sess, var, dt, &val_lst, NULL) != 0) goto fail; SEXP_list_add(ste_ent, val_lst); SEXP_free(val_lst); } SEXP_list_add(ste, ste_ent); SEXP_free(ste_ent); } oval_state_content_iterator_free(contents); *out_sexp = ste; return (0); fail: oval_state_content_iterator_free(contents); SEXP_vfree(ste, ste_ent, NULL); return (-1); }
int oval_object_to_sexp(void *sess, const char *typestr, struct oval_syschar *syschar, SEXP_t **out_sexp) { unsigned int ent_cnt, varref_cnt; int ret; SEXP_t *obj_sexp, *elm, *varrefs, *ent_lst, *lst, *stmp; SEXP_t *r0, *r1, *r2, *obj_attr, sm0, sm1; struct oval_object *object; struct oval_object_content_iterator *cit; struct oval_behavior_iterator *bit; struct oval_object_content *content; struct oval_entity *entity; char obj_name[128]; const char *obj_id; object = oval_syschar_get_object(syschar); /* * Object name & attributes (id) */ ret = snprintf(obj_name, sizeof obj_name, "%s_object", typestr); if (ret<0 || (unsigned int) ret > sizeof obj_name) { dE("obj_name length too short"); return -1; } // even though it returns const char* it has to be freed :-( char *obj_over = (char*)oval_schema_version_to_cstr(oval_object_get_platform_schema_version(object)); obj_id = oval_object_get_id(object); obj_attr = probe_attr_creat("id", SEXP_string_new_r(&sm0, obj_id, strlen(obj_id)), "oval_version", SEXP_string_new_r(&sm1, obj_over, strlen(obj_over)), NULL); free(obj_over); obj_sexp = probe_obj_new(obj_name, obj_attr); SEXP_free_r(&sm0); SEXP_free_r(&sm1); SEXP_free(obj_attr); /* * Object content */ ent_lst = SEXP_list_new(NULL); varrefs = NULL; ent_cnt = varref_cnt = 0; cit = oval_object_get_object_contents(object); while (oval_object_content_iterator_has_more(cit)) { oval_check_t ochk; oval_entity_varref_type_t vr_type; content = oval_object_content_iterator_next(cit); elm = NULL; lst = ent_lst; switch (oval_object_content_get_type(content)) { case OVAL_OBJECTCONTENT_ENTITY: entity = oval_object_content_get_entity(content); elm = oval_entity_to_sexp(entity); if (elm == NULL) break; ochk = oval_object_content_get_varCheck(content); if (ochk != OVAL_CHECK_UNKNOWN) { probe_ent_attr_add(elm, "var_check", r0 = SEXP_number_newu_32(ochk)); SEXP_free(r0); } ret = 0; vr_type = oval_entity_get_varref_type(entity); if (vr_type == OVAL_ENTITY_VARREF_ATTRIBUTE) { const char *var_id = oval_variable_get_id(oval_entity_get_variable(entity)); const char *field_name = oval_object_content_get_field_name(content); dI("Object '%s' references variable '%s' in '%s' field.", obj_id, var_id, field_name); ret = oval_varref_attr_to_sexp(sess, entity, syschar, &stmp); if (ret == 0) { if (varrefs == NULL) varrefs = SEXP_list_new(NULL); SEXP_list_add(varrefs, stmp); SEXP_free(stmp); // todo: don't add duplicates ++varref_cnt; lst = obj_sexp; ++ent_cnt; } } else if (vr_type == OVAL_ENTITY_VARREF_ELEMENT) { SEXP_t *val_lst; struct oval_variable *var; oval_datatype_t dt; var = oval_entity_get_variable(entity); dt = oval_entity_get_datatype(entity); ret = oval_varref_elm_to_sexp(sess, var, dt, &val_lst, syschar); if (ret == 0) { SEXP_list_add(elm, val_lst); SEXP_free(val_lst); } } if (ret != 0) { SEXP_t s_flag; SEXP_number_newi_32_r(&s_flag, SYSCHAR_FLAG_DOES_NOT_EXIST); probe_item_attr_add(obj_sexp, "skip_eval", &s_flag); SEXP_free_r(&s_flag); SEXP_free(elm); SEXP_free(ent_lst); if (varrefs != NULL) SEXP_free(varrefs); oval_object_content_iterator_free(cit); *out_sexp = obj_sexp; return (0); } break; case OVAL_OBJECTCONTENT_SET: elm = oval_set_to_sexp(oval_object_content_get_setobject(content)); break; case OVAL_OBJECTCONTENT_FILTER: { struct oval_filter *filter = oval_object_content_get_filter(content); struct oval_state *ste = oval_filter_get_state(filter); const char *ste_id = oval_state_get_id(ste); oval_filter_action_t action = oval_filter_get_filter_action(filter); const char *action_text = oval_filter_action_get_text(action); dI("Object '%s' has a filter that %ss items conforming to state '%s'.", obj_id, action_text, ste_id); elm = oval_filter_to_sexp(filter); } break; case OVAL_OBJECTCONTENT_UNKNOWN: break; } if (elm == NULL) { SEXP_free(obj_sexp); SEXP_free(ent_lst); if (varrefs != NULL) SEXP_free(varrefs); oval_object_content_iterator_free(cit); return -1; } SEXP_list_add(lst, elm); SEXP_free(elm); } if (varrefs != NULL) { // todo: SEXP_list_push() stmp = SEXP_list_new(r0 = SEXP_string_new("varrefs", 7), r1 = SEXP_number_newu(varref_cnt), r2 = SEXP_number_newu(ent_cnt), NULL); SEXP_vfree(r0, r1, r2, NULL); r0 = SEXP_list_join(stmp, varrefs); SEXP_list_add(obj_sexp, r0); SEXP_vfree(stmp, varrefs, r0, NULL); } stmp = SEXP_list_join(obj_sexp, ent_lst); SEXP_free(obj_sexp); SEXP_free(ent_lst); obj_sexp = stmp; oval_object_content_iterator_free(cit); /* * Object behaviors */ bit = oval_object_get_behaviors(object); if (oval_behavior_iterator_has_more(bit)) { elm = oval_behaviors_to_sexp(bit); SEXP_list_add(obj_sexp, elm); SEXP_free(elm); } oval_behavior_iterator_free(bit); *out_sexp = obj_sexp; return (0); }
static SEXP_t *oval_set_to_sexp(struct oval_setobject *set) { SEXP_t *elm, *elm_name; SEXP_t *r0, *r1, *r2; elm_name = SEXP_list_new(r0 = SEXP_string_new("set", 3), /* operation */ r1 = SEXP_string_new(":operation", 10), r2 = SEXP_number_newu_32(oval_setobject_get_operation(set)), NULL); SEXP_free(r0); SEXP_free(r1); SEXP_free(r2); elm = SEXP_list_new(elm_name, NULL); SEXP_free(elm_name); switch (oval_setobject_get_type(set)) { case OVAL_SET_AGGREGATE:{ struct oval_setobject_iterator *sit; struct oval_setobject *subset; sit = oval_setobject_get_subsets(set); while (oval_setobject_iterator_has_more(sit)) { subset = oval_setobject_iterator_next(sit); SEXP_list_add(elm, r0 = oval_set_to_sexp(subset)); SEXP_free(r0); } oval_setobject_iterator_free(sit); } break; case OVAL_SET_COLLECTIVE:{ struct oval_object_iterator *oit; struct oval_filter_iterator *fit; struct oval_object *obj; SEXP_t *subelm; oit = oval_setobject_get_objects(set); while (oval_object_iterator_has_more(oit)) { obj = oval_object_iterator_next(oit); subelm = SEXP_list_new(r0 = SEXP_string_new("obj_ref", 7), r1 = SEXP_string_newf("%s", oval_object_get_id(obj)), NULL); SEXP_free(r0); SEXP_free(r1); SEXP_list_add(elm, subelm); SEXP_free(subelm); } oval_object_iterator_free(oit); fit = oval_setobject_get_filters(set); while (oval_filter_iterator_has_more(fit)) { struct oval_filter *fil; fil = oval_filter_iterator_next(fit); subelm = oval_filter_to_sexp(fil); SEXP_list_add(elm, subelm); SEXP_free(subelm); } oval_filter_iterator_free(fit); } break; default: abort(); } return (elm); }
static int oval_varref_attr_to_sexp(void *sess, struct oval_entity *entity, struct oval_syschar *syschar, SEXP_t **out_sexp) { unsigned int val_cnt = 0; SEXP_t *val_lst, *val_sexp, *varref, *id_sexp, *val_cnt_sexp; oval_datatype_t dt; struct oval_variable *var; struct oval_value_iterator *vit; struct oval_value *val; oval_syschar_collection_flag_t flag; char msg[100]; int ret = 0; var = oval_entity_get_variable(entity); if (oval_probe_query_variable(sess, var) != 0) { dE("Can't convert variable reference to SEXP."); return -1; } flag = oval_variable_get_collection_flag(var); switch (flag) { case SYSCHAR_FLAG_COMPLETE: case SYSCHAR_FLAG_INCOMPLETE: vit = oval_variable_get_values(var); if (oval_value_iterator_has_more(vit)) break; oval_value_iterator_free(vit); /* fall through */ case SYSCHAR_FLAG_DOES_NOT_EXIST: snprintf(msg, sizeof(msg), "Referenced variable has no values (%s).", oval_variable_get_id(var)); dI("%s", msg); ret = 1; break; default: snprintf(msg, sizeof(msg), "There was a problem processing referenced variable (%s).", oval_variable_get_id(var)); dW("%s", msg); ret = 1; } if (ret) { oval_syschar_add_new_message(syschar, msg, OVAL_MESSAGE_LEVEL_WARNING); oval_syschar_set_flag(syschar, SYSCHAR_FLAG_DOES_NOT_EXIST); return ret; } val_lst = SEXP_list_new(NULL); while (oval_value_iterator_has_more(vit)) { val = oval_value_iterator_next(vit); dt = oval_entity_get_datatype(entity); val_sexp = oval_value_to_sexp(val, dt); if (val_sexp == NULL) { oval_syschar_add_new_message(syschar, "Failed to convert variable value.", OVAL_MESSAGE_LEVEL_ERROR); oval_syschar_set_flag(syschar, SYSCHAR_FLAG_ERROR); SEXP_free(val_lst); oval_value_iterator_free(vit); return -1; } SEXP_list_add(val_lst, val_sexp); SEXP_free(val_sexp); ++val_cnt; } oval_value_iterator_free(vit); id_sexp = SEXP_string_newf("%s", oval_variable_get_id(var)); val_cnt_sexp = SEXP_number_newu(val_cnt); varref = SEXP_list_new(id_sexp, val_cnt_sexp, val_lst, NULL); SEXP_free(id_sexp); SEXP_free(val_cnt_sexp); SEXP_free(val_lst); *out_sexp = varref; return 0; }
static int oval_probe_variable_eval(oval_probe_session_t *sess, struct oval_syschar *syschar) { struct oval_value_iterator *vit; struct oval_variable *var; struct oval_object *obj; oval_syschar_collection_flag_t flag = SYSCHAR_FLAG_ERROR; int ret = 0; obj = oval_syschar_get_object(syschar); var = oval_probe_variable_objgetvar(obj); if (var == NULL) { oval_syschar_set_flag(syschar, SYSCHAR_FLAG_ERROR); return(-1); } if (oval_probe_query_variable(sess, var) != 0) { oval_syschar_set_flag(syschar, SYSCHAR_FLAG_ERROR); return(-1); } flag = oval_variable_get_collection_flag(var); switch (flag) { case SYSCHAR_FLAG_COMPLETE: case SYSCHAR_FLAG_INCOMPLETE: break; default: { char msg[100]; snprintf(msg, sizeof(msg), "There was a problem processing referenced variable (%s).", oval_variable_get_id(var)); dW("%s\n", msg); oval_syschar_add_new_message(syschar, msg, OVAL_MESSAGE_LEVEL_WARNING); oval_syschar_set_flag(syschar, SYSCHAR_FLAG_ERROR); return(1); } } vit = oval_variable_get_values(var); if (vit == NULL) { flag = SYSCHAR_FLAG_ERROR; oval_syschar_set_flag(syschar, SYSCHAR_FLAG_ERROR); return(1); } else { SEXP_t *r0, *item, *cobj, *vrent, *val_sexp, *valent; char *var_ref; cobj = probe_cobj_new(SYSCHAR_FLAG_UNKNOWN, NULL, NULL); /* Create shared entity */ var_ref = oval_variable_get_id(var); vrent = probe_ent_creat1("var_ref", NULL, r0 = SEXP_string_new(var_ref, strlen(var_ref))); SEXP_free(r0); while (oval_value_iterator_has_more(vit)) { oval_datatype_t dtype; struct oval_value *val; val = oval_value_iterator_next(vit); oval_value_cast(val, OVAL_DATATYPE_STRING); dtype = oval_value_get_datatype(val); val_sexp = oval_value_to_sexp(val, dtype); assume_d(val_sexp != NULL, -1); valent = probe_ent_creat1("value", NULL, val_sexp); item = probe_item_creat("variable_item", NULL, NULL); /* temporary workaround to generate ids */ _gen_item_id(item); /* Add shared var_ref entity */ SEXP_list_add(item, vrent); /* Add value entity */ SEXP_list_add(item, valent); /* Add item to the item list */ probe_cobj_add_item(cobj, item); SEXP_vfree(item, valent, val_sexp, NULL); } oval_value_iterator_free(vit); probe_cobj_compute_flag(cobj); ret = oval_sexp2sysch(cobj, syschar); SEXP_vfree(cobj, vrent, NULL); } return(ret); }