/*****************************************************************************/ /* ProxyMaint.c See PROXYCACHE.C for commentary. This module implements both the ROUTINE and REACTIVE purge maintenance for the proxy file cache. See PROXYCACHE.C module for information on cache management strategy. VERSION HISTORY --------------- 20-MAR-2021 MGD reduced to a shadow of its former self (caching obsolete) 28-APR-2018 MGD refactor Admin..() AST delivery 18-JAN-2010 JPP bugfix; ProxyMaintInit() use v10orPrev10() for scan spec 19-AUG-2007 MGD use PercentOf() to avoid divide-by-zero exceptions 12-APR-2005 MGD ProxyMaintSupervisor() return if caching not enabled 04-SEP-2004 MGD PROXYCACHE.C v9.0.0 cache file header date/time usage 30-APR-2004 MGD use QIO to erase cache file (save a few cycles) 13-JAN-2004 MGD DECC 6.2 objected to '$DESCRIPTOR(name,ptr->string)' 11-JUN-2003 MGD bugfix; ProxyMaintDeviceStats() volume count (set) handling 11-MAY-2003 MGD proxy unknown request fields 29-APR-2003 MGD add proxy cache device error count statistics 02-APR-2003 MGD maintain 'ProxyXForwardedFor', modify for 'ProxyForwarded' 20-FEB-2003 MGD ProxytMaintSupervisor() used instead of timers, background purge (set with '[ProxyCacheRoutineHourOfDay] 24') 03-JUN-2002 MGD bugfix; ensure sys$search() RMS channel is released 15-MAY-2002 MGD proxy gateway statistics 11-APR-2002 MGD make a reactive purge initially more agressive, bugfix; switch return not break with next reactive scan 04-APR-2002 MGD add command-line and menu STOP to cache scans, update admin and monitor status string with scan progress, bugfix; command-line cache maintenance reporting 02-FEB-2002 MGD rework POSTed query due to request body processing changes 22-SEP-2001 MGD InstanceLock/UnLock() to control access to cache 04-AUG-2001 MGD support module WATCHing 07-MAY-2001 MGD monitor global section accounting changes 05-APR-2001 MGD add boolean to prevent ProxyMaintCacheLock() lock status block overwriting if multiple scans intiated from Admin Menu 20-DEC-2000 MGD routine proxy maintainence optionally disabled/external 13-SEP-2000 MGD ProxyMaintReport() call refined to optionally provide host name cache entries 08-JUL-2000 MGD add VMS locking around cache scan (for clusters) 04-MAR-2000 MGD use FaolToBuffer(), et.al. 03-JAN-2000 MGD no changes required for ODS-5 compliance ... it's not (see note in PROXYCACHE.C) 30-DEC-1999 MGD change $GETDVI() to $GETDVIW() (potential bugfix) 04-DEC-1999 MGD rework startup cache device and report details 22-OCT-1999 MGD inaccessable cache device non-fatal during startup 20-JUN-1999 MGD allow for cache devices >9GB in space calculations, some refinement to statistics report 19-AUG-1998 MGD initial development (recommenced DEC 1998) */ /*****************************************************************************/ #ifdef WASD_VMS_V7 #undef _VMS__V6__SOURCE #define _VMS__V6__SOURCE #undef __VMS_VER #define __VMS_VER 70000000 #undef __CRTL_VER #define __CRTL_VER 70000000 #endif /* standard C header files */ #include #include #include #include /* VMS related header files */ #include #include #include #include #include #include #include #include #include #include #include /* application-related header files */ #include "wasd.h" #define WASD_MODULE "PROXYMAINT" /********************/ /* external storage */ /********************/ extern BOOL ProxyServingEnabled, ProxyUnknownRequestFields; extern int EfnWait, EfnNoWait, HttpdTickSecond, OpcomMessages, ProxyConnectPersistMax, ProxyConnectPersistSeconds, ProxyConnectTimeoutSeconds, ProxyForwardedBy, ProxyHostLookupRetryCount, ProxyNetConnectCount, ProxyVerifyRecordMax, ProxyXForwardedFor; extern int ToLowerCase[], ToUpperCase[]; extern char ErrorSanityCheck[], ServerHostPort[]; extern unsigned short HttpdTime7[]; extern ACCOUNTING_STRUCT *AccountingPtr; extern CONFIG_STRUCT Config; extern MSG_STRUCT Msgs; extern PROXY_ACCOUNTING_STRUCT *ProxyAccountingPtr; extern PROXYVERIFY_GBLSEC *ProxyVerifyGblSecPtr; extern WATCH_STRUCT Watch; /*****************************************************************************/ /* Return a report and control menu related proxy serving. */ ProxyMaintReport (REQUEST_STRUCT *rqptr) { int status; /*********/ /* begin */ /*********/ if (WATCHMOD (rqptr, WATCH_MOD_PROXY)) WatchThis (WATCHITM(rqptr), WATCH_MOD_PROXY, "ProxyMaintReport()"); AdminPageTitle (rqptr, "Proxy Report"); status = ProxyMaintStatsReport (rqptr); if (VMSnok (status)) { rqptr->rqResponse.ErrorTextPtr = "ProxyMaintStatisticsReport()"; ErrorVmsStatus (rqptr, status, FI_LI); AdminEnd (rqptr); return; } status = ProxyMaintFunctionReport (rqptr); if (VMSnok (status)) { rqptr->rqResponse.ErrorTextPtr = "ProxyMaintFunctionReport()"; ErrorVmsStatus (rqptr, status, FI_LI); AdminEnd (rqptr); return; } rqptr->rqResponse.PreExpired = PRE_EXPIRE_ADMIN; ResponseHeader200 (rqptr, "text/html", &rqptr->NetWriteBufferDsc); AdminEnd (rqptr); } /*****************************************************************************/ /* Return a report on proxy serving. */ int ProxyMaintStatsReport (REQUEST_STRUCT *rqptr) { static char ResponseFao [] = "

\n\ \n\ \n\
Statistics!AZ
\n\ \n\ \n\
\n\ \ \n\ \n\ \n\ \n\ \n\ \n\
Proxy Total
Requests:!&L
Bytes:!&,@UQ
IPv4:!&L(!UL%)
IPv6:!&L(!UL%)
\n\ \
\n\ \ \n\ \n\ \n\ \n\ \n\
SOCKS5
Total:!&L
Success:!&L
Fail:!&L
\n\ \
\n\ \ \n\ \n\ \n\ \n\ \n\ \n\
Host Resolution
Literal:!&L
DNS:!&L(!UL%)
Cache:!&L
Error:!&L
\n\ \
\n\
\n"; int status, ConnectCountNetwork, PercentBytesNetwork, PercentCountIpv4, PercentCountIpv6, PercentCountNetwork, PercentDnsName, TotalCount; int64 BytesRaw64, BytesRawRx64, BytesRawTx64, BytesTotal64; unsigned short Length; unsigned long FaoVector [64]; unsigned long *vecptr; char Buffer [2048]; $DESCRIPTOR (BufferDsc, Buffer); /*********/ /* begin */ /*********/ if (WATCHMOD (rqptr, WATCH_MOD_PROXY)) WatchThis (WATCHITM(rqptr), WATCH_MOD_PROXY, "ProxyMaintStatsReport()"); InstanceMutexLock (INSTANCE_MUTEX_HTTPD); /*********/ /* bytes */ /*********/ BytesRaw64 = ProxyAccountingPtr->BytesRawRx64 + ProxyAccountingPtr->BytesRawTx64; PercentBytesNetwork = PercentOf64 (&BytesRaw64, &BytesTotal64); /*********************/ /* counts percentage */ /*********************/ ConnectCountNetwork = ProxyAccountingPtr->ConnectIpv4Count + ProxyAccountingPtr->ConnectIpv6Count; PercentCountIpv4 = PercentOf32 (&ProxyAccountingPtr->ConnectIpv4Count, &ConnectCountNetwork); PercentCountIpv6 = PercentOf32 (&ProxyAccountingPtr->ConnectIpv6Count, &ConnectCountNetwork); /* get these values because of the locking requirements */ BytesRawRx64 = ProxyAccountingPtr->BytesRawRx64; BytesRawTx64 = ProxyAccountingPtr->BytesRawTx64; TotalCount = AccountingPtr->LookupDnsNameCount + AccountingPtr->LookupCacheNameCount; if (TotalCount) PercentDnsName = AccountingPtr->LookupDnsNameCount * 100 / TotalCount; else PercentDnsName = 0; /***********/ /* display */ /***********/ vecptr = FaoVector; if (ProxyServingEnabled) *vecptr++ = ""; else *vecptr++ = " ... DISABLED"; *vecptr++ = AccountingPtr->DoProxyCount; *vecptr++ = &BytesRaw64; *vecptr++ = ProxyAccountingPtr->ConnectIpv4Count; *vecptr++ = PercentCountIpv4; *vecptr++ = ProxyAccountingPtr->ConnectIpv6Count; *vecptr++ = PercentCountIpv6; *vecptr++ = ProxyAccountingPtr->Socks5Count; *vecptr++ = ProxyAccountingPtr->Socks5SuccessCount; *vecptr++ = ProxyAccountingPtr->Socks5FailCount; *vecptr++ = AccountingPtr->LookupLiteralCount; *vecptr++ = AccountingPtr->LookupDnsNameCount; *vecptr++ = PercentDnsName; *vecptr++ = AccountingPtr->LookupCacheNameCount; *vecptr++ = AccountingPtr->LookupDnsNameErrorCount; InstanceMutexUnLock (INSTANCE_MUTEX_HTTPD); *vecptr++ = AdminRefresh (rqptr); status = FaolToNet (rqptr, ResponseFao, &FaoVector); if (VMSnok (status)) ErrorNoticed (rqptr, status, NULL, FI_LI); return (status); } /*****************************************************************************/ /* Return a report on proxy special functionality. */ int ProxyMaintFunctionReport (REQUEST_STRUCT *rqptr) { static char ResponseFao [] = "

\n\ \n\ \n\
Function!AZ
\n\ \n\ \ \ \n\ \ \n\ \ \n\ \ \ \n\ \ \n\
\n\ \ \n\ \n\ \ \ \ \n\ \ \ \ \ \n\ \ \ \ \ \n\ \ \ \ \ \n\ \ \ \ \ \n\ \ \ \ \ \n\
Gateway
Out \\ In:HTTPHTTPS
HTTP!&L!&L
HTTPS!&L!&L
Out \\ In:IPv4IPv6
IPv4!&L!&L
IPv6!&L!&L
\n\
\n\ \n\ \n\ \ \ \ \ \n\ \ \ \ \ \ \n\ \ \ \ \ \ \n\ \ \ \ \ \ \n\ \ \ \ \ \ \n\ \n\ \n\
Tunnel
Out \\ In:CONNECTFirewallRaw
CONNECT!&L!&L!&L
HTTP!&L!&L!&L
HTTPS!&L!&L!&L
Raw!&L!&L!&L
Current:!&L  \ Report\n\
\n\
\n\ \n\ \n\ \n\ \n\ \n\ \n\ \n\ \n\ \n\ \n\
Verify
Max:!&LFull:!&L
Current:!&L200:!&L
Set:!&L403:!&L
Find:!&L404:!&L
\n\
\n\ \n\ \n\ \n\ \n\ \n\ \n\ \n\
Rework
Count:!&L
No Type:!&L
Search:!&L
Replace:!&L
Too Big:!&L
\n\ \
\n\
\n"; int in, out, status; unsigned short Length; unsigned long FaoVector [64]; unsigned long *vecptr; char Buffer [2048]; $DESCRIPTOR (BufferDsc, Buffer); /*********/ /* begin */ /*********/ if (WATCHMOD (rqptr, WATCH_MOD_PROXY)) WatchThis (WATCHITM(rqptr), WATCH_MOD_PROXY, "ProxyMaintFunctionReport()"); InstanceMutexLock (INSTANCE_MUTEX_HTTPD); vecptr = FaoVector; if (ProxyServingEnabled) *vecptr++ = ""; else *vecptr++ = " ... DISABLED"; /* [http=0,https=1][http=0,https=1] */ *vecptr++ = ProxyAccountingPtr->GatewaySchemeCount[0][0]; *vecptr++ = ProxyAccountingPtr->GatewaySchemeCount[1][0]; *vecptr++ = ProxyAccountingPtr->GatewaySchemeCount[0][1]; *vecptr++ = ProxyAccountingPtr->GatewaySchemeCount[1][1]; /* [ipv4=0,ipv6=1][ipv4=0,ipv6=1] */ *vecptr++ = ProxyAccountingPtr->GatewayIpvCount[0][0]; *vecptr++ = ProxyAccountingPtr->GatewayIpvCount[1][0]; *vecptr++ = ProxyAccountingPtr->GatewayIpvCount[0][1]; *vecptr++ = ProxyAccountingPtr->GatewayIpvCount[1][1]; for (out = 0; out < TUNNEL_COUNT_MAX; out++) { if (out+1 == PROXY_TUNNEL_FIREWALL) continue; for (in = 0; in < TUNNEL_COUNT_MAX; in++) { if (in+1 == PROXY_TUNNEL_HTTP || in+1 == PROXY_TUNNEL_HTTPS) continue; *vecptr++ = ProxyAccountingPtr->TunnelCount[in][out]; } } *vecptr++ = ProxyAccountingPtr->TunnelCurrent; if (SysTrnLnm ("WASD_TUNNEL")) *vecptr++ = ""; else *vecptr++ = " dbttn"; *vecptr++ = ADMIN_REPORT_PROXY_TUNNEL; *vecptr++ = ProxyVerifyRecordMax; *vecptr++ = ProxyAccountingPtr->VerifyFullCount; *vecptr++ = ProxyAccountingPtr->VerifyCurrentCount; *vecptr++ = ProxyAccountingPtr->Verify200Count; *vecptr++ = ProxyAccountingPtr->VerifySetRecordCount; *vecptr++ = ProxyAccountingPtr->Verify403Count; *vecptr++ = ProxyAccountingPtr->VerifyFindRecordCount; *vecptr++ = ProxyAccountingPtr->Verify404Count; *vecptr++ = ProxyAccountingPtr->ReworkCount; *vecptr++ = ProxyAccountingPtr->ReworkNoType; *vecptr++ = ProxyAccountingPtr->ReworkReplaceSearch; *vecptr++ = ProxyAccountingPtr->ReworkReplaceCount; *vecptr++ = ProxyAccountingPtr->ReworkTooBig; InstanceMutexUnLock (INSTANCE_MUTEX_HTTPD); status = FaolToNet (rqptr, ResponseFao, &FaoVector); if (VMSnok (status)) ErrorNoticed (rqptr, status, NULL, FI_LI); return (status); } /****************************************************************************/