⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 rt-mt.c

📁 早期freebsd实现
💻 C
📖 第 1 页 / 共 2 页
字号:
    if (num < 0 || num >= total.author) {	/*error("invalid author in thread file: %d [%ld]\n", num, art_num);*/	invalid_data = TRUE;	return Nullch;    }    return savestr(author_array[num]);}/* Our parent/sibling information is a relative offset in the article array.** zero for none.  Child values are always found in the very next array** element if child_cnt is non-zero.*/static ARTICLE *the_article(relative_offset, num)WORD relative_offset;int num;{    union { ARTICLE *ap; int num; } uni;    if (!relative_offset)	return Nullart;    num += relative_offset;    if (num < 0 || num >= total.article) {	/*error("invalid article offset in thread file.\n");*/	invalid_data = TRUE;	return Nullart;    }    uni.num = num+1;    return uni.ap;		/* slip them an offset in disguise */}/* Read the articles into their trees.  Point everything everywhere. */static intread_articles(){    register int count;    register ARTICLE *article, **art_ptr;    int ret;    /* Build an array to interpret interlinkages of articles. */    article_array = (ARTICLE**)safemalloc(total.article * sizeof (ARTICLE*));    art_ptr = article_array;    invalid_data = FALSE;    for (count = 0; count < total.article; count++) {#ifdef USE_XTHREAD	ret = nntp_read((char*)&p_article, (long)sizeof (PACKED_ARTICLE));#else	ret = fread((char*)&p_article, 1, sizeof (PACKED_ARTICLE), fp);#endif	if (ret != sizeof (PACKED_ARTICLE)) {	    /*error("failed article read -- %d bytes instead of %d.\n",		ret, sizeof (PACKED_ARTICLE));*/	    return 0;	}	lp_bmap(&p_article.num, 2);	wp_bmap(&p_article.subject, 8);	article = *art_ptr++ = allocate_article(p_article.num);	article->date = p_article.date;#ifndef DBM_XREFS	if (olden_days < 2 && !(p_article.flags & HAS_XREFS))	    article->xrefs = nullstr;#endif	article->from = the_author(p_article.author);	article->parent = the_article(p_article.parent, count);	article->child1 = the_article(p_article.child_cnt ? 1 : 0, count);	article->sibling = the_article(p_article.sibling, count);	article->subj = the_subject(p_article.subject);	if (invalid_data) {	    /* (Error already logged.) */	    return 0;	}	/* This is ok because parent articles precede their children */	if (article->parent) {	    union { ARTICLE *ap; int num; } uni;	    uni.ap = article->parent;	    article->parent = article_array[uni.num-1];	}	if (article->subj) {	    if (!(article->flags & AF_MISSING)) {		article->flags |= AF_FROMTRUNCED | AF_THREADED		    | ((p_article.flags & ROOT_ARTICLE)? 0 : AF_HAS_RE);	    }	    /* Give this subject to any faked parent articles */	    while (article->parent && !article->parent->subj) {		article->parent->subj = article->subj;		article = article->parent;	    }	} else	    article->flags |= AF_FAKE;    }    /* We're done with most of the pointer arrays at this point. */    safefree((char**)&subject_array);    safefree((char**)&author_array);    safefree(&strings);    return 1;}/* Read the message-id strings and attach them to each article.  The data** format consists of the mushed-together null-terminated strings (a domain** name followed by all its unique-id prefixes) and then the article offsets** to which they belong.  The first domain name was omitted, as it is a null** domain for those truly weird message-id's without '@'s.*/static intread_ids(){    register ARTICLE *article;    register char *string_ptr;    register int i, count, len, len2;    if (!read_item(&strings, (MEM_SIZE)total.string2)     || !read_item((char**)&ids,		(MEM_SIZE)(total.article+total.domain+1) * sizeof (WORD))) {	return 0;    }    wp_bmap(ids, total.article + total.domain + 1);    string_ptr = strings;    string_end = string_ptr + total.string2;    if (string_end[-1] != '\0') {	/*error("second string table is invalid.\n");*/	return 0;    }    for (i = 0, count = total.domain + 1; count--; i++) {	if (i) {	    if (string_ptr >= string_end) {		/*error("error unpacking domain strings.\n");*/		return 0;	    }	    sprintf(buf, "@%s", string_ptr);	    len = strlen(string_ptr) + 1;	    string_ptr += len;	} else {	    *buf = '\0';	    len = 0;	}	if (ids[i] != -1) {	    if (ids[i] < 0 || ids[i] >= total.article) {		/*error("error in id array.\n");*/		return 0;	    }	    article = article_array[ids[i]];	    for (;;) {		if (string_ptr >= string_end) {		    /*error("error unpacking domain strings.\n");*/		    return 0;		}		len2 = strlen(string_ptr);		article->msgid = safemalloc(len2 + len + 2 + 1);		sprintf(article->msgid, "<%s%s>", string_ptr, buf);		string_ptr += len2 + 1;		if (msgid_hash)		{		    HASHDATUM data;		    if ((article->flags & AF_TMPMEM) == AF_TMPMEM) {			data.dat_ptr = (char*)article;			data.dat_len = 0;		    } else {			data.dat_ptr = Nullch;			data.dat_len = article_num(article);		    }		    hashstore(msgid_hash, article->msgid, len2+len+2, data);		}		if (++i >= total.article + total.domain + !count) {		    /*error("overran id array unpacking domains.\n");*/		    return 0;		}		if (ids[i] != -1) {		    if (ids[i] < 0 || ids[i] >= total.article)			return 0;		    article = article_array[ids[i]];		} else		    break;	    }	}    }    safefree((char**)&ids);    safefree(&strings);    return 1;}/* And finally, turn all the links into real pointers and mark missing** articles as read.*/static voidtweak_data(){    register int count;    register ARTICLE *ap, **art_ptr;    register SUBJECT *sp;    register ART_NUM i;    union { ARTICLE *ap; int num; } uni;    for (sp = first_subject; sp; sp = sp->next) {	uni.ap = sp->thread;	sp->thread = article_array[uni.num];	sp->thread->subj->flags |= SF_THREAD;    }    art_ptr = article_array;    for (count = total.article; count--; ) {	ap = *art_ptr++;	if (ap->child1) {	    uni.ap = ap->child1;	    ap->child1 = article_array[uni.num-1];	}	if (ap->sibling) {	    uni.ap = ap->sibling;	    ap->sibling = article_array[uni.num-1];	}	if (!(ap->flags & AF_MISSING))	    cache_article(ap);    }    /* Mark any missing articles as read */    for (i = absfirst, ap = article_ptr(i); i <= total.last; i++, ap++) {	if ((ap->flags & (AF_CACHED|AF_MISSING)) == AF_CACHED)	    check_poster(ap);	else	    onemissing(ap);    }    safefree((char**)&article_array);}/* A shorthand for reading a chunk of the file into a malloc'ed array.*/static intread_item(dest, len)char **dest;MEM_SIZE len;{    long ret;    *dest = safemalloc(len);#ifdef USE_XTHREAD    ret = nntp_read(*dest, (long)len);#else    ret = fread(*dest, 1, (int)len, fp);#endif    if (ret != len) {	free(*dest);	*dest = Nullch;	return 0;    }    putchar('.'), fflush(stdout);    return 1;}/* Free some memory if it hasn't already been freed.*/static voidsafefree(pp)char **pp;{    if (*pp) {	free(*pp);	*pp = Nullch;    }}/* Determine this machine's byte map for WORDs and LONGs.  A byte map is an** array of BYTEs (sizeof (WORD) or sizeof (LONG) of them) with the 0th BYTE** being the byte number of the high-order byte in my <type>, and so forth.*/static voidmybytemap(map)BMAP *map;{    union {	BYTE b[sizeof (LONG)];	WORD w;	LONG l;    } u;    register BYTE *mp;    register int i, j;    mp = &map->w[sizeof (WORD)];    u.w = 1;    for (i = sizeof (WORD); i > 0; i--) {	for (j = 0; j < sizeof (WORD); j++) {	    if (u.b[j] != 0)		break;	}	if (j == sizeof (WORD))	    goto bad_news;	*--mp = j;	while (u.b[j] != 0 && u.w)	    u.w <<= 1;    }    mp = &map->l[sizeof (LONG)];    u.l = 1;    for (i = sizeof (LONG); i > 0; i--) {	for (j = 0; j < sizeof (LONG); j++) {	    if (u.b[j] != 0)		break;	}	if (j == sizeof (LONG)) {	  bad_news:	    /* trouble -- set both to *something* consistent */	    for (j = 0; j < sizeof (WORD); j++)		map->w[j] = j;	    for (j = 0; j < sizeof (LONG); j++)		map->l[j] = j;	    return;	}	*--mp = j;	while (u.b[j] != 0 && u.l)	    u.l <<= 1;    }}/* Transform each WORD's byte-ordering in a buffer of the designated length.*/static voidwp_bmap(buf, len)WORD *buf;int len;{    union {	BYTE b[sizeof (WORD)];	WORD w;    } in, out;    register int i;    if (word_same)	return;    while (len--) {	in.w = *buf;	for (i = 0; i < sizeof (WORD); i++)	    out.b[my_bmap.w[i]] = in.b[mt_bmap.w[i]];	*buf++ = out.w;    }}/* Transform each LONG's byte-ordering in a buffer of the designated length.*/static voidlp_bmap(buf, len)LONG *buf;int len;{    union {	BYTE b[sizeof (LONG)];	LONG l;    } in, out;    register int i;    if (long_same)	return;    while (len--) {	in.l = *buf;	for (i = 0; i < sizeof (LONG); i++)	    out.b[my_bmap.l[i]] = in.b[mt_bmap.l[i]];	*buf++ = out.l;    }}#endif /* USE_MT */

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -