예제 #1
0
파일: cgi.c 프로젝트: mr-justin/freebsd
static void
pg_searchres(const struct req *req, struct manpage *r, size_t sz)
{
	char		*arch, *archend;
	size_t		 i, iuse, isec;
	int		 archprio, archpriouse;
	int		 prio, priouse;
	char		 sec;

	for (i = 0; i < sz; i++) {
		if (validate_filename(r[i].file))
			continue;
		fprintf(stderr, "invalid filename %s in %s database\n",
		    r[i].file, req->q.manpath);
		pg_error_internal();
		return;
	}

	if (1 == sz) {
		/*
		 * If we have just one result, then jump there now
		 * without any delay.
		 */
		printf("Status: 303 See Other\r\n");
		printf("Location: http://%s%s/%s/%s?",
		    HTTP_HOST, scriptname, req->q.manpath, r[0].file);
		http_printquery(req, "&");
		printf("\r\n"
		     "Content-Type: text/html; charset=utf-8\r\n"
		     "\r\n");
		return;
	}

	resp_begin_html(200, NULL);
	resp_searchform(req);
	puts("<DIV CLASS=\"results\">");
	puts("<TABLE>");

	for (i = 0; i < sz; i++) {
		printf("<TR>\n"
		       "<TD CLASS=\"title\">\n"
		       "<A HREF=\"%s/%s/%s?", 
		    scriptname, req->q.manpath, r[i].file);
		http_printquery(req, "&amp;");
		printf("\">");
		html_print(r[i].names);
		printf("</A>\n"
		       "</TD>\n"
		       "<TD CLASS=\"desc\">");
		html_print(r[i].output);
		puts("</TD>\n"
		     "</TR>");
	}

	puts("</TABLE>\n"
	     "</DIV>");

	/*
	 * In man(1) mode, show one of the pages
	 * even if more than one is found.
	 */

	if (req->q.equal) {
		puts("<HR>");
		iuse = 0;
		priouse = 10;
		archpriouse = 3;
		for (i = 0; i < sz; i++) {
			isec = strcspn(r[i].file, "123456789");
			sec = r[i].file[isec];
			if ('\0' == sec)
				continue;
			prio = sec_prios[sec - '1'];
			if (NULL == req->q.arch) {
				archprio =
				    (NULL == (arch = strchr(
					r[i].file + isec, '/'))) ? 3 :
				    (NULL == (archend = strchr(
					arch + 1, '/'))) ? 0 :
				    strncmp(arch, "amd64/",
					archend - arch) ? 2 : 1;
				if (archprio < archpriouse) {
					archpriouse = archprio;
					priouse = prio;
					iuse = i;
					continue;
				}
				if (archprio > archpriouse)
					continue;
			}
			if (prio >= priouse)
				continue;
			priouse = prio;
			iuse = i;
		}
		resp_show(req, r[iuse].file);
	}

	resp_end_html();
}
예제 #2
0
static void
resp_search(struct res *r, size_t sz, void *arg)
{
	size_t		 i, matched;
	const struct req *req;

	req = (const struct req *)arg;

	if (sz > 0)
		assert(req->q.manroot >= 0);

	for (matched = i = 0; i < sz; i++)
		if (r[i].matched)
			matched++;
	
	if (1 == matched) {
		for (i = 0; i < sz; i++)
			if (r[i].matched)
				break;
		/*
		 * If we have just one result, then jump there now
		 * without any delay.
		 */
		puts("Status: 303 See Other");
		printf("Location: http://%s%s/show/%d/%u/%u.html?",
				host, progname, req->q.manroot,
				r[i].volume, r[i].rec);
		http_printquery(req);
		puts("\n"
		     "Content-Type: text/html; charset=utf-8\n");
		return;
	}

	resp_begin_html(200, NULL);
	resp_searchform(req);

	puts("<DIV CLASS=\"results\">");

	if (0 == matched) {
		puts("<P>\n"
		     "No results found.\n"
		     "</P>\n"
		     "</DIV>");
		resp_end_html();
		return;
	}

	qsort(r, sz, sizeof(struct res), cmp);

	puts("<TABLE>");

	for (i = 0; i < sz; i++) {
		if ( ! r[i].matched)
			continue;
		printf("<TR>\n"
		       "<TD CLASS=\"title\">\n"
		       "<A HREF=\"%s/show/%d/%u/%u.html?", 
				progname, req->q.manroot,
				r[i].volume, r[i].rec);
		html_printquery(req);
		printf("\">");
		html_print(r[i].title);
		putchar('(');
		html_print(r[i].cat);
		if (r[i].arch && '\0' != *r[i].arch) {
			putchar('/');
			html_print(r[i].arch);
		}
		printf(")</A>\n"
		       "</TD>\n"
		       "<TD CLASS=\"desc\">");
		html_print(r[i].desc);
		puts("</TD>\n"
		     "</TR>");
	}

	puts("</TABLE>\n"
	     "</DIV>");
	resp_end_html();
}