diff blobstat/readclass.c @ 293:23e5b940cb8b

blobstat: mostly complete
author Mychaela Falconia <falcon@freecalypso.org>
date Sat, 21 Sep 2019 21:07:45 +0000
parents
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/blobstat/readclass.c	Sat Sep 21 21:07:45 2019 +0000
@@ -0,0 +1,160 @@
+#include <sys/types.h>
+#include <ctype.h>
+#include <string.h>
+#include <strings.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include "struct.h"
+
+extern struct category *category_list;
+extern struct libentry *libentry_list;
+
+static struct category *
+find_or_create_cat(catname)
+	char *catname;
+{
+	struct category *p, **pp;
+	char *buf;
+
+	for (pp = &category_list; p = *pp; pp = &p->next)
+		if (!strcmp(p->name, catname))
+			return(p);
+	buf = malloc(sizeof(struct category) + strlen(catname) + 1);
+	if (!buf) {
+		perror("malloc");
+		exit(1);
+	}
+	p = (struct category *) buf;
+	p->name = buf + sizeof(struct category);
+	strcpy(p->name, catname);
+	p->accum = 0;
+	p->next = 0;
+	*pp = p;
+	return(p);
+}
+
+static
+add_whole_lib(libname, cat)
+	char *libname;
+	struct category *cat;
+{
+	struct libentry *p, **pp;
+	char *buf;
+
+	for (pp = &libentry_list; p = *pp; pp = &p->next)
+		if (!strcmp(p->libname, libname))
+			return(-1);
+	buf = malloc(sizeof(struct libentry) + strlen(libname) + 1);
+	if (!buf) {
+		perror("malloc");
+		exit(1);
+	}
+	p = (struct libentry *) buf;
+	p->libname = buf + sizeof(struct libentry);
+	strcpy(p->libname, libname);
+	p->member = 0;
+	p->cat = cat;
+	p->next = 0;
+	*pp = p;
+	return(0);
+}
+
+static
+add_lib_member(libname, member, cat)
+	char *libname, *member;
+	struct category *cat;
+{
+	struct libentry *p, **pp;
+	char *buf;
+
+	for (pp = &libentry_list; p = *pp; pp = &p->next) {
+		if (strcmp(p->libname, libname))
+			continue;
+		if (!p->member || !strcmp(p->member, member))
+			return(-1);
+	}
+	buf = malloc(sizeof(struct libentry) + strlen(libname) +
+			strlen(member) + 2);
+	if (!buf) {
+		perror("malloc");
+		exit(1);
+	}
+	p = (struct libentry *) buf;
+	buf += sizeof(struct libentry);
+	p->libname = buf;
+	strcpy(p->libname, libname);
+	buf += strlen(libname) + 1;
+	p->member = buf;
+	strcpy(p->member, member);
+	p->cat = cat;
+	p->next = 0;
+	*pp = p;
+	return(0);
+}
+
+static void
+process_line(linebuf, lineno, filename_for_errs)
+	char *linebuf, *filename_for_errs;
+	int lineno;
+{
+	char *cp, *libname, *member, *catname;
+	struct category *cat;
+	int rc;
+
+	for (cp = linebuf; isspace(*cp); cp++)
+		;
+	if (*cp == '\0' || *cp == '#')
+		return;
+	for (libname = cp; *cp && !isspace(*cp); cp++)
+		;
+	if (!*cp) {
+inv:		fprintf(stderr, "%s line %d: invalid syntax\n",
+			filename_for_errs, lineno);
+		exit(1);
+	}
+	*cp++ = '\0';
+	while (isspace(*cp))
+		cp++;
+	if (*cp == '\0' || *cp == '#')
+		goto inv;
+	for (catname = cp; *cp && !isspace(*cp); cp++)
+		;
+	if (*cp)
+		*cp++ = '\0';
+	while (isspace(*cp))
+		cp++;
+	if (*cp != '\0' && *cp != '#')
+		goto inv;
+	member = index(libname, ':');
+	if (member)
+		*member++ = '\0';
+	cat = find_or_create_cat(catname);
+	if (member)
+		rc = add_lib_member(libname, member, cat);
+	else
+		rc = add_whole_lib(libname, cat);
+	if (rc < 0) {
+		fprintf(stderr,
+			"%s line %d: conflict with earlier declaration\n",
+			filename_for_errs, lineno);
+		exit(1);
+	}
+}
+
+read_class_file(filename)
+	char *filename;
+{
+	FILE *inf;
+	int lineno;
+	char linebuf[512];
+
+	inf = fopen(filename, "r");
+	if (!inf) {
+		perror(filename);
+		exit(1);
+	}
+	for (lineno = 1; fgets(linebuf, sizeof linebuf, inf); lineno++)
+		process_line(linebuf, lineno, filename);
+	fclose(inf);
+	return(0);
+}