static uint8_t fw_cfg_read(FWCfgState *s) { int arch = !!(s->cur_entry & FW_CFG_ARCH_LOCAL); FWCfgEntry *e = &s->entries[arch][s->cur_entry & FW_CFG_ENTRY_MASK]; uint8_t ret; if (s->cur_entry == FW_CFG_INVALID || !e->data || s->cur_offset >= e->len) ret = 0; else { if (e->read_callback) { e->read_callback(e->callback_opaque, s->cur_offset); } ret = e->data[s->cur_offset++]; } trace_fw_cfg_read(s, ret); return ret; }
static void fw_cfg_write(FWCfgState *s, uint8_t value) { int arch = !!(s->cur_entry & FW_CFG_ARCH_LOCAL); FWCfgEntry *e = &s->entries[arch][s->cur_entry & FW_CFG_ENTRY_MASK]; FW_CFG_DPRINTF("write %d\n", value); if (s->cur_entry & FW_CFG_WRITE_CHANNEL && s->cur_offset < e->len) { e->data[s->cur_offset++] = value; if (s->cur_offset == e->len) { e->callback(e->callback_opaque, e->data); s->cur_offset = 0; } } }
static int fw_cfg_select(FWCfgState *s, uint16_t key) { int arch, ret; FWCfgEntry *e; s->cur_offset = 0; if ((key & FW_CFG_ENTRY_MASK) >= fw_cfg_max_entry(s)) { s->cur_entry = FW_CFG_INVALID; ret = 0; } else { s->cur_entry = key; ret = 1; /* entry successfully selected, now run callback if present */ arch = !!(key & FW_CFG_ARCH_LOCAL); e = &s->entries[arch][key & FW_CFG_ENTRY_MASK]; if (e->select_cb) { e->select_cb(e->callback_opaque); } } trace_fw_cfg_select(s, key, ret); return ret; }