[3348] in Moira
dbck updates
daemon@ATHENA.MIT.EDU (Garry Zacheiss)
Wed Aug 24 22:20:28 2005
Message-Id: <200508250220.j7P2KI4D032446@frank-n-furter.mit.edu>
To: moiradev@MIT.EDU
Date: Wed, 24 Aug 2005 22:20:18 -0400
From: Garry Zacheiss <zacheiss@MIT.EDU>
Since doing the purge involves running dbck, this patch implements
support for checking the containers and mcntmap tables in dbck,
necessary since we don't want dbck to decide any of modbys in the
containers table are unreferenced strings, unlikely as that may be.
This is tested and doesn't find any problems currently.
It also fixes the checking for MACHINE members of lists, since that's
broken (oops).
Garry
Index: dbck.h
===================================================================
RCS file: /afs/athena.mit.edu/astaff/project/moiradev/repository/moira/dbck/dbck.h,v
retrieving revision 1.13
diff -u -r1.13 dbck.h
--- dbck.h 15 Aug 2000 00:07:20 -0000 1.13
+++ dbck.h 25 Aug 2005 02:09:19 -0000
@@ -19,6 +19,7 @@
extern int debug, mode, fast, dcmenable, warn;
extern struct hash *users, *machines, *clusters, *lists, *printservers;
extern struct hash *filesys, *nfsphys, *strings, *subnets, *string_dups;
+extern struct hash *containers;
#define MAX_ID_VALUE 32765
#define MIN_ID_VALUE 100
@@ -112,6 +113,17 @@
int modby;
};
+struct container {
+ char name[CONTAINERS_NAME_SIZE];
+ int cnt_id;
+ int list_id;
+ char acl_type;
+ int acl_id;
+ char memacl_type;
+ int memacl_id;
+ int modby;
+};
+
void dbmserr(void);
void out_of_mem(char *msg);
void cleanup(void);
Index: dbck.pc
===================================================================
RCS file: /afs/athena.mit.edu/astaff/project/moiradev/repository/moira/dbck/dbck.pc,v
retrieving revision 1.6
diff -u -r1.6 dbck.pc
--- dbck.pc 13 Jan 2000 01:39:45 -0000 1.6
+++ dbck.pc 24 Aug 2005 20:15:27 -0000
@@ -27,6 +27,7 @@
int abort_p = 0;
struct hash *users, *machines, *clusters, *lists, *filesys, *nfsphys;
struct hash *strings, *members, *subnets, *string_dups, *printservers;
+struct hash *containers;
EXEC SQL BEGIN DECLARE SECTION;
int dcmenable;
EXEC SQL END DECLARE SECTION;
Index: phase1.pc
===================================================================
RCS file: /afs/athena.mit.edu/astaff/project/moiradev/repository/moira/dbck/phase1.pc,v
retrieving revision 1.12
diff -u -r1.12 phase1.pc
--- phase1.pc 15 Aug 2000 00:07:20 -0000 1.12
+++ phase1.pc 24 Aug 2005 21:25:17 -0000
@@ -39,6 +39,7 @@
int show_str_id(void *string);
int print_str_id(void *id);
void print_dup_map(int key, void *data, void *hint);
+int show_cnt_name(void *cnt);
int show_user_id(void *user)
{
@@ -234,6 +235,13 @@
printf("String %d is a duplicate of string %d\n", key, (int)data);
}
+int show_cnt_name(void *container)
+{
+ struct container *cnt = container;
+ printf("Container %s (%d) has duplicate name\n", cnt->name, cnt->cnt_id);
+ return 0;
+}
+
void phase1(void)
{
EXEC SQL BEGIN DECLARE SECTION;
@@ -250,6 +258,7 @@
struct filesys *f;
struct nfsphys *n;
struct printserver *ps;
+ struct container *cnt;
printf("Phase 1 - Looking for duplicates\n");
@@ -343,7 +352,7 @@
dprintf("Loading users...\n");
sq = sq_create();
- users = create_hash(30000);
+ users = create_hash(65000);
if (!sq || !users)
out_of_mem("loading users");
@@ -965,4 +974,71 @@
}
EXEC SQL CLOSE csr120;
}
+
+ dprintf("Loading containers...\n");
+ containers = create_hash(1000);
+ if (!containers)
+ out_of_mem("loading containers");
+
+ EXEC SQL DECLARE csr_cnts CURSOR FOR
+ SELECT name, cnt_id, list_id, acl_type, acl_id, memacl_type, memacl_id,
+ modby FROM containers;
+ EXEC SQL OPEN csr_cnts;
+ while (1)
+ {
+ EXEC SQL BEGIN DECLARE SECTION;
+ int cnt_id, list_id, acl_id, memacl_id, modby;
+ char name[CONTAINERS_NAME_SIZE];
+ char acl_type[CONTAINERS_ACL_TYPE_SIZE];
+ char memacl_type[CONTAINERS_MEMACL_TYPE_SIZE];
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL FETCH csr_cnts INTO :name, :cnt_id, :list_id, :acl_type,
+ :acl_id, :memacl_type, :memacl_id, :modby;
+ if (sqlca.sqlcode)
+ break;
+
+ cnt = malloc(sizeof(struct container));
+ if (!cnt)
+ out_of_mem("storing container");
+ strcpy(cnt->name, strtrim(name));
+ cnt->cnt_id = cnt_id;
+ cnt->list_id = list_id;
+ cnt->acl_type = acl_type[0];
+ cnt->acl_id = acl_id;
+ cnt->memacl_type = memacl_type[0];
+ cnt->memacl_id = memacl_id;
+ cnt->modby = modby;
+ retval = hash_store(containers, cnt_id, cnt);
+ if (retval == -1)
+ out_of_mem("storing container in hash table");
+ else if (retval == 1)
+ {
+ printf("Duplicate container cnt_id %d\n", cnt_id);
+ cant_fix(0);
+ }
+ }
+ EXEC SQL CLOSE csr_cnts;
+
+ if (!fast)
+ {
+ sq = sq_create();
+ if (!sq)
+ out_of_mem("looking for duplicate container names");
+
+ EXEC SQL DECLARE csr121 CURSOR FOR
+ SELECT cnt1.cnt_id FROM containers cnt1, containers cnt2
+ WHERE cnt1.name = cnt2.name AND cnt1.cnt_id != cnt2.cnt_id;
+ EXEC SQL OPEN csr121;
+ while (1)
+ {
+ EXEC SQL FETCH csr121 INTO :id;
+ if (sqlca.sqlcode)
+ break;
+
+ sq_save_data(sq, hash_lookup(containers, id));
+ }
+ EXEC SQL CLOSE csr121;
+ generic_fix(sq, show_cnt_name, "Change name", cant_fix, 0);
+ }
}
Index: phase2.pc
===================================================================
RCS file: /afs/athena.mit.edu/astaff/project/moiradev/repository/moira/dbck/phase2.pc,v
retrieving revision 1.20
diff -u -r1.20 phase2.pc
--- phase2.pc 14 Dec 2001 21:04:54 -0000 1.20
+++ phase2.pc 25 Aug 2005 02:11:34 -0000
@@ -21,6 +21,8 @@
int show_mcm_mach(void *id);
int show_mcm_clu(void *id);
+int show_mcntmap_mach(void *id);
+int show_mcntmap_cnt(void *id);
int show_hostalias(void *id);
int show_printer_mach(void *id);
int show_printer_server(void *id);
@@ -67,6 +69,9 @@
void check_fs(int id, void *filesys, void *hint);
void check_nfsphys(int id, void *nfsphys, void *hint);
void check_ps(int id, void *printserver, void *hint);
+void check_container(int id, void *container, void *hint);
+void fix_container_acl(int id);
+void fix_container_memacl(int id);
int show_fsg_missing(void *id);
int show_fsg_type(void *filesys);
void fix_fsg_type(void *filesys);
@@ -140,6 +145,59 @@
return found;
}
+int show_mcntmap_mach(void *id)
+{
+ EXEC SQL BEGIN DECLARE SECTION;
+ int iid = (int)id, found = 1;
+ char name[CONTAINERS_NAME_SIZE];
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL DECLARE csr_show_mcnt_mach CURSOR FOR
+ SELECT cnt.name FROM container cnt, mcntmap mc
+ WHERE cnt.cnt_id = mc.cnt_id AND mc.mach_id = :iid;
+ EXEC SQL OPEN csr_show_mcnt_mach;
+ while (1)
+ {
+ EXEC SQL FETCH csr_show_mcnt_mach INTO :name;
+ if (sqlca.sqlcode)
+ break;
+
+ strtrim(name);
+ found = 0;
+ printf("Container %s, non-existant machine %d in container map\n",
+ name, iid);
+ }
+ EXEC SQL CLOSE csr_show_mcnt_mach;
+ return found;
+}
+
+int show_mcntmap_cnt(void *id)
+{
+ EXEC SQL BEGIN DECLARE SECTION;
+ int iid = (int)id, found = 1;
+ char name[MACHINE_NAME_SIZE];
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL DECLARE csr_show_mcnt_cnt CURSOR FOR
+ SELECT m.name FROM machine m, mcntmap mc
+ WHERE m.mach_id = mc.mach_id AND mc.cnt_id = :iid;
+ EXEC SQL OPEN csr_show_mcnt_cnt;
+ while (1)
+ {
+ EXEC SQL FETCH csr_show_mcnt_cnt INTO :name;
+ if (sqlca.sqlcode)
+ break;
+
+ strtrim(name);
+
+ found = 0;
+ printf("Machine %s, non-existant container %d in container map\n",
+ name, iid);
+ }
+ EXEC SQL CLOSE csr_show_mcnt_cnt;
+ return found;
+}
+
int show_hostalias(void *id)
{
EXEC SQL BEGIN DECLARE SECTION;
@@ -1512,6 +1570,135 @@
}
}
+static void clear_container_list(struct container *cnt)
+{
+ EXEC SQL BEGIN DECLARE SECTION;
+ int rowcount, id = cnt->cnt_id;
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL UPDATE containers SET list_id = 0
+ WHERE cnt_id = :id;
+ rowcount = sqlca.sqlerrd[2];
+ if (rowcount > 0)
+ printf("%d entr%s fixed\n", rowcount, rowcount == 1 ? "y" : "ies");
+ else
+ printf("Not fixed\n");
+ modified("containers");
+}
+
+void fix_container_acl(int id)
+{
+ EXEC SQL BEGIN DECLARE SECTION;
+ int rowcount, iid = (int)id;
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL UPDATE containers SET acl_id = 0, acl_type = 'NONE'
+ WHERE cnt_id = :iid;
+ rowcount = sqlca.sqlerrd[2];
+ if (rowcount > 0)
+ printf("%d entr%s fixed\n", rowcount, rowcount == 1 ? "y" : "ies");
+ else
+ printf("Not fixed\n");
+ modified("containers");
+}
+
+void fix_container_memacl(int id)
+{
+ EXEC SQL BEGIN DECLARE SECTION;
+ int rowcount, iid = (int)id;
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL UPDATE containers SET memacl_id = 0, memacl_type = 'NONE'
+ WHERE cnt_id = :iid;
+ rowcount = sqlca.sqlerrd[2];
+ if (rowcount > 0)
+ printf("%d entr%s fixed\n", rowcount, rowcount == 1 ? "y" : "ies");
+ else
+ printf("Not fixed\n");
+ modified("containers");
+}
+
+void check_container(int id, void *container, void *hint)
+{
+ struct container *cnt = container;
+
+ if (!hash_lookup(lists, cnt->list_id))
+ {
+ printf("Container %s has non-existent associated list_id %d\n",
+ cnt->name, cnt->list_id);
+ if (single_fix("Set to no associated list", 1))
+ clear_container_list(cnt);
+ }
+
+ switch (cnt->acl_type)
+ {
+ case 'L':
+ if (!hash_lookup(lists, cnt->acl_id))
+ {
+ printf("Container %s has bad LIST acl %d\n", cnt->name, cnt->acl_id);
+ if (single_fix("Patch", 1))
+ fix_container_acl(cnt->cnt_id);
+ }
+ break;
+ case 'U':
+ if (!hash_lookup(users, cnt->acl_id))
+ {
+ printf("Container %s has bad USER acl %d\n", cnt->name, cnt->acl_id);
+ if (single_fix("Patch", 1))
+ fix_container_acl(cnt->cnt_id);
+ }
+ break;
+ case 'K':
+ cnt->acl_id = maybe_fixup_unref_string(cnt->acl_id, id, cnt->name,
+ "container", "acl_id", "cnt_id");
+ if (!cnt->acl_id)
+ {
+ printf("Container %s has bad KERBEROS acl %d\n", cnt->name,
+ cnt->acl_id);
+ if (single_fix("Patch", 1))
+ fix_container_acl(cnt->cnt_id);
+ }
+ break;
+ }
+
+ switch (cnt->memacl_type)
+ {
+ case 'L':
+ if (!hash_lookup(lists, cnt->memacl_id))
+ {
+ printf("Container %s has bad LIST memacl %d\n", cnt->name,
+ cnt->memacl_id);
+ if (single_fix("Patch", 1))
+ fix_container_memacl(cnt->cnt_id);
+ }
+ break;
+ case 'U':
+ if (!hash_lookup(users, cnt->memacl_id))
+ {
+ printf("Container %s has bad USER memacl %d\n", cnt->name,
+ cnt->memacl_id);
+ if (single_fix("Patch", 1))
+ fix_container_memacl(cnt->cnt_id);
+ }
+ break;
+ case 'K':
+ cnt->memacl_id = maybe_fixup_unref_string(cnt->memacl_id, id, cnt->name,
+ "container", "memacl_id",
+ "cnt_id");
+ if (!cnt->memacl_id)
+ {
+ printf("Container %s has bad KERBEROS memacl %d\n", cnt->name,
+ cnt->memacl_id);
+ if (single_fix("Patch", 1))
+ fix_container_memacl(cnt->cnt_id);
+ }
+ break;
+ }
+
+ cnt->modby = maybe_fixup_modby(cnt->modby, id, cnt->name, "containers",
+ "modby", "cnt_id");
+}
+
int show_fsg_missing(void *id)
{
EXEC SQL BEGIN DECLARE SECTION;
@@ -2017,7 +2204,7 @@
sq_save_unique_data(sq4, (void *)id);
else if (type[0] == 'K' && !maybe_fixup_unref_string2("imembers", "member_id", rowid, id))
sq_save_unique_data(sq5, (void *)id);
- else if (type[0] == 'M' && !maybe_fixup_unref_string2("imembers", "member_id", rowid, id))
+ else if (type[0] == 'M' && !hash_lookup(machines, id))
sq_save_unique_data(sq6, (void *)id);
else
l->members++;
@@ -2393,5 +2580,34 @@
dprintf("Checking printservers\n");
hash_step(printservers, check_ps, NULL);
+
+ dprintf("Checking containers\n");
+ hash_step(containers, check_container, NULL);
+
+ dprintf("Checking mcntmap\n");
+ sq1 = sq_create();
+ sq2 = sq_create();
+ EXEC SQL DECLARE csr_mcntmap CURSOR FOR
+ SELECT mach_id, cnt_id FROM mcntmap;
+ EXEC SQL OPEN csr_mcntmap;
+ while (1)
+ {
+ EXEC SQL BEGIN DECLARE SECTION;
+ int mach_id, cnt_id;
+ EXEC SQL END DECLARE SECTION;
+
+ EXEC SQL FETCH csr_mcntmap INTO :mach_id, :cnt_id;
+ if (sqlca.sqlcode)
+ break;
+
+ if (!(m = hash_lookup(machines, mach_id)))
+ sq_save_unique_data(sq1, (void *)mach_id);
+ else if (!hash_lookup(containers, cnt_id))
+ sq_save_unique_data(sq2, (void *)cnt_id);
+ }
+ EXEC SQL CLOSE csr_mcntmap;
+ generic_delete(sq1, show_mcntmap_mach, "mcntmap", "mach_id", 1);
+ generic_delete(sq2, show_mcntmap_cnt, "mcntmap", "cnt_id", 1);
+
}