2.11BSD/src/usr.bin/learn/selsub.c
#ifndef lint
static char sccsid[] = "@(#)selsub.c 4.3 (Berkeley) 5/15/86";
#endif not lint
#include "stdio.h"
#include "sys/types.h"
#include "sys/stat.h"
#include "lrnref.h"
char learnrc[100];
selsub(argc,argv)
char *argv[];
{
char ans1[100];
static char ans2[40];
static char dirname[40];
static char subname[40];
FILE *fp;
char *getenv();
char *home;
if (argc > 1 && argv[1][0] == '-') {
direct = argv[1]+1;
argc--;
argv++;
}
if (chdir(direct) != 0) {
perror(direct);
fprintf(stderr, "Selsub: couldn't cd to non-standard directory\n");
exit(1);
}
sname = argc > 1 ? argv[1] : 0;
if (argc > 2) {
strcpy (level=ans2, argv[2]);
if (strcmp(level, "-") == 0) /* no lesson name is - */
ask = 1;
else if (strcmp(level, "0") == 0)
level = 0;
else
again = 1; /* treat as if "again" lesson */
}
else
level = 0;
if (argc > 3 )
speed = atoi(argv[3]);
if ((home = getenv("HOME")) != NULL) {
sprintf(learnrc, "%s/.learnrc", home);
if ((fp=fopen(learnrc, "r")) != NULL) {
char xsub[40], xlev[40]; int xsp;
fscanf(fp, "%s %s %d", xsub, xlev, &xsp);
fclose(fp);
if (*xsub && *xlev && xsp >= 0 /* all read OK */
&& (argc == 2 && strcmp(sname, xsub) == 0
|| argc <= 1)) {
strcpy(sname = subname, xsub);
strcpy(level = ans2, xlev);
speed = xsp;
again = 1;
printf("[ Taking up where you left off last time: learn %s %s.\n",
sname, level);
printf("%s\n \"rm $HOME/.learnrc\", and re-enter with \"learn %s\". ]\n",
" To start this sequence over leave learn by typing \"bye\", then",
sname);
}
}
}
if (!sname) {
printf("These are the available courses -\n");
list("Linfo");
printf("If you want more information about the courses,\n");
printf("or if you have never used 'learn' before,\n");
printf("press RETURN; otherwise type the name of\n");
printf("the course you want, followed by RETURN.\n");
fflush(stdout);
gets(sname=subname);
if (sname[0] == '\0') {
list("Xinfo");
do {
printf("\nWhich subject? ");
fflush(stdout);
gets(sname=subname);
} while (sname[0] == '\0');
}
}
chknam(sname);
total = cntlessons(sname);
if (!level) {
printf("If you were in the middle of this subject\n");
printf("and want to start where you left off, type\n");
printf("the last lesson number the computer printed.\n");
printf("If you don't know the number, type in a word\n");
printf("you think might appear in the lesson you want,\n");
printf("and I will look for the first lesson containing it.\n");
printf("To start at the beginning, just hit RETURN.\n");
fflush(stdout);
gets(ans2);
if (ans2[0]==0)
strcpy(ans2,"0");
else
again = 1;
level=ans2;
getlesson();
}
/* make new directory for user to play in */
if (chdir("/tmp") != 0) {
perror("/tmp");
fprintf(stderr, "Selsub: couldn't cd to public directory\n");
exit(1);
}
sprintf(dir=dirname, "pl%da", getpid());
sprintf(ans1, "mkdir %s", dir);
system(ans1);
if (chdir(dir) < 0) {
perror(dir);
fprintf(stderr, "Selsub: couldn't make play directory with %s.\nBye.\n", ans1);
exit(1);
}
/* after this point, we have a working directory. */
/* have to call wrapup to clean up */
if (access(sprintf(ans1, "%s/%s/Init", direct, sname), 04)==0)
if (system(sprintf(ans1, "%s/%s/Init %s", direct, sname, level)) != 0) {
printf("Leaving learn.\n");
wrapup(1);
}
}
chknam(name)
char *name;
{
if (access(name, 05) < 0) {
printf("Sorry, there is no subject or lesson named %s.\nBye.\n", name);
exit(1);
}
}
#ifndef DIR
#include <sys/dir.h>
#endif
cntlessons(sname) /* return number of entries in lesson directory; */
char *sname; /* approximate at best since I don't count L0, Init */
{ /* and lessons skipped by good students */
#if BSD4_2
struct direct dbuf;
register struct direct *ep = &dbuf; /* directory entry pointer */
int n = 0;
DIR *dp;
if ((dp = opendir(sname)) == NULL) {
perror(sname);
wrapup(1);
}
for (ep = readdir(dp); ep != NULL; ep = readdir(dp)) {
if (ep->d_ino != 0)
n++;
}
closedir(dp);
return n - 2; /* minus . and .. */
#else
struct stat statbuf;
stat(sname, &statbuf);
return statbuf.st_size / 16 - 2;
#endif
}