📄 parse.c
字号:
free_tree(previous); goto next; } else if (!strncmp(child2->label, ANON, ANON_LEN)) { merge_anon_children(child2, child1); if (previous) previous->next_peer = child2->next_peer; else tp2->child_list = child2->next_peer; free_tree(child2); previous = child1; /* Move 'child1' to 'tp2' */ child1 = child1->next_peer; previous->next_peer = tp2->child_list; tp2->child_list = previous; for (previous = tp2->child_list; previous; previous = previous->next_peer) previous->parent = tp2; goto next; } else if (!label_compare(child1->label, child2->label)) { if (netsnmp_ds_get_int(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_MIB_WARNINGS)) { snmp_log(LOG_WARNING, "Warning: %s.%ld is both %s and %s (%s)\n", tp2->label, child1->subid, child1->label, child2->label, File); } continue; } else { /* * Two copies of the same node. * 'child2' adopts the children of 'child1' */ if (child2->child_list) { for (previous = child2->child_list; previous->next_peer; previous = previous->next_peer); /* Find the end of the list */ previous->next_peer = child1->child_list; } else child2->child_list = child1->child_list; for (previous = child1->child_list; previous; previous = previous->next_peer) previous->parent = child2; child1->child_list = NULL; previous = child1; /* Finished with 'child1' */ child1 = child1->next_peer; free_tree(previous); goto next; } } } /* * If no match, move 'child1' to 'tp2' child_list */ if (child1) { previous = child1; child1 = child1->next_peer; previous->parent = tp2; previous->next_peer = tp2->child_list; tp2->child_list = previous; } next:; }}/* * Find all the children of root in the list of nodes. Link them into the * tree and out of the nodes list. */static voiddo_subtree(struct tree *root, struct node **nodes){ struct tree *tp, *anon_tp = NULL; struct tree *xroot = root; struct node *np, **headp; struct node *oldnp = NULL, *child_list = NULL, *childp = NULL; int hash; int *int_p; while (xroot->next_peer && xroot->next_peer->subid == root->subid) {#if 0 printf("xroot: %s.%s => %s\n", xroot->parent->label, xroot->label, xroot->next_peer->label);#endif xroot = xroot->next_peer; } tp = root; headp = &nbuckets[NBUCKET(name_hash(tp->label))]; /* * Search each of the nodes for one whose parent is root, and * move each into a separate list. */ for (np = *headp; np; np = np->next) { if (!label_compare(tp->label, np->parent)) { /* * take this node out of the node list */ if (oldnp == NULL) { *headp = np->next; /* fix root of node list */ } else { oldnp->next = np->next; /* link around this node */ } if (child_list) childp->next = np; else child_list = np; childp = np; } else { oldnp = np; } } if (childp) childp->next = NULL; /* * Take each element in the child list and place it into the tree. */ for (np = child_list; np; np = np->next) { struct tree *otp = NULL; struct tree *xxroot = xroot; anon_tp = NULL; tp = xroot->child_list; if (np->subid == -1) { /* * name ::= { parent } */ np->subid = xroot->subid; tp = xroot; xxroot = xroot->parent; } while (tp) { if (tp->subid == np->subid) break; else { otp = tp; tp = tp->next_peer; } } if (tp) { if (!label_compare(tp->label, np->label)) { /* * Update list of modules */ int_p = (int *) malloc((tp->number_modules + 1) * sizeof(int)); if (int_p == NULL) return; memcpy(int_p, tp->module_list, tp->number_modules * sizeof(int)); int_p[tp->number_modules] = np->modid; if (tp->number_modules > 1) free((char *) tp->module_list); ++tp->number_modules; tp->module_list = int_p; if (netsnmp_ds_get_boolean(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_MIB_REPLACE)) { /* * Replace from node */ tree_from_node(tp, np); } /* * Handle children */ do_subtree(tp, nodes); continue; } if (!strncmp(np->label, ANON, ANON_LEN) || !strncmp(tp->label, ANON, ANON_LEN)) { anon_tp = tp; /* Need to merge these two trees later */ } else if (netsnmp_ds_get_int(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_MIB_WARNINGS)) { snmp_log(LOG_WARNING, "Warning: %s.%ld is both %s and %s (%s)\n", root->label, np->subid, tp->label, np->label, File); } } tp = (struct tree *) calloc(1, sizeof(struct tree)); if (tp == NULL) return; tp->parent = xxroot; tp->modid = np->modid; tp->number_modules = 1; tp->module_list = &(tp->modid); tree_from_node(tp, np); tp->next_peer = otp ? otp->next_peer : xxroot->child_list; if (otp) otp->next_peer = tp; else xxroot->child_list = tp; hash = NBUCKET(name_hash(tp->label)); tp->next = tbuckets[hash]; tbuckets[hash] = tp; do_subtree(tp, nodes); if (anon_tp) { if (!strncmp(tp->label, ANON, ANON_LEN)) { /* * The new node is anonymous, * so merge it with the existing one. */ merge_anon_children(tp, anon_tp); /* * unlink and destroy tp */ unlink_tree(tp); free_tree(tp); } else if (!strncmp(anon_tp->label, ANON, ANON_LEN)) { struct tree *ntp; /* * The old node was anonymous, * so merge it with the existing one, * and fill in the full information. */ merge_anon_children(anon_tp, tp); /* * unlink anon_tp from the hash */ unlink_tbucket(anon_tp); /* * get rid of old contents of anon_tp */ free_partial_tree(anon_tp, FALSE); /* * put in the current information */ anon_tp->label = tp->label; anon_tp->child_list = tp->child_list; anon_tp->modid = tp->modid; anon_tp->tc_index = tp->tc_index; anon_tp->type = tp->type; anon_tp->enums = tp->enums; anon_tp->indexes = tp->indexes; anon_tp->augments = tp->augments; anon_tp->varbinds = tp->varbinds; anon_tp->ranges = tp->ranges; anon_tp->hint = tp->hint; anon_tp->units = tp->units; anon_tp->description = tp->description; anon_tp->defaultValue = tp->defaultValue; anon_tp->parent = tp->parent; set_function(anon_tp); /* * update parent pointer in moved children */ ntp = anon_tp->child_list; while (ntp) { ntp->parent = anon_tp; ntp = ntp->next_peer; } /* * hash in anon_tp in its new place */ hash = NBUCKET(name_hash(anon_tp->label)); anon_tp->next = tbuckets[hash]; tbuckets[hash] = anon_tp; /* * unlink and destroy tp */ unlink_tbucket(tp); unlink_tree(tp); free(tp); } else { /* * Uh? One of these two should have been anonymous! */ if (netsnmp_ds_get_int(NETSNMP_DS_LIBRARY_ID, NETSNMP_DS_LIB_MIB_WARNINGS)) { snmp_log(LOG_WARNING, "Warning: expected anonymous node (either %s or %s) in %s\n", tp->label, anon_tp->label, File); } } anon_tp = NULL; } } /* * free all nodes that were copied into tree */ oldnp = NULL; for (np = child_list; np; np = np->next) { if (oldnp) free_node(oldnp); oldnp = np; } if (oldnp) free_node(oldnp);}static voiddo_linkup(struct module *mp, struct node *np){ struct module_import *mip; struct node *onp, *oldp, *newp; struct tree *tp; int i, more; /* * All modules implicitly import * the roots of the tree */ if (snmp_get_do_debugging() > 1) dump_module_list(); DEBUGMSGTL(("parse-mibs", "Processing IMPORTS for module %d %s\n", mp->modid, mp->name)); if (mp->no_imports == 0) { mp->no_imports = NUMBER_OF_ROOT_NODES; mp->imports = root_imports; } /* * Build the tree */ init_node_hash(np); for (i = 0, mip = mp->imports; i < mp->no_imports; ++i, ++mip) { char modbuf[256]; DEBUGMSGTL(("parse-mibs", " Processing import: %s\n", mip->label)); if (get_tc_index(mip->label, mip->modid) != -1) continue; tp = find_tree_node(mip->label, mip->modid); if (!tp) { if (mip->modid != -1) snmp_log(LOG_WARNING, "Did not find '%s' in module %s (%s)\n", mip->label, module_name(mip->modid, modbuf), File); continue; } do_subtree(tp, &np); } /* * If any nodes left over, * check that they're not the result of a "fully qualified" * name, and then add them to the list of orphans */ if (!np) return; for (tp = tree_head; tp; tp = tp->next_peer) do_subtree(tp, &np); if (!np) return; /* * quietly move all internal references to the orphan list */ oldp = orphan_nodes; do { for (i = 0; i < NHASHSIZE; i++) for (onp = nbuckets[i]; onp; onp = onp->next) { struct node *op = NULL; int hash = NBUCKET(name_hash(onp->label)); np = nbuckets[hash]; while (np) { if (label_compare(onp->label, np->parent)) { op = np; np = np->next; } else { if (op) op->next = np->next; else nbuckets[hash] = np->next; np->next = orphan_nodes; orphan_nodes = np; op = NULL; np = nbuckets[hash]; } } } newp = orphan_nodes; more = 0; for (onp = orphan_nodes; onp != oldp; onp = onp->next) { struct node *op = NULL; int hash = NBUCKET(name_hash(onp->label)); np = nbuckets[hash]; while (np) { if (label_compare(onp->label, np->parent)) { op = np; np = np->next; } else { if (op) op->next = np->next; else nbuckets[hash] = np->next; np->next = orphan_nodes; orphan_nodes = np; op = NULL; np = nbuckets[hash]; more = 1; } } } oldp = newp; } while (more); /* * complain about left over nodes */ for (np = orphan_nodes; np && np->next; np = np->next); /* find the end of the orphan list */ for (i = 0; i < NHASHSIZE; i++) if (nbuckets[i]) { if (orphan_nodes) onp = np->next = nbuckets[i]; else onp = orphan_nodes = nbuckets[i]; nbuckets[i] = NULL; while (onp) { snmp_log(LOG_WARNING, "Unlinked OID in %s: %s ::= { %s %ld }\n", (mp->name ? mp->name : "<no module>"), (onp->label ? onp->label : "<no label>"), (onp->parent ? onp->parent : "<no parent>"), onp->subid); snmp_log(LOG_WARNING, "Undefined identifier: %s near line %d of %s\n", (onp->parent ? onp->parent : "<no parent>"), onp->lineno, onp->filename); np = onp; onp = onp->next; } } return;}/*
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -