diff options
author | Suren A. Chilingaryan <csa@suren.me> | 2015-10-09 03:11:34 +0200 |
---|---|---|
committer | Suren A. Chilingaryan <csa@suren.me> | 2015-10-09 03:11:34 +0200 |
commit | 3b8e32c9bbe0d909c34303da0ad36ef0ef5be852 (patch) | |
tree | ed22378979b2889a84615cf9f24de76359a95244 /pcilib/register.c | |
parent | 21812f8d763fac8ee9bb3fdc593642b06f405a2b (diff) | |
download | pcitool-3b8e32c9bbe0d909c34303da0ad36ef0ef5be852.tar.gz pcitool-3b8e32c9bbe0d909c34303da0ad36ef0ef5be852.tar.bz2 pcitool-3b8e32c9bbe0d909c34303da0ad36ef0ef5be852.tar.xz pcitool-3b8e32c9bbe0d909c34303da0ad36ef0ef5be852.zip |
Introduce hashes
Diffstat (limited to 'pcilib/register.c')
-rw-r--r-- | pcilib/register.c | 37 |
1 files changed, 35 insertions, 2 deletions
diff --git a/pcilib/register.c b/pcilib/register.c index 68e5d36..3a60800 100644 --- a/pcilib/register.c +++ b/pcilib/register.c @@ -23,6 +23,7 @@ int pcilib_add_registers(pcilib_t *ctx, pcilib_model_modification_flags_t flags, // DS: Overrride existing registers // Registers identified by addr + offset + size + type or name + pcilib_register_t i; pcilib_register_description_t *regs; pcilib_register_context_t *reg_ctx; size_t size; @@ -45,11 +46,26 @@ int pcilib_add_registers(pcilib_t *ctx, pcilib_model_modification_flags_t flags, memset(reg_ctx + ctx->alloc_reg, 0, (size - ctx->alloc_reg) * sizeof(pcilib_register_context_t)); - ctx->register_ctx = reg_ctx; + if (ctx->register_ctx != reg_ctx) { + // We need to recreate cache if context is moved... + HASH_CLEAR(hh, ctx->reg_hash); + for (i = 0; i < ctx->num_reg; i++) { + pcilib_register_context_t *cur = &ctx->register_ctx[ctx->num_reg + i]; + HASH_ADD_KEYPTR(hh, ctx->reg_hash, cur->name, strlen(cur->name), cur); + } + } + ctx->register_ctx = reg_ctx; ctx->alloc_reg = size; } + for (i = 0; i < n; i++) { + pcilib_register_context_t *cur = &ctx->register_ctx[ctx->num_reg + i]; + cur->reg = ctx->num_reg + i; + cur->name = registers[i].name; + HASH_ADD_KEYPTR(hh, ctx->reg_hash, cur->name, strlen(cur->name), cur); + } + memcpy(ctx->registers + ctx->num_reg, registers, n * sizeof(pcilib_register_description_t)); memset(ctx->registers + ctx->num_reg + n, 0, sizeof(pcilib_register_description_t)); @@ -61,11 +77,28 @@ int pcilib_add_registers(pcilib_t *ctx, pcilib_model_modification_flags_t flags, } ctx->num_reg += n; - + return 0; } +void pcilib_clean_registers(pcilib_t *ctx) { + pcilib_register_t reg; + + HASH_CLEAR(hh, ctx->reg_hash); + for (reg = 0; reg < ctx->num_reg; reg++) { + if (ctx->register_ctx[reg].views) + free(ctx->register_ctx[reg].views); + } + + if (ctx->registers) + memset(ctx->registers, 0, sizeof(pcilib_register_description_t)); + + if (ctx->register_ctx) + memset(ctx->register_ctx, 0, ctx->alloc_reg * sizeof(pcilib_register_context_t)); + + ctx->num_reg = 0; +} static int pcilib_read_register_space_internal(pcilib_t *ctx, pcilib_register_bank_t bank, pcilib_register_addr_t addr, size_t n, pcilib_register_size_t offset, pcilib_register_size_t bits, pcilib_register_value_t *buf) { int err; |