/* * MI function to reload db table or env * expects 1 node: the tablename or dbenv name to reload */ struct mi_root* mi_bdb_reload(struct mi_root *cmd, void *param) { struct mi_node *node; str *db_path; node = cmd->node.kids; if (node && node->next) return init_mi_tree( 400, MI_MISSING_PARM_S, MI_MISSING_PARM_LEN); db_path = &node->value; if (!db_path || db_path->len == 0) return init_mi_tree( 400, "bdb_reload missing db arg", 21); if (bdb_reload(db_path->s) == 0) { return init_mi_tree( 200, MI_OK_S, MI_OK_LEN); } else { return init_mi_tree( 500, "db_berkeley Reload Failed", 26); } }
/* * Attempts to reload a Berkeley database; reloads when the inode changes */ void bdb_check_reload(db_con_t* _con) { str s; char* p; int rc, len; struct stat st; database_p db; char n[MAX_ROW_SIZE]; char t[MAX_TABLENAME_SIZE]; table_p tp = NULL; tbl_cache_p tbc = NULL; p=n; rc = len = 0; /*get dbenv name*/ db = BDB_CON_CONNECTION(_con); if(!db->dbenv) return; s.s = db->name.s; s.len = db->name.len; len+=s.len; if(len > MAX_ROW_SIZE) { LM_ERR("dbenv name too long \n"); return; } strncpy(p, s.s, s.len); p+=s.len; len++; if(len > MAX_ROW_SIZE) { LM_ERR("dbenv name too long \n"); return; } /*append slash */ *p = '/'; p++; /*get table name*/ s.s = (char*)CON_TABLE(_con); s.len = strlen(CON_TABLE(_con)); len+=s.len; if((len>MAX_ROW_SIZE) || (s.len > MAX_TABLENAME_SIZE) ) { LM_ERR("table name too long \n"); return; } strncpy(t, s.s, s.len); t[s.len] = 0; strncpy(p, s.s, s.len); p+=s.len; *p=0; if( (tbc = bdblib_get_table(db, &s)) == NULL) return; if( (tp = tbc->dtp) == NULL) return; LM_DBG("stat file [%.*s]\n", len, n); rc = stat(n, &st); if(!rc) { if((tp->ino!=0) && (st.st_ino != tp->ino)) bdb_reload(t); /*file changed on disk*/ tp->ino = st.st_ino; } }