113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/* Copyright (C) 2005 Red Hat, Inc. */ 213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/* Object: dbase_llist_t (Linked List) 413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle * Partially Implements: dbase_t (Database) 513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle */ 613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlestruct dbase_llist; 813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindletypedef struct dbase_llist dbase_t; 913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#define DBASE_DEFINED 1013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 1113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include <stdlib.h> 1213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include "debug.h" 1313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include "handle.h" 1413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle#include "database_llist.h" 1513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 1613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_needs_resync(semanage_handle_t * handle, dbase_llist_t * dbase) 1713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 1813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 1913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int cache_serial; 2013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 2113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->cache_serial < 0) 2213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return 1; 2313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 2413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_serial = handle->funcs->get_serial(handle); 2513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (cache_serial < 0) 2613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return 1; 2713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 2813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (cache_serial != dbase->cache_serial) { 2913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_drop_cache(dbase); 3013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_serial = -1; 3113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return 1; 3213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 3313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return 0; 3413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 3513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 3613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/* Helper for adding records to the cache */ 3713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_cache_prepend(semanage_handle_t * handle, 3813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, const record_t * data) 3913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 4013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 4113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle /* Initialize */ 4213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *entry = (cache_entry_t *) malloc(sizeof(cache_entry_t)); 4313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (entry == NULL) 4413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto omem; 4513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 4613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->rtable->clone(handle, data, &entry->data) < 0) 4713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 4813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 4913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle entry->prev = NULL; 5013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle entry->next = dbase->cache; 5113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 5213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle /* Link */ 5313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->cache != NULL) 5413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache->prev = entry; 5513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->cache_tail == NULL) 5613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_tail = entry; 5713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache = entry; 5813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_sz++; 5913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 6013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 6113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle omem: 6213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "out of memory"); 6313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 6413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 6513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not cache record"); 6613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle free(entry); 6713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 6813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 6913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 7013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlevoid dbase_llist_drop_cache(dbase_llist_t * dbase) 7113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 7213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 7313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->cache_serial < 0) 7413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return; 7513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 7613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *prev, *ptr = dbase->cache; 7713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle while (ptr != NULL) { 7813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle prev = ptr; 7913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ptr = ptr->next; 8013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->rtable->free(prev->data); 8113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle free(prev); 8213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 8313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 8413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_serial = -1; 8513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->modified = 0; 8613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 8713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 8813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_set_serial(semanage_handle_t * handle, dbase_llist_t * dbase) 8913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 9013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 9113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int cache_serial = handle->funcs->get_serial(handle); 9213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (cache_serial < 0) { 9313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not update cache serial"); 9413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 9513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 9613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 9713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_serial = cache_serial; 9813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 9913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 10013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 10113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle/* Helper for finding records in the cache */ 10213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindlestatic int dbase_llist_cache_locate(semanage_handle_t * handle, 10313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 10413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle const record_key_t * key, 10513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t ** entry) 10613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 10713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 10813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *ptr; 10913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 11013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle /* Implemented in parent */ 11113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->dtable->cache(handle, dbase) < 0) 11213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 11313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 11413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle for (ptr = dbase->cache; ptr != NULL; ptr = ptr->next) { 11513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (!dbase->rtable->compare(ptr->data, key)) { 11613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle *entry = ptr; 11713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 11813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 11913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 12013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 12113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_NODATA; 12213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 12313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 12413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not complete cache lookup"); 12513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 12613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 12713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 12813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_exists(semanage_handle_t * handle, 12913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 13013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle const record_key_t * key, int *response) 13113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 13213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 13313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *entry; 13413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int status; 13513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 13613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle status = dbase_llist_cache_locate(handle, dbase, key, &entry); 13713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (status < 0) 13813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 13913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 14013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle *response = (status != STATUS_NODATA); 14113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 14213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 14313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 14413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not check if record exists"); 14513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 14613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 14713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 14813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_add(semanage_handle_t * handle, 14913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 150f7dd4ca760de5f2dfa962749dddf8a99587f2257Justin P. Mattock const record_key_t * key __attribute__ ((unused)), 151f7dd4ca760de5f2dfa962749dddf8a99587f2257Justin P. Mattock const record_t * data) 15213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 15313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 15413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase_llist_cache_prepend(handle, dbase, data) < 0) 15513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 15613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 15713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle key = NULL; 15813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->modified = 1; 15913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 16013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 16113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 16213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not add record to the database"); 16313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 16413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 16513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 16613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_set(semanage_handle_t * handle, 16713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 16813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle const record_key_t * key, const record_t * data) 16913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 17013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 17113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *entry; 17213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int status; 17313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 17413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle status = dbase_llist_cache_locate(handle, dbase, key, &entry); 17513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (status < 0) 17613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 17713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (status == STATUS_NODATA) { 17813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "record not found in the database"); 17913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 18013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } else { 18113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->rtable->free(entry->data); 18213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->rtable->clone(handle, data, &entry->data) < 0) 18313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 18413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 18513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 18613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->modified = 1; 18713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 18813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 18913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 19013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not set record value"); 19113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 19213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 19313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 19413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_modify(semanage_handle_t * handle, 19513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 19613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle const record_key_t * key, const record_t * data) 19713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 19813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 19913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *entry; 20013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int status; 20113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 20213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle status = dbase_llist_cache_locate(handle, dbase, key, &entry); 20313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (status < 0) 20413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 20513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (status == STATUS_NODATA) { 20613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase_llist_cache_prepend(handle, dbase, data) < 0) 20713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 20813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } else { 20913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->rtable->free(entry->data); 21013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->rtable->clone(handle, data, &entry->data) < 0) 21113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 21213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 21313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 21413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->modified = 1; 21513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 21613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 21713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 21813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not modify record value"); 21913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 22013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 22113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 222f7dd4ca760de5f2dfa962749dddf8a99587f2257Justin P. Mattockhidden int dbase_llist_count(semanage_handle_t * handle __attribute__ ((unused)), 22313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, unsigned int *response) 22413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 22513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 22613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle *response = dbase->cache_sz; 22713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle handle = NULL; 22813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 22913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 23013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 23113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_query(semanage_handle_t * handle, 23213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 23313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle const record_key_t * key, record_t ** response) 23413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 23513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 23613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *entry; 23713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int status; 23813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 23913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle status = dbase_llist_cache_locate(handle, dbase, key, &entry); 24013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (status < 0 || status == STATUS_NODATA) 24113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 24213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 24313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->rtable->clone(handle, entry->data, response) < 0) 24413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 24513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 24613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 24713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 24813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 24913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not query record value"); 25013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 25113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 25213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 25313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_iterate(semanage_handle_t * handle, 25413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 25513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int (*fn) (const record_t * record, 25613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle void *fn_arg), void *arg) 25713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 25813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 25913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int rc; 26013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *ptr; 26113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 26213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle for (ptr = dbase->cache_tail; ptr != NULL; ptr = ptr->prev) { 26313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 26413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle rc = fn(ptr->data, arg); 26513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (rc < 0) 26613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 26713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 26813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle else if (rc > 1) 26913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle break; 27013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 27113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 27213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 27313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 27413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 27513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not iterate over records"); 27613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 27713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 27813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 279f7dd4ca760de5f2dfa962749dddf8a99587f2257Justin P. Mattockint dbase_llist_del(semanage_handle_t * handle __attribute__ ((unused)), 28013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, const record_key_t * key) 28113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 28213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 28313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *ptr, *prev = NULL; 28413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 28513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle for (ptr = dbase->cache; ptr != NULL; ptr = ptr->next) { 28613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (!dbase->rtable->compare(ptr->data, key)) { 28713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (prev != NULL) 28813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle prev->next = ptr->next; 28913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle else 29013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache = ptr->next; 29113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 29213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (ptr->next != NULL) 29313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ptr->next->prev = ptr->prev; 29413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle else 29513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_tail = ptr->prev; 29613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 29713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->rtable->free(ptr->data); 29813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_sz--; 29913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle free(ptr); 30013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->modified = 1; 30113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 30213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } else 30313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle prev = ptr; 30413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 30513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 30613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle handle = NULL; 30713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 30813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 30913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 31013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_clear(semanage_handle_t * handle, dbase_llist_t * dbase) 31113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 31213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 31313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int old_serial = dbase->cache_serial; 31413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 31513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase_llist_set_serial(handle, dbase) < 0) { 31613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not set serial of cleared dbase"); 31713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 31813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 31913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 32013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (old_serial >= 0) { 32113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *prev, *ptr = dbase->cache; 32213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle while (ptr != NULL) { 32313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle prev = ptr; 32413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ptr = ptr->next; 32513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->rtable->free(prev->data); 32613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle free(prev); 32713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 32813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 32913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 33013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache = NULL; 33113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_tail = NULL; 33213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->cache_sz = 0; 33313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase->modified = 1; 33413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 33513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 33613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 33713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindleint dbase_llist_list(semanage_handle_t * handle, 33813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle dbase_llist_t * dbase, 33913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle record_t *** records, unsigned int *count) 34013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle{ 34113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 34213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle cache_entry_t *ptr; 34313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle record_t **tmp_records = NULL; 34413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle unsigned int tmp_count; 34513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle int i = 0; 34613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 34713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle tmp_count = dbase->cache_sz; 34813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (tmp_count > 0) { 34913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle tmp_records = (record_t **) 35013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle calloc(tmp_count, sizeof(record_t *)); 35113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 35213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (tmp_records == NULL) 35313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto omem; 35413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 35513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle for (ptr = dbase->cache_tail; ptr != NULL; ptr = ptr->prev) { 35613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle if (dbase->rtable->clone(handle, 35713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ptr->data, 35813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle &tmp_records[i]) < 0) 35913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle goto err; 36013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle i++; 36113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 36213cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle } 36313cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 36413cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle *records = tmp_records; 36513cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle *count = tmp_count; 36613cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_SUCCESS; 36713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 36813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle omem: 36913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "out of memory"); 37013cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle 37113cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle err: 3722276a2fa51517ead7f4cf028263dee4b5e2bb46aEric Paris if (tmp_records) { 3732276a2fa51517ead7f4cf028263dee4b5e2bb46aEric Paris for (; i >= 0; i--) 3742276a2fa51517ead7f4cf028263dee4b5e2bb46aEric Paris dbase->rtable->free(tmp_records[i]); 3752276a2fa51517ead7f4cf028263dee4b5e2bb46aEric Paris free(tmp_records); 3762276a2fa51517ead7f4cf028263dee4b5e2bb46aEric Paris } 37713cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle ERR(handle, "could not allocate record array"); 37813cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle return STATUS_ERR; 37913cd4c8960688af11ad23b4c946149015c80d54Joshua Brindle} 380