src/build_history.c
/* [<][>][^][v][top][bottom][index][help] */
DEFINITIONS
This source file includes following functions.
- getdirname
- fullpath
- scan_article
- scan_directory
- build_history
/* $Id: build_history.c,v 1.1.1.1 1998/07/29 15:14:29 proff Exp $
* $Copyright$
*/
#include "nglobal.h"
#include "filesystem.h"
#include "history.h"
#include "build_history.h"
/* Strip off the port numbers to get the directory name. */
static char *getdirname(char *host)
/* [<][>][^][v][top][bottom][index][help] */
{
char *p, *q;
p = Sstrdup(host);
q = strchr(p, ':');
if (q) *q = 0;
return p;
}
/* Form the "full" pathname of a file. */
static char *fullpath(char *path, char *d_name)
/* [<][>][^][v][top][bottom][index][help] */
{
char *p;
int path_len, d_name_len;
int len;
path_len = strlen(path);
d_name_len = strlen(d_name);
len = path_len + d_name_len + 2;
p = Smalloc(len);
memcpy(p, path, path_len);
p[path_len] = '/';
memcpy(p + path_len + 1, d_name, d_name_len);
p[len - 1] = 0;
return p;
}
/* Scan one article and add it to the history if necessary. */
static void scan_article(char *path, char *artno)
/* [<][>][^][v][top][bottom][index][help] */
{
FILE *fp;
char buf[MAX_HEADER];
char msgid[MAX_MSGID] = "";
if (!(fp = fopen(artno, "r"))) {
loge(("couldn't open '%s' for history rebuild", artno));
return;
}
while (!*msgid && fgets(buf, sizeof(buf), fp)) {
if (tolower(*buf) == 'm' &&
strnCaseEq(buf, "message-id:", 11)) {
if (strSnip (buf+11, sizeof buf, "<", ">\n\r", msgid, sizeof msgid) > 0) {
if (!hisGetDbz(msgid))
hisAddDbz(msgid, path);
}
break;
}
while (buf[strlen(buf) - 1] != '\n' &&
fgets(buf, sizeof(buf), fp));
}
fclose(fp);
}
/* Scan the current directory recursively for things to add to the history. */
static void scan_directory(char *path)
/* [<][>][^][v][top][bottom][index][help] */
{
DIR *dp;
struct dirent *ep;
char *p, *q;
int i;
struct stat st;
if (!(dp = opendir(path))) {
loge(("rebuild: opendir('%s') failed", path));
return;
}
while ((ep = readdir(dp))) {
q = ep->d_name;
p = fullpath(path, q);
if (stat(p, &st) < 0) {
loge(("rebuild: stat('%s') failed", p));
free(p);
continue;
}
if (*q == '.')
;
else if (S_ISDIR(st.st_mode)) scan_directory(p);
else {
i = strspn(q, "0123456789");
if (S_ISREG(st.st_mode) && isdigit(q[0]) &&
(!q[i] || q[i] == '_')) {
if (q[i] == '_') q[i] = 0;
q = fullpath(path, q);
scan_article(q, p);
}
}
free(p);
}
closedir(dp);
}
/* Build the history file. */
EXPORT void build_history()
/* [<][>][^][v][top][bottom][index][help] */
{
char *p;
struct server_cfg *scfg;
for (scfg = ServerList; scfg; scfg = scfg->next) {
if (chdir(con->cacheDir)) {
loge(("rebuild: unable to chdir('%s')", con->cacheDir));
return;
}
p = getdirname(scfg->host);
scan_directory(p);
free(p);
}
}