bool DirItem::isDenied(const char *path) { if (m_bIncludeSub) return (strncmp(m_sPath.c_str(), path, m_sPath.len()) == 0); else return (strcmp(m_sPath.c_str(), path) == 0); }
int LshttpdMain::startAdminSocket() { int i; char achBuf[1024]; AutoStr2 *pProcChroot = ServerProcessConfig::getInstance().getChroot(); if (m_fdAdmin != -1) return 0; srand(time(NULL)); for (i = 0; i < 100; ++i) { snprintf(achBuf, 132, "uds:/%s%sadmin/tmp/admin.sock.%d", (pProcChroot != NULL) ? pProcChroot->c_str() : "", MainServerConfig::getInstance().getServerRoot(), 7000 + rand() % 1000); //snprintf(achBuf, 255, "127.0.0.1:%d", 7000 + rand() % 1000 ); if (CoreSocket::listen(achBuf, 10, &m_fdAdmin, 0 , 0) == 0) break; if (!(i % 20)) { snprintf(achBuf, 1024, "rm -rf '%s%sadmin/tmp/admin.sock.*'", (pProcChroot != NULL) ? pProcChroot->c_str() : "", MainServerConfig::getInstance().getServerRoot()); system(achBuf); } } if (i == 100) return LS_FAIL; ::fcntl(m_fdAdmin, F_SETFD, FD_CLOEXEC); HttpServerConfig::getInstance().setAdminSock(strdup(achBuf)); LS_NOTICE("[ADMIN] server socket: %s", achBuf); return 0; }
int SslOcspStapling::certVerify(OCSP_RESPONSE *pResponse, OCSP_BASICRESP *pBasicResp, X509_STORE *pXstore) { int n, iResult = -1; STACK_OF(X509) *pXchain; ASN1_GENERALIZEDTIME *pThisupdate, *pNextupdate; struct stat st; pXchain = m_pCtx->extra_certs; if (OCSP_basic_verify(pBasicResp, pXchain, pXstore, OCSP_NOVERIFY) == 1) { if ((m_pCertId != NULL) && (OCSP_resp_find_status(pBasicResp, m_pCertId, &n, NULL, NULL, &pThisupdate, &pNextupdate) == 1) && (n == V_OCSP_CERTSTATUS_GOOD) && (OCSP_check_validity(pThisupdate, pNextupdate, 300, -1) == 1)) { iResult = 0; updateRespData(pResponse); unlink(m_sRespfile.c_str()); rename(m_sRespfileTmp.c_str(), m_sRespfile.c_str()); if (::stat(m_sRespfile.c_str(), &st) == 0) m_RespTime = st.st_mtime; } } if (iResult) { setLastErrMsg("%s", SSLError().what()); ERR_clear_error(); if (m_pHttpFetch) m_pHttpFetch->writeLog(s_ErrMsg.c_str()); } return iResult; }
void plainconf::appendModuleParam(XmlNode *pModuleNode, const char *param) { XmlNode *pParamNode = pModuleNode->getChild("param"); if (pParamNode == NULL) { pParamNode = new XmlNode; const char *attr = NULL; pParamNode->init("param", &attr); pParamNode->setValue(param, strlen(param)); pModuleNode->addChild(pParamNode->getName(), pParamNode); } else { AutoStr2 totalValue = pParamNode->getValue(); totalValue.append("\n", 1); totalValue.append(param, strlen(param)); pParamNode->setValue(totalValue.c_str(), totalValue.len()); } logToMem(LOG_LEVEL_INFO, "[%s:%s] module [%s] add param [%s]", pModuleNode->getParent()->getName(), ((pModuleNode->getParent()->getValue()) ? pModuleNode->getParent()->getValue() : ""), pModuleNode->getValue(), param); }
int LshttpdMain::getFullPath(const char *pRelativePath, char *pBuf, int bufLen) { AutoStr2 *pProcChroot = ServerProcessConfig::getInstance().getChroot(); return ls_snprintf(pBuf, bufLen, "%s%s%s", (pProcChroot != NULL) ? pProcChroot->c_str() : "", MainServerConfig::getInstance().getServerRoot(), pRelativePath); }
//When checking we use lock for may need to update the conf file later //If user RCS checkout a revision, a unlock should be used for next time checkin. //Example: co -u1.1 httpd_config.conf void plainconf::checkInFile(const char *path) { if (access(path, 0) == -1) return ; //Backup file abd checkin and out char new_path[4096]; strcpy(new_path, path); strcat(new_path, "0"); AutoStr2 buf; buf.setStr("cp \""); buf.append(path, strlen(path)); buf.append("\" \"", 3); buf.append(new_path, strlen(new_path)); buf.append("\"", 1); int ret = system(buf.c_str()); if (ret != 0) { logToMem(LOG_LEVEL_INFO, "Failed to backup the conf file %s, ret %d.", path, ret); return ; } buf.setStr("ci -l -q -t-\""); buf.append(new_path, strlen(new_path)); buf.append("\" -mUpdate \"", 12); buf.append(new_path, strlen(new_path)); buf.append("\" >/dev/null 2>&1", 17); ret = system(buf.c_str()); if (ret == 0) logToMem(LOG_LEVEL_INFO, "RCS checkin config file %s OK.", new_path); else logToMem(LOG_LEVEL_INFO, "Failed to RCS checkin conf file %s, ret %d, error(%s). " "Org command is %s.", new_path, ret, strerror(errno), buf.c_str()); unlink(new_path); }
MimeSetting *MIMESubMap::addMIME(char *pMIME) { const char *p = strchr(pMIME, '/'); if (!p) return NULL; ++p; if (!*p) return NULL; AutoStr2 *pStr = ::getMIME(pMIME); if (!pStr) return NULL; p = pStr->c_str() + (p - pMIME); MimeSetting *pSetting = new MimeSetting(); if (!pSetting) return NULL; pSetting->setMIME(pStr); if (strncasecmp(pStr->c_str(), "image/", 6) == 0) pSetting->getExpires()->setBit(CONFIG_IMAGE); insert(p, pSetting); return pSetting; }
int RewriteEngine::appendUnparsedRule( AutoStr2 & sDirective, char * pBegin, char * pEnd ) { if ( m_qsLen + sDirective.len() + (pEnd - pBegin ) + 2 > REWRITE_BUF_SIZE * 4 ) return -1; char * pBuf = m_rewriteBuf[0]; memmove( &pBuf[m_qsLen], sDirective.c_str(), sDirective.len() ); m_qsLen += sDirective.len(); pBuf[m_qsLen++] = ' '; memmove( &pBuf[m_qsLen], pBegin, pEnd - pBegin ); m_qsLen += pEnd - pBegin; pBuf[m_qsLen++] = '\n'; pBuf[m_qsLen] = 0; return 0; }
int StaticFileCacheData::build( const AutoStr2 &path, const struct stat& fileStat , int etag) { m_fileData.setFileStat( fileStat ); char * pReal = m_real.resizeBuf( path.len() + 6 ); if ( !pReal ) return -1; strcpy( pReal, path.c_str() ); m_real.setLen( path.len() ); memmove( pReal + path.len() + 1, "lsz\0\0", 5 ); //int ret = buildFixedHeaders(); int ret = buildFixedHeaders(etag); if ( ret ) return ret; ret = m_fileData.buildCLHeader( false ); return ret; }
static inline LsShmHash *LsLuaShmOpen(const char *name) { AutoStr2 *pName; LsShmHash *pRet; LsShm *pShm = LsShm::open(name, 0, NULL); if (pShm == NULL) return NULL; LsShmPool *pPool = pShm->getGlobalPool(); if (pPool == NULL) return NULL; pName = new AutoStr2(name); pName->append("hash", 4); pRet = pPool->getNamedHash(pName->c_str(), LSSHM_HASHINITSIZE, LsShmHash::hashString, LsShmHash::compString, LSSHM_FLAG_NONE); delete pName; return pRet; }
//name: form like "moduleName|submodlue|itemname" const char *plainconf::getConfDeepValue(const XmlNode *pNode, const char *name) { const char *p = strchr(name, '|'); if (!p) return pNode->getChildValue(name); else { AutoStr2 subName; subName.setStr(name, p - name); const XmlNode *subNode = pNode->getChild(subName.c_str()); if (subNode) return getConfDeepValue(subNode, p + 1); else return NULL; } }
int SslOcspStapling::processResponse(HttpFetch *pHttpFetch) { struct stat st; const char *pRespContentType; //assert( pHttpFetch == m_pHttpFetch ); int istatusCode = m_pHttpFetch->getStatusCode() ; pRespContentType = m_pHttpFetch->getRespContentType(); if ((istatusCode == 200) && (strcasecmp(pRespContentType, "application/ocsp-response") == 0)) verifyRespFile(); else { setLastErrMsg("Received bad OCSP response. ReponderUrl=%s, StatusCode=%d, ContentType=%s\n", m_sOcspResponder.c_str(), istatusCode, ((pRespContentType) ? (pRespContentType) : (""))); //printf("%s\n", s_ErrMsg.c_str()); m_pHttpFetch->writeLog(s_ErrMsg.c_str()); } if (::stat(m_sRespfileTmp.c_str(), &st) == 0) unlink(m_sRespfileTmp.c_str()); return 0; }
const char *MIMESubMap::setMainType(const char *pType, int len) { m_sMainType.setStr(pType, len); return m_sMainType.c_str(); }
const char *getMainType() const { return m_sMainType.c_str(); }
const char *getStaplingErrMsg() { return s_ErrMsg.c_str(); }
int HttpCgiTool::processHeaderLine(HttpExtConnector *pExtConn, const char *pLineBegin, const char *pLineEnd, int &status) { HttpRespHeaders::HEADERINDEX index; int tmpIndex; const char *pKeyEnd = NULL; const char *pValue = pLineBegin; char *p; HttpResp *pResp = pExtConn->getHttpSession()->getResp(); HttpReq *pReq = pExtConn->getHttpSession()->getReq(); index = HttpRespHeaders::getRespHeaderIndex(pValue); if (index < HttpRespHeaders::H_HEADER_END) { pValue += HttpRespHeaders::getHeaderStringLen(index); while (isspace(*pValue)) ++pValue; pKeyEnd = pValue; if (*pValue != ':') index = HttpRespHeaders::H_HEADER_END; else { do { ++pValue; } while (isspace(*pValue)); } } if (index == HttpRespHeaders::H_HEADER_END) { pKeyEnd = (char *)memchr(pValue, ':', pLineEnd - pValue); if (pKeyEnd != NULL) { pValue = pKeyEnd + 1; while (isspace(*pValue)) ++pValue; } else { if (!isspace(*pLineBegin)) return 0; } } switch (index) { case HttpRespHeaders::H_CONTENT_TYPE: if (pReq->getStatusCode() == SC_304) return 0; p = (char *)memchr(pValue, ';', pLineEnd - pValue); if (pReq->gzipAcceptable() == GZIP_REQUIRED) { char ch = 0; char *p1; if (p) p1 = (char *)p; else p1 = (char *)pLineEnd; ch = *p1; *p1 = 0; if (!HttpMime::getMime()->compressible(pValue)) pReq->andGzip(~GZIP_ENABLED); *p1 = ch; } if (pReq->isKeepAlive()) pReq->smartKeepAlive(pValue); { if (!HttpMime::needCharset(pValue)) break; const AutoStr2 *pCharset = pReq->getDefaultCharset(); if (!pCharset) break; if (p) { while (isspace(*(++p))) ; if (strncmp(p, "charset=", 8) == 0) break; } HttpRespHeaders &buf = pResp->getRespHeaders(); AutoStr2 str = ""; str.append(pLineBegin, pLineEnd - pLineBegin); str.append(pCharset->c_str(), pCharset->len()); str.append("\r\n", 2); buf.parseAdd(str.c_str(), str.len(), LSI_HEADEROP_ADD); } return 0; case HttpRespHeaders::H_CONTENT_ENCODING: if (pReq->getStatusCode() == SC_304) return 0; if (strncasecmp(pValue, "gzip", 4) == 0) pReq->orGzip(UPSTREAM_GZIP); else if (strncasecmp(pValue, "deflate", 7) == 0) pReq->orGzip(UPSTREAM_DEFLATE); // if ( !(pReq->gzipAcceptable() & REQ_GZIP_ACCEPT) ) // return 0; // } // else //if ( strncasecmp( pValue, "deflate", 7 ) == 0 ) // { // pReq->andGzip( ~GZIP_ENABLED ); // } break; case HttpRespHeaders::H_LOCATION: if ((status & HEC_RESP_PROXY) || (pReq->getStatusCode() != SC_200)) break; case HttpRespHeaders::H_LITESPEED_LOCATION: if (*pValue != '/') { //set status code to 307 pReq->setStatusCode(SC_302); } else { if ((pReq->getStatusCode() == SC_404) || (index == HttpRespHeaders::H_LITESPEED_LOCATION)) pReq->setStatusCode(SC_200); if (index == HttpRespHeaders::H_LITESPEED_LOCATION) { char ch = *pLineEnd; *((char *)pLineEnd) = 0; pReq->locationToUrl(pValue, pLineEnd - pValue); *((char *)pLineEnd) = ch; } else pReq->setLocation(pValue, pLineEnd - pValue); pExtConn->getHttpSession()->changeHandler(); //status |= HEC_RESP_LOC_SET; return 0; } break; case HttpRespHeaders::H_CGI_STATUS: tmpIndex = HttpStatusCode::getInstance().codeToIndex(pValue); if (tmpIndex != -1) { pReq->updateNoRespBodyByStatus(tmpIndex); if ((tmpIndex >= SC_300) && (tmpIndex < SC_400)) { if (pReq->getLocation() != NULL) { pResp->appendHeader("location: ", 10, pReq->getLocation(), pReq->getLocationLen()); pReq->clearLocation(); } } if ((status & HEC_RESP_AUTHORIZER) && (tmpIndex == SC_200)) status |= HEC_RESP_AUTHORIZED; } return 0; case HttpRespHeaders::H_TRANSFER_ENCODING: pResp->setContentLen(LSI_RSP_BODY_SIZE_CHUNKED); return 0; case HttpRespHeaders::H_SET_COOKIE: //pReq->getRespCacheCtrl().setHasCookie(); pReq->processSetCookieHeader(pValue, pLineEnd - pValue); break; case HttpRespHeaders::H_PROXY_CONNECTION: case HttpRespHeaders::H_CONNECTION: if (strncasecmp(pValue, "close", 5) == 0) status |= HEC_RESP_CONN_CLOSE; return 0; case HttpRespHeaders::H_CONTENT_LENGTH: if (pResp->getContentLen() == LSI_RSP_BODY_SIZE_UNKNOWN) { off_t lContentLen = strtoll(pValue, NULL, 10); if ((lContentLen >= 0) && (lContentLen != LLONG_MAX)) { pResp->setContentLen(lContentLen); status |= HEC_RESP_CONT_LEN; pReq->orContextState(RESP_CONT_LEN_SET); } } //fall through case HttpRespHeaders::H_KEEP_ALIVE: case HttpRespHeaders::H_SERVER: case HttpRespHeaders::H_DATE: return 0; default: //"script-control: no-abort" is not supported break; } if (status & HEC_RESP_AUTHORIZED) { if (strncasecmp(pLineBegin, "Variable-", 9) == 0) { if (pKeyEnd > pLineBegin + 9) RequestVars::setEnv(pExtConn->getHttpSession(), pLineBegin + 9, pKeyEnd - pLineBegin - 9, pValue, pLineEnd - pValue); } return 0; } assert(pKeyEnd); return pResp->appendHeader(pLineBegin, pKeyEnd - pLineBegin, pValue, pLineEnd - pValue); }
//This function may be recruse called void plainconf::loadConfFile(const char *path) { logToMem(LOG_LEVEL_INFO, "start parsing file %s", path); int type = checkFiletype(path); if (type == 0) return; else if (type == 2) loadDirectory(path, NULL); else if (type == 3) { AutoStr2 prefixPath = path; const char *p = strrchr(path, '/'); if (p) prefixPath.setStr(path, p - path); struct stat sb; //removed the wildchar filename, should be a directory if exist if (stat(prefixPath.c_str(), &sb) == -1) { logToMem(LOG_LEVEL_ERR, "LoadConfFile error 1, path:%s directory:%s", path, prefixPath.c_str()); return ; } if ((sb.st_mode & S_IFMT) != S_IFDIR) { logToMem(LOG_LEVEL_ERR, "LoadConfFile error 2, path:%s directory:%s", path, prefixPath.c_str()); return ; } loadDirectory(prefixPath.c_str(), p + 1); } else //existed file { //gModuleList.push_back(); //XmlNode *xmlNode = new XmlNode; FILE *fp = fopen(path, "r"); if (fp == NULL) { logToMem(LOG_LEVEL_ERR, "Cannot open configuration file: %s", path); return; } const int MAX_LINE_LENGTH = 8192; char sLine[MAX_LINE_LENGTH]; char *p; char sLines[MAX_LINE_LENGTH] = {0}; int lineNumber = 0; const int MAX_MULLINE_SIGN_LENGTH = 128; char sMultiLineModeSign[MAX_MULLINE_SIGN_LENGTH] = {0}; size_t nMultiLineModeSignLen = 0; //>0 is mulline mode while (fgets(sLine, MAX_LINE_LENGTH, fp), !feof(fp)) { ++lineNumber; p = sLine; if (nMultiLineModeSignLen) { //Check if reach the END of the milline mode size_t len = 0; const char *pLineStart = getStrNoSpace(p, len); if (len == nMultiLineModeSignLen && strncasecmp(pLineStart, sMultiLineModeSign, nMultiLineModeSignLen) == 0) { nMultiLineModeSignLen = 0; removeSpace(sLines, 1); //Remove the last \r\n so that if it is one line, it will still be one line parseLine(path, lineNumber, sLines); sLines[0] = 0x00; } else strcat(sLines, p); continue; } removeSpace(p, 0); removeSpace(p, 1); if (!isValidline(p)) continue; AutoStr2 pathInclude; if (isInclude(p, pathInclude)) { char achBuf[512] = {0}; getIncludeFile(pathInclude.c_str(), achBuf); loadConfFile(achBuf); } else { nMultiLineModeSignLen = checkMultiLineMode(p, sMultiLineModeSign, MAX_MULLINE_SIGN_LENGTH); if (nMultiLineModeSignLen > 0) strncat(sLines, p, strlen(p) - (3 + nMultiLineModeSignLen)); //need to continue else if (isChunkedLine(p)) { strncat(sLines, p, strlen(p) - 1); //strcatchr(sLines, ' ', MAX_LINE_LENGTH); //add a space at the end of the line which has a '\\' } else { strcat(sLines, p); parseLine(path, lineNumber, sLines); sLines[0] = 0x00; } } } fclose(fp); //Parsed, check in it checkInFile(path); } }