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

📄 cache_manager.c

📁 -
💻 C
字号:
/* * $Id: cache_manager.c,v 1.20 1999/01/19 02:24:21 wessels Exp $ * * DEBUG: section 16    Cache Manager Objects * AUTHOR: Duane Wessels * * SQUID Internet Object Cache  http://squid.nlanr.net/Squid/ * ---------------------------------------------------------- * *  Squid is the result of efforts by numerous individuals from the *  Internet community.  Development is led by Duane Wessels of the *  National Laboratory for Applied Network Research and funded by the *  National Science Foundation.  Squid is Copyrighted (C) 1998 by *  Duane Wessels and the University of California San Diego.  Please *  see the COPYRIGHT file for full details.  Squid incorporates *  software developed and/or copyrighted by other sources.  Please see *  the CREDITS file for full details. * *  This program is free software; you can redistribute it and/or modify *  it under the terms of the GNU General Public License as published by *  the Free Software Foundation; either version 2 of the License, or *  (at your option) any later version. *   *  This program is distributed in the hope that it will be useful, *  but WITHOUT ANY WARRANTY; without even the implied warranty of *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the *  GNU General Public License for more details. *   *  You should have received a copy of the GNU General Public License *  along with this program; if not, write to the Free Software *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA. * */#include "squid.h"#define MGR_PASSWD_SZ 128typedef struct {    StoreEntry *entry;    char *action;    char *user_name;    char *passwd;} cachemgrStateData;typedef struct _action_table {    char *action;    char *desc;    OBJH *handler;    struct {	int pw_req:1;	int atomic:1;    } flags;    struct _action_table *next;} action_table;static action_table *cachemgrFindAction(const char *action);static cachemgrStateData *cachemgrParseUrl(const char *url);static void cachemgrParseHeaders(cachemgrStateData * mgr, const request_t * request);static int cachemgrCheckPassword(cachemgrStateData *);static void cachemgrStateFree(cachemgrStateData * mgr);static char *cachemgrPasswdGet(cachemgr_passwd *, const char *);static const char *cachemgrActionProtection(const action_table * at);static OBJH cachemgrShutdown;static OBJH cachemgrMenu;action_table *ActionTable = NULL;voidcachemgrRegister(const char *action, const char *desc, OBJH * handler, int pw_req_flag, int atomic){    action_table *a;    action_table **A;    if (cachemgrFindAction(action) != NULL) {	debug(16, 3) ("cachemgrRegister: Duplicate '%s'\n", action);	return;    }    a = xcalloc(1, sizeof(action_table));    a->action = xstrdup(action);    a->desc = xstrdup(desc);    a->handler = handler;    a->flags.pw_req = pw_req_flag;    a->flags.atomic = atomic;    for (A = &ActionTable; *A; A = &(*A)->next);    *A = a;    debug(16, 3) ("cachemgrRegister: registered %s\n", action);}static action_table *cachemgrFindAction(const char *action){    action_table *a;    for (a = ActionTable; a != NULL; a = a->next) {	if (0 == strcmp(a->action, action))	    return a;    }    return NULL;}static cachemgrStateData *cachemgrParseUrl(const char *url){    int t;    LOCAL_ARRAY(char, host, MAX_URL);    LOCAL_ARRAY(char, request, MAX_URL);    LOCAL_ARRAY(char, password, MAX_URL);    action_table *a;    cachemgrStateData *mgr = NULL;    const char *prot;    t = sscanf(url, "cache_object://%[^/]/%[^@]@%s", host, request, password);    if (t < 2) {	xstrncpy(request, "menu", MAX_URL);#ifdef _SQUID_OS2_	/*	 * emx's sscanf insists of returning 2 because it sets request	 * to null	 */    } else if (request[0] == '\0') {	xstrncpy(request, "menu", MAX_URL);#endif    } else if ((a = cachemgrFindAction(request)) == NULL) {	debug(16, 1) ("cachemgrParseUrl: action '%s' not found\n", request);	return NULL;    } else {	prot = cachemgrActionProtection(a);	if (!strcmp(prot, "disabled") || !strcmp(prot, "hidden")) {	    debug(16, 1) ("cachemgrParseUrl: action '%s' is %s\n", request, prot);	    return NULL;	}    }    /* set absent entries to NULL so we can test if they are present later */    mgr = xcalloc(1, sizeof(cachemgrStateData));    mgr->user_name = NULL;    mgr->passwd = t == 3 ? xstrdup(password) : NULL;    mgr->action = xstrdup(request);    return mgr;}static voidcachemgrParseHeaders(cachemgrStateData * mgr, const request_t * request){    const char *basic_cookie;	/* base 64 _decoded_ user:passwd pair */    const char *passwd_del;    assert(mgr && request);    basic_cookie = httpHeaderGetAuth(&request->header, HDR_AUTHORIZATION, "Basic");    if (!basic_cookie)	return;    if (!(passwd_del = strchr(basic_cookie, ':'))) {	debug(16, 1) ("cachemgrParseHeaders: unknown basic_cookie format '%s'\n", basic_cookie);	return;    }    /* found user:password pair, reset old values */    safe_free(mgr->user_name);    safe_free(mgr->passwd);    mgr->user_name = xstrdup(basic_cookie);    mgr->user_name[passwd_del - basic_cookie] = '\0';    mgr->passwd = xstrdup(passwd_del + 1);    /* warning: this prints decoded password which maybe not what you want to do @?@ @?@ */    debug(16, 9) ("cachemgrParseHeaders: got user: '%s' passwd: '%s'\n", mgr->user_name, mgr->passwd);}/* * return 0 if mgr->password is good */static intcachemgrCheckPassword(cachemgrStateData * mgr){    char *pwd = cachemgrPasswdGet(Config.passwd_list, mgr->action);    action_table *a = cachemgrFindAction(mgr->action);    assert(a != NULL);    if (pwd == NULL)	return a->flags.pw_req;    if (strcmp(pwd, "disable") == 0)	return 1;    if (strcmp(pwd, "none") == 0)	return 0;    if (!mgr->passwd)	return 1;    return strcmp(pwd, mgr->passwd);}static voidcachemgrStateFree(cachemgrStateData * mgr){    safe_free(mgr->action);    safe_free(mgr->user_name);    safe_free(mgr->passwd);    storeUnlockObject(mgr->entry);    xfree(mgr);}voidcachemgrStart(int fd, request_t * request, StoreEntry * entry){    cachemgrStateData *mgr = NULL;    ErrorState *err = NULL;    action_table *a;    debug(16, 3) ("objectcacheStart: '%s'\n", storeUrl(entry));    if ((mgr = cachemgrParseUrl(storeUrl(entry))) == NULL) {	err = errorCon(ERR_INVALID_URL, HTTP_NOT_FOUND);	err->url = xstrdup(storeUrl(entry));	errorAppendEntry(entry, err);	entry->expires = squid_curtime;	return;    }    mgr->entry = entry;    storeLockObject(entry);    entry->expires = squid_curtime;    debug(16, 5) ("CACHEMGR: %s requesting '%s'\n",	fd_table[fd].ipaddr, mgr->action);    /* get additional info from request headers */    cachemgrParseHeaders(mgr, request);    /* Check password */    if (cachemgrCheckPassword(mgr) != 0) {	/* build error message */	ErrorState *err;	HttpReply *rep;	err = errorCon(ERR_CACHE_MGR_ACCESS_DENIED, HTTP_UNAUTHORIZED);	/* warn if user specified incorrect password */	if (mgr->passwd)	    debug(16, 1) ("CACHEMGR: %s@%s: incorrect password for '%s'\n",		mgr->user_name ? mgr->user_name : "<unknown>",		fd_table[fd].ipaddr, mgr->action);	else	    debug(16, 1) ("CACHEMGR: %s@%s: password needed for '%s'\n",		mgr->user_name ? mgr->user_name : "<unknown>",		fd_table[fd].ipaddr, mgr->action);	err->request = requestLink(request);	rep = errorBuildReply(err);	errorStateFree(err);	/*	 * add Authenticate header, use 'action' as a realm because	 * password depends on action	 */	httpHeaderPutAuth(&rep->header, "Basic", mgr->action);	/* move info to the mem_obj->reply */	httpReplyAbsorb(entry->mem_obj->reply, rep);	/* store the reply */	httpReplySwapOut(entry->mem_obj->reply, entry);	entry->expires = squid_curtime;	storeComplete(entry);	cachemgrStateFree(mgr);	return;    }    debug(16, 1) ("CACHEMGR: %s@%s requesting '%s'\n",	mgr->user_name ? mgr->user_name : "<unknown>",	fd_table[fd].ipaddr, mgr->action);    /* retrieve object requested */    a = cachemgrFindAction(mgr->action);    assert(a != NULL);    if (a->flags.atomic)	storeBuffer(entry);    {	HttpReply *rep = entry->mem_obj->reply;	/* prove there are no previous reply headers around */	assert(0 == rep->sline.status);	httpReplySetHeaders(rep,	    (double) 1.0,	    HTTP_OK,	    NULL,	    "text/plain",	    -1,			/* C-Len */	    squid_curtime,	/* LMT */	    squid_curtime);	httpReplySwapOut(rep, entry);    }    a->handler(entry);    if (a->flags.atomic) {	storeBufferFlush(entry);	storeComplete(entry);    }    cachemgrStateFree(mgr);}static voidcachemgrShutdown(StoreEntry * entryunused){    debug(16, 0) ("Shutdown by command.\n");    shut_down(0);}static const char *cachemgrActionProtection(const action_table * at){    char *pwd;    assert(at);    pwd = cachemgrPasswdGet(Config.passwd_list, at->action);    if (!pwd)	return at->flags.pw_req ? "hidden" : "public";    if (!strcmp(pwd, "disable"))	return "disabled";    if (strcmp(pwd, "none") == 0)	return "public";    return "protected";}static voidcachemgrMenu(StoreEntry * sentry){    action_table *a;    for (a = ActionTable; a != NULL; a = a->next) {	storeAppendPrintf(sentry, " %-22s\t%s\t%s\n",	    a->action, a->desc, cachemgrActionProtection(a));    }}static char *cachemgrPasswdGet(cachemgr_passwd * a, const char *action){    wordlist *w;    while (a != NULL) {	for (w = a->actions; w != NULL; w = w->next) {	    if (0 == strcmp(w->key, action))		return a->passwd;	    if (0 == strcmp(w->key, "all"))		return a->passwd;	}	a = a->next;    }    return NULL;}voidcachemgrInit(void){    cachemgrRegister("menu",	"This Cachemanager Menu",	cachemgrMenu, 0, 1);    cachemgrRegister("shutdown",	"Shut Down the Squid Process",	cachemgrShutdown, 1, 1);}

⌨️ 快捷键说明

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