/*************************************************************************** * Copyright (C) 04/2008 by Olaf Rempel * * razzor@kopf-tisch.de * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; version 2 of the License * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License for more details. * * * * You should have received a copy of the GNU General Public License * * along with this program; if not, write to the * * Free Software Foundation, Inc., * * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * ***************************************************************************/ #include #include #include #include #include "tdc_parser.h" #include "tdc_proto.h" #include "tdc_store.h" #include "tdc_variable.h" #include "gui_graph_tab.h" #include "gui_variable_tab.h" struct tdc_board { char name[32]; struct tdc_var *varmap[256]; int refresh_graph_interval; int refresh_interval; gint refresh_tag; }; static struct tdc_board *board_arr[8]; struct tdc_board * tdcstore_get_board(int address) { return board_arr[address & 0x7]; } struct tdc_var * tdcstore_get_var(int address, int id) { struct tdc_board *board = tdcstore_get_board(address); return (board != NULL) ? board->varmap[id & 0xFF] : NULL; } static int tdcstore_destroy_var(struct tdc_board *board, int id) { struct tdc_var *var = board->varmap[id & 0xFF]; if (var == NULL) return -1; if (var->privdata_vartab) gui_vartab_remove_var(var); if (var->privdata_graphtab) gui_graphtab_remove_var(var); tdcvar_destroy(var); board->varmap[id & 0xFF] = NULL; return 0; } static int tdcstore_destroy_board(int address) { struct tdc_board *board = tdcstore_get_board(address); if (board == NULL) return -1; int i; for (i = 0; i < 256; i++) { if (board->varmap[i] == NULL) continue; tdcstore_destroy_var(board, i); } g_free(board); board_arr[address & 0x7] = NULL; return 0; } void tdcstore_create_board(int address, char *name) { struct tdc_board *old = tdcstore_get_board(address); if (old != NULL) tdcstore_destroy_board(address); struct tdc_board *board = g_malloc0(sizeof(struct tdc_board)); strncpy(board->name, name, 32); printf("ADDR%d:%s\n", address, board->name); board_arr[address & 0x7] = board; } int tdcstore_create_var(int address, struct tdc_var *var) { struct tdc_board *board = tdcstore_get_board(address); if (board == NULL) return -1; struct tdc_var *old = tdcstore_get_var(address, var->id); if (old != NULL) tdcstore_destroy_var(board, var->id); board->varmap[var->id] = var; gui_vartab_add_var(var); return 0; } int tdcstore_update_var(int address, int id, uint8_t *data, int len) { struct tdc_var *var = tdcstore_get_var(address, id); if (var == NULL) return -1; tdcvar_update(var, data, len); if (var->privdata_vartab) gui_vartab_update_var(var); if (var->privdata_graphtab) gui_graphtab_update_var(var); return 0; } static gint refresh_helper(gpointer data) { int i; int address = (int)data; for (i = 0; i < 256; i++) { struct tdc_var *var = tdcstore_get_var(address, i); /* unknown var, or value updated via refresh_graph */ if ((var == NULL) || (var->flags & TDC_GUI_GRAPH)) continue; /* error while sending -> bail out, disable timeout */ if (tdcparser_send_getvalue(address, i) < 0) return FALSE; } return TRUE; } int tdcstore_refresh_values(int address, int interval) { struct tdc_board *board = tdcstore_get_board(address); if (board == NULL) return -1; int old_interval = board->refresh_interval; if (old_interval != 0) g_source_remove(board->refresh_tag); board->refresh_tag = g_timeout_add(interval, refresh_helper, (gpointer)address); return 0; } static void tdcstore_get_bitmap(int address, uint32_t *bitmap) { int i, cnt = 0; uint32_t tmp = 0; for (i = 0; i < 256; i++) { struct tdc_var *var = tdcstore_get_var(address, i); if ((var != NULL) && (var->flags & TDC_GUI_GRAPH)) tmp |= (1 << cnt); cnt = (cnt +1) % 32; if (cnt == 0) { bitmap[i >> 5] = tmp; tmp = 0; } } } int tdcstore_graph_refresh(int address, int interval) { struct tdc_board *board = tdcstore_get_board(address); if (board == NULL) return -1; if (interval == -1) interval = board->refresh_graph_interval; uint32_t bitmap[8]; tdcstore_get_bitmap(address, bitmap); tdcparser_send_request(address, interval, bitmap); board->refresh_graph_interval = interval; return 0; } void tdcstore_flush(void) { int i; for (i = 0; i < 8; i++) tdcstore_destroy_board(i); }