void type_free(type *t) { type *tn; tym_t ty; while (t) { //dbg_printf("type_free(%p, Tcount = %d)\n", t, t->Tcount); type_debug(t); assert((int)t->Tcount != -1); if (--t->Tcount) /* if usage count doesn't go to 0 */ break; ty = tybasic(t->Tty); if (tyfunc(ty)) { param_free(&t->Tparamtypes); list_free(&t->Texcspec, (list_free_fp)type_free); } #if SCPP else if (ty == TYtemplate) param_free(&t->Tparamtypes); else if (ty == TYident) MEM_PH_FREE(t->Tident); #endif else if (t->Tflags & TFvla && t->Tel) el_free(t->Tel); #if SCPP else if (t->Talternate && typtr(ty)) type_free(t->Talternate); #endif #if MARS else if (t->Tkey && typtr(ty)) type_free(t->Tkey); #endif #ifdef DEBUG type_num--; //dbg_printf("Free'ing type %p ",t); WRTYxx(t->Tty); dbg_printf("\n"); t->id = 0; /* no longer a valid type */ #endif tn = t->Tnext; t->Tnext = type_list; type_list = t; /* link into free list */ t = tn; } }
void type_free(struct type **tp) { if (!tp || !(*tp)) { return; } struct type *t = *tp; param_free(&t->params); type_free(&t->rtype); free(t); *tp = 0; }
void param_free(struct param **pp) { if (!pp || !(*pp)) { return; } struct param *p = *pp; free(p->name); type_free(&p->type); param_free(&p->next); free(p); *pp = 0; }
/** * This function is used for sending a 302 redirect in the browser. */ static void do_url_redirect(Session *sn, Request *rq, char* redirect_url) { /* Set the return code to 302 Redirect */ protocol_status(sn, rq, PROTOCOL_REDIRECT, NULL); /* set the new URL to redirect */ pblock_nvinsert("escape", "no", rq->vars); param_free(pblock_remove("Location", rq->srvhdrs)); pblock_nvinsert("Location", redirect_url, rq->srvhdrs); protocol_start_response(sn, rq); }
char * get_post_assertion_data(Session *sn, Request *rq, char *url) { int i = 0; char *body = NULL; int cl = 0; char *cl_str = NULL; /** * content length and body * * note: memory allocated in here should be released by * other function such as: "policy_unregister_post" */ request_header("content-length", &cl_str, sn, rq); if(cl_str == NULL) cl_str = pblock_findval("content-length", rq->headers); if(cl_str == NULL) return body; if(PR_sscanf(cl_str, "%ld", &cl) == 1) { body = (char *)malloc(cl + 1); if(body != NULL){ for (i = 0; i < cl; i++) { int ch = netbuf_getc(sn->inbuf); if (ch==IO_ERROR || ch == IO_EOF) { break; } body[i] = ch; } body[i] = '\0'; } } else { am_web_log_error("Error reading POST content body"); } am_web_log_max_debug("Read POST content body : %s", body); /** * need to reset content length before redirect, * otherwise, web server will wait for serveral minutes * for non existant data */ param_free(pblock_remove("content-length", rq->headers)); pblock_nvinsert("content-length", "0", rq->headers); return body; }
/* * Function: pg_exec * * Wrapper for PQexecParams. Only supports text parameters as binary parameters * are not possible in Zabbix item keys. * * Returns: PGresult */ PGresult *pg_exec(PGconn *conn, const char *command, PGparams params) { PGresult *res = NULL; int i = 0, nparams = 0; // count parameters nparams = param_len(params); // log the query zabbix_log(LOG_LEVEL_DEBUG, "Executing query with %i parameters: %s", nparams, command); for (i = 0; i < nparams; i++) zabbix_log(LOG_LEVEL_DEBUG, " $%i: %s", i, params[i]); // execute query with escaped parameters res = PQexecParams(conn, command, nparams, NULL, params, NULL, NULL, 0); //free up the params array which would have been alloc'ed for this request param_free(params); return res; }
static int sed_response_insert(FilterLayer *layer, pblock *pb) { SedData *seddata = (SedData *)layer->context->data; if (!seddata) { seddata = init_sed_data(pb, layer->context->sn, layer->context->rq, layer->context->pool, SED_RESPONSE); if (!seddata) return REQ_ABORTED; layer->context->data = seddata; } // We modify the response entity body length param_free(pblock_removekey(pb_key_content_length, layer->context->rq->srvhdrs)); // sed splits the input into separate lines, so enable buffering to // reduce system call overhead httpfilter_buffer_output(layer->context->sn, layer->context->rq, PR_TRUE); return REQ_PROCEED; }
int service_reconfig(pblock *pb, Session *sn, Request *rq) { param_free(pblock_remove("content-type", rq->srvhdrs)); pblock_nvinsert("content-type", "text/html", rq->srvhdrs); protocol_status(sn, rq, PROTOCOL_OK, NULL); protocol_start_response(sn, rq); PR_fprintf(sn->csd, "<html><head><title>" "Dynamic Reconfiguration" "</title></head><body>\n" "<H2>Dynamic Reconfiguration</H2>\n" "<p>pid: %d</p>\n", getpid()); // Asynchronous reconfiguration WebServer::RequestReconfiguration(); PR_fprintf(sn->csd, "</body></html>"); return REQ_PROCEED; }
int service_dumpstats(pblock *pb, Session *sn, Request *rq) { char *refresh, *refresh_val = NULL; /* See if client asked for automatic refresh in query string */ if ((refresh = pblock_findval("query", rq->reqpb)) != NULL ) { if (!strncmp("refresh", refresh, 7)) { refresh_val = strchr(refresh, '='); if (refresh_val) refresh_val++; } } param_free(pblock_remove("content-type", rq->srvhdrs)); pblock_nvinsert("content-type", "text/plain", rq->srvhdrs); if (refresh_val) pblock_nvinsert("refresh", refresh_val, rq->srvhdrs); httpfilter_buffer_output(sn, rq, PR_TRUE); protocol_status(sn, rq, PROTOCOL_OK, NULL); protocol_start_response(sn,rq); PR_fprintf(sn->csd, PRODUCT_DAEMON_BIN" pid: %d\n", getpid()); StatsHeaderNode *hdr = StatsManager::getHeader(); if (!hdr) { PR_fprintf(sn->csd, "\nStatistics disabled\n"); return REQ_PROCEED; } int rv = REQ_PROCEED; #ifdef XP_WIN32 rv = write_stats_dump(sn->csd, hdr); #else if (hdr && (hdr->hdrStats.maxProcs == 1)) { rv = write_stats_dump(sn->csd, hdr); } else { StatsManager::serviceDumpStats(sn->csd, NULL); } #endif return rv; }
NSAPI_PUBLIC PRBool conf_setGlobal(char *name, char *value) { pblock *globals = conf_get_true_globals()->genericGlobals; char *d = _lowercase(name); if (pblock_find(d, globals)) { // Mark directive as multiply defined pblock_nvinsert(d, name, globalsMultiplyDefined); param_free(pblock_remove(d, globals)); } else { // Mark directive as unaccessed pblock_nvinsert(d, name, globalsUnaccessed); } PRBool rv = (pblock_nvinsert(d, value, globals) != NULL); FREE(d); return rv; }
NSAPI_PUBLIC char *conf_findGlobal(char *name) { if (!conf_api_initialized) { log_ereport(LOG_VERBOSE, XP_GetAdminStr(DBT_confApiCallBeforeInit)); return NULL; } char *rv = NULL; char *d = _lowercase(name); if (d) { // Mark directive as accessed if (globalsUnaccessed) param_free(pblock_remove(d, globalsUnaccessed)); // Lookup directive rv = pblock_findval(d, conf_get_true_globals()->genericGlobals); FREE(d); } return rv; }
void param_free(param_t **pparamlst) { param_t *p,*pn; #if !TX86 debug_assert(PARSER); #endif for (p = *pparamlst; p; p = pn) { param_debug(p); pn = p->Pnext; type_free(p->Ptype); mem_free(p->Pident); el_free(p->Pelem); type_free(p->Pdeftype); if (p->Pptpl) param_free(&p->Pptpl); #ifdef DEBUG p->id = 0; #endif p->Pnext = param_list; param_list = p; } *pparamlst = NULL; }
PRStatus FcgiParser::parseHttpHeader(CircularBuffer& to) { if(!waitingForDataParse) return PR_SUCCESS; const char *data = httpHeader.data(); int len = httpHeader.length(); PRUint8 flag = 0; while(len-- && flag < 2) { switch(*data) { case '\r': break; case '\n': flag++; break; default: flag = 0; break; } data++; } /* * Return (to be called later when we have more data) */ if(flag < 2) return PR_SUCCESS; waitingForDataParse = PR_FALSE; Request *rq = request->getOrigRequest(); pblock *authpb = NULL; if(fcgiRole == FCGI_AUTHORIZER) { authpb = pblock_create(rq->srvhdrs->hsize); } register int x ,y; register char c; int nh; char t[REQ_MAX_LINE]; PRBool headerEnd = PR_FALSE; char* statusHeader = pblock_findval("status", rq->srvhdrs); char *next = const_cast<char *>(httpHeader.data()); nh = 0; x = 0; y = -1; for(; !headerEnd;) { c = *(next++); switch(c) { case CR: // Silently ignore CRs break; case LF: if (x == 0) { headerEnd = PR_TRUE; break; } t[x] = '\0'; if(y == -1) { request->log(LOG_FAILURE, "name without value: got line \"%s\"", t); return PR_FAILURE; } while(t[y] && isspace(t[y])) ++y; // Do not change the status header to 200 if it was already set // This would happen only if it were a cgi error handler // and so the status had been already set on the request // originally if (!statusHeader || // If we don't already have a Status: header PL_strcmp(t, "status") || // or this isn't a Status: header PL_strncmp(&t[y], "200", 3)) // or this isn't "Status: 200" { if(!PL_strcmp(t, "content-type")) { pb_param* pParam = pblock_remove ( "content-type", rq->srvhdrs ); if ( pParam ) param_free ( pParam ); } if(fcgiRole == FCGI_AUTHORIZER) { pblock_nvinsert(t, &t[y], authpb); } else { pblock_nvinsert(t, &t[y], rq->srvhdrs); } // !FCGI_AUTHORIZER } x = 0; y = -1; ++nh; break; case ':': if(y == -1) { y = x+1; c = '\0'; } default: t[x++] = ((y == -1) && isupper(c) ? tolower(c) : c); } } // for if(fcgiRole == FCGI_AUTHORIZER) { if(parseAuthHeaders(authpb) != PR_SUCCESS) { pblock_free(authpb); return PR_FAILURE; } pblock_copy(authpb, rq->srvhdrs); pblock_free(authpb); } else { /* * We're done scanning the FCGI script's header output. Now * we have to write to the client: status, FCGI header, and * any over-read FCGI output. */ char *s; char *l = pblock_findval("location", rq->srvhdrs); if((s = pblock_findval("status", rq->srvhdrs))) { if((strlen(s) < 3) || (!isdigit(s[0]) || (!isdigit(s[1])) || (!isdigit(s[2])))) { s = NULL; } else { char ch = s[3]; s[3] = '\0'; int statusNum = atoi(s); s[3] = ch; rq->status_num = statusNum; } } if(!s) { if (l) pblock_nvinsert("url", l, rq->vars); protocol_status(request->getOrigSession(), request->getOrigRequest(), (l ? PROTOCOL_REDIRECT : PROTOCOL_OK), NULL); } } len = next - httpHeader.data(); len = httpHeader.length() - len; if(len < 0) return PR_FAILURE; /* * Only send the body for methods other than HEAD. */ if(!request->isHead()) { if(len > 0) { if(to.addData(next, len) != len) return PR_FAILURE; } } next = NULL; return PR_SUCCESS; }
/* * Function Name: validate_session_policy * This is the NSAPI directive funtion which gets called for each request * It does session validation and policy check for each request. * Input: As defined by a SAF * Output: As defined by a SAF */ NSAPI_PUBLIC int validate_session_policy(pblock *param, Session *sn, Request *rq) { const char *thisfunc = "validate_session_policy()"; char *dpro_cookie = NULL; am_status_t status = AM_SUCCESS; int requestResult = REQ_ABORTED; int notifResult = REQ_ABORTED; const char *ruser = NULL; am_map_t env_parameter_map = NULL; am_policy_result_t result = AM_POLICY_RESULT_INITIALIZER; void *args[] = { (void *)rq }; char *request_url = NULL; char *orig_req = NULL ; char *response = NULL; char *clf_req = NULL; char *server_protocol = NULL; void *agent_config = NULL; char *logout_url = NULL; char *uri_hdr = NULL; char *pathInfo_hdr = NULL; char *method_hdr = NULL; char *method = NULL; char *virtHost_hdr = NULL; char *query_hdr = NULL; char *query = NULL; char *protocol = "HTTP"; const char *clientIP_hdr_name = NULL; char *clientIP_hdr = NULL; char *clientIP = NULL; const char *clientHostname_hdr_name = NULL; char *clientHostname_hdr = NULL; char *clientHostname = NULL; am_status_t cdStatus = AM_FAILURE; // check if agent is initialized. // if not initialized, then call agent init function // This needs to be synchronized as only one time agent // initialization needs to be done. if(agentInitialized != B_TRUE){ //Start critical section crit_enter(initLock); if(agentInitialized != B_TRUE){ am_web_log_debug("%s: Will call init.", thisfunc); init_at_request(); if(agentInitialized != B_TRUE){ am_web_log_error("%s: Agent is still not intialized", thisfunc); //deny the access requestResult = do_deny(sn, rq, status); status = AM_FAILURE; } else { am_web_log_debug("%s: Agent intialized"); } } //end critical section crit_exit(initLock); } if (status == AM_SUCCESS) { // Get the agent configuration agent_config = am_web_get_agent_configuration(); // Dump the entire set of request headers if (am_web_is_max_debug_on()) { char *header_str = pblock_pblock2str(rq->reqpb, NULL); am_web_log_max_debug("%s: Headers: %s", thisfunc, header_str); system_free(header_str); } } // Get header values if (status == AM_SUCCESS) { status = get_header_value(rq->reqpb, REQUEST_URI, B_TRUE, &uri_hdr, B_FALSE, NULL); } if (status == AM_SUCCESS) { status = get_header_value(rq->vars, PATH_INFO, B_FALSE, &pathInfo_hdr, B_FALSE, NULL); } if (status == AM_SUCCESS) { status = get_header_value(rq->reqpb, REQUEST_METHOD, B_TRUE, &method_hdr, B_TRUE, &method); } if (status == AM_SUCCESS) { status = get_header_value(rq->headers, "ampxy_host", B_TRUE, &virtHost_hdr, B_FALSE, NULL); } if (status == AM_SUCCESS) { status = get_header_value(rq->reqpb, REQUEST_QUERY, B_FALSE, &query_hdr, B_TRUE, &query); } if (security_active) { protocol = "HTTPS"; } // Get the request URL if (status == AM_SUCCESS) { if (am_web_is_proxy_override_host_port_set(agent_config) == AM_FALSE) { status = am_web_get_request_url(virtHost_hdr, protocol, NULL, 0, uri_hdr, query, &request_url, agent_config); if(status == AM_SUCCESS) { am_web_log_debug("%s: Request_url: %s", thisfunc, request_url); } else { am_web_log_error("%s: Could not get the request URL. " "Failed with error: %s.", thisfunc, am_status_to_string(status)); } } } if (status == AM_SUCCESS) { if (am_web_is_proxy_override_host_port_set(agent_config) == AM_TRUE) { const char *agent_host = am_web_get_agent_server_host(agent_config); int agent_port = am_web_get_agent_server_port(agent_config); if (agent_host != NULL) { char *temp = NULL; temp = replace_host_port(request_url, agent_host, agent_port, agent_config); if (temp != NULL) { free(request_url); request_url = temp; } } am_web_log_debug("%s: Request_url after overriding " "host and port: %s", thisfunc, request_url); } } if (status == AM_SUCCESS) { // Check for magic notification URL if (B_TRUE == am_web_is_notification(request_url, agent_config)) { am_web_free_memory(request_url); am_web_delete_agent_configuration(agent_config); if(query != NULL) { free(query); query = NULL; } if(method != NULL) { free(method); method = NULL; } return REQ_PROCEED; } } // Check if the SSO token is in the cookie header if (status == AM_SUCCESS) { requestResult = getISCookie(pblock_findval(COOKIE_HDR, rq->headers), &dpro_cookie, agent_config); if (requestResult == REQ_ABORTED) { status = AM_FAILURE; } else if (dpro_cookie != NULL) { am_web_log_debug("%s: SSO token found in cookie header.", thisfunc); } } // Create the environment map if( status == AM_SUCCESS) { status = am_map_create(&env_parameter_map); if( status != AM_SUCCESS) { am_web_log_error("%s: Unable to create map, status = %s (%d)", thisfunc, am_status_to_string(status), status); } } // If there is a proxy in front of the agent, the user can set in the // properties file the name of the headers that the proxy uses to set // the real client IP and host name. In that case the agent needs // to use the value of these headers to process the request // // Get the client IP address header set by the proxy, if there is one if (status == AM_SUCCESS) { clientIP_hdr_name = am_web_get_client_ip_header_name(agent_config); if (clientIP_hdr_name != NULL) { status = get_header_value(rq->headers, clientIP_hdr_name, B_FALSE, &clientIP_hdr, B_FALSE, NULL); } } // Get the client host name header set by the proxy, if there is one if (status == AM_SUCCESS) { clientHostname_hdr_name = am_web_get_client_hostname_header_name(agent_config); if (clientHostname_hdr_name != NULL) { status = get_header_value(rq->headers, clientHostname_hdr_name, B_FALSE, &clientHostname_hdr, B_FALSE, NULL); } } // If the client IP and host name headers contain more than one // value, take the first value. if (status == AM_SUCCESS) { if ((clientIP_hdr != NULL) || (clientHostname_hdr != NULL)) { status = am_web_get_client_ip_host(clientIP_hdr, clientHostname_hdr, &clientIP, &clientHostname); } } // Set the IP address and host name in the environment map if ((status == AM_SUCCESS) && (clientIP != NULL)) { status = am_web_set_host_ip_in_env_map(clientIP, clientHostname, env_parameter_map, agent_config); } // If the client IP was not obtained previously, // get it from the REMOTE_ADDR header. if ((status == AM_SUCCESS) && (clientIP == NULL)) { status = get_header_value(sn->client, REQUEST_IP_ADDR, B_FALSE, &clientIP_hdr, B_TRUE, &clientIP); } // In CDSSO mode, check if the sso token is in the post data if( status == AM_SUCCESS) { if((am_web_is_cdsso_enabled(agent_config) == B_TRUE) && (strcmp(method, REQUEST_METHOD_POST) == 0)) { if((dpro_cookie == NULL) && (am_web_is_url_enforced(request_url, pathInfo_hdr, clientIP, agent_config) == B_TRUE)) { // Set original method to GET orig_req = strdup(REQUEST_METHOD_GET); if (orig_req != NULL) { am_web_log_debug("%s: Request method set to GET.", thisfunc); } else { am_web_log_error("%s: Not enough memory to ", "allocate orig_req.", thisfunc); status = AM_NO_MEMORY; } // Check if dpro_cookie is in post data if( status == AM_SUCCESS) { response = get_post_assertion_data(sn, rq, request_url); status = am_web_check_cookie_in_post(args, &dpro_cookie, &request_url, &orig_req, method, response, B_FALSE, set_cookie, set_method, agent_config); if( status == AM_SUCCESS) { am_web_log_debug("%s: SSO token found in " "assertion.",thisfunc); } else { am_web_log_debug("%s: SSO token not found in " "assertion. Redirecting to login page.", thisfunc); status = AM_INVALID_SESSION; } } // Set back the original clf-request attribute if (status == AM_SUCCESS) { int clf_reqSize = 0; if ((query != NULL) && (strlen(query) > 0)) { clf_reqSize = strlen(orig_req) + strlen(uri_hdr) + strlen (query) + strlen(protocol) + 4; } else { clf_reqSize = strlen(orig_req) + strlen(uri_hdr) + strlen(protocol) + 3; } clf_req = malloc(clf_reqSize); if (clf_req == NULL) { am_web_log_error("%s: Unable to allocate %i " "bytes for clf_req", thisfunc, clf_reqSize); status = AM_NO_MEMORY; } else { memset (clf_req,'\0',clf_reqSize); strcpy(clf_req, orig_req); strcat(clf_req, " "); strcat(clf_req, uri_hdr); if ((query != NULL) && (strlen(query) > 0)) { strcat(clf_req, "?"); strcat(clf_req, query); } strcat(clf_req, " "); strcat(clf_req, protocol); am_web_log_debug("%s: clf-request set to %s", thisfunc, clf_req); } pblock_nvinsert(REQUEST_CLF, clf_req, rq->reqpb); } } } } // Check if access is allowed. if( status == AM_SUCCESS) { if (dpro_cookie != NULL) { am_web_log_debug("%s: SSO token = %s", thisfunc, dpro_cookie); } else { am_web_log_debug("%s: SSO token not found.", thisfunc); } status = am_web_is_access_allowed(dpro_cookie, request_url, pathInfo_hdr, method, clientIP, env_parameter_map, &result, agent_config); am_map_destroy(env_parameter_map); } switch(status) { case AM_SUCCESS: // Set remote user and authentication type ruser = result.remote_user; if (ruser != NULL) { pb_param *pbuser = pblock_remove(AUTH_USER_VAR, rq->vars); pb_param *pbauth = pblock_remove(AUTH_TYPE_VAR, rq->vars); if (pbuser != NULL) { param_free(pbuser); } pblock_nvinsert(AUTH_USER_VAR, ruser, rq->vars); if (pbauth != NULL) { param_free(pbauth); } pblock_nvinsert(AUTH_TYPE_VAR, AM_WEB_AUTH_TYPE_VALUE, rq->vars); am_web_log_debug("%s: access allowed to %s", thisfunc, ruser); } else { am_web_log_debug("%s: Remote user not set, " "allowing access to the url as it is in not " "enforced list", thisfunc); } if (am_web_is_logout_url(request_url, agent_config) == B_TRUE) { (void)am_web_logout_cookies_reset(reset_cookie, args, agent_config); } // set LDAP user attributes to http header status = am_web_result_attr_map_set(&result, set_header, set_cookie_in_response, set_header_attr_as_cookie, get_cookie_sync, args, agent_config); if (status != AM_SUCCESS) { am_web_log_error("%s: am_web_result_attr_map_set failed, " "status = %s (%d)", thisfunc, am_status_to_string(status), status); requestResult = REQ_ABORTED; } else { requestResult = REQ_PROCEED; } break; case AM_ACCESS_DENIED: am_web_log_debug("%s: Access denied to %s", thisfunc, result.remote_user ? result.remote_user : "******"); requestResult = do_redirect(sn, rq, status, &result, request_url, method, agent_config); break; case AM_INVALID_SESSION: if (am_web_is_cdsso_enabled(agent_config) == B_TRUE) { cdStatus = am_web_do_cookie_domain_set(set_cookie, args, EMPTY_STRING, agent_config); if(cdStatus != AM_SUCCESS) { am_web_log_error("%s: CDSSO reset cookie failed", thisfunc); } } am_web_do_cookies_reset(reset_cookie, args, agent_config); requestResult = do_redirect(sn, rq, status, &result, request_url, method, agent_config); break; case AM_INVALID_FQDN_ACCESS: // Redirect to self with correct FQDN - no post preservation requestResult = do_redirect(sn, rq, status, &result, request_url, method, agent_config); break; case AM_REDIRECT_LOGOUT: status = am_web_get_logout_url(&logout_url, agent_config); if(status == AM_SUCCESS) { do_url_redirect(sn,rq,logout_url); } else { requestResult = REQ_ABORTED; am_web_log_debug("validate_session_policy(): " "am_web_get_logout_url failed. "); } break; case AM_INVALID_ARGUMENT: case AM_NO_MEMORY: default: am_web_log_error("validate_session_policy() Status: %s (%d)", am_status_to_string(status), status); requestResult = REQ_ABORTED; break; } // Cleaning am_web_clear_attributes_map(&result); am_policy_result_destroy(&result); am_web_free_memory(dpro_cookie); am_web_free_memory(request_url); am_web_free_memory(logout_url); am_web_delete_agent_configuration(agent_config); if (orig_req != NULL) { free(orig_req); orig_req = NULL; } if (response != NULL) { free(response); response = NULL; } if (clf_req != NULL) { free(clf_req); clf_req = NULL; } if(query != NULL) { free(query); query = NULL; } if(method != NULL) { free(method); method = NULL; } if(clientIP != NULL) { am_web_free_memory(clientIP); } if(clientHostname != NULL) { am_web_free_memory(clientHostname); } am_web_log_max_debug("%s: Completed handling request with status: %s.", thisfunc, am_status_to_string(status)); return requestResult; }
static am_status_t set_header(const char *key, const char *values, void **args) { Request *rq = (Request *)args[0]; pb_param *hdr_pp = pblock_find("full-headers", rq->reqpb); const char *the_key = key; if (hdr_pp != NULL) { if(values != NULL && *values != '\0') { //Added by bn152013 for 6739097 int append = 0; int length = strlen(the_key) + strlen(values) + 5; if (hdr_pp->value != NULL) { size_t len = strlen(hdr_pp->value); length += len; append = 1; hdr_pp->value = (char *) system_realloc(hdr_pp->value, length); hdr_pp->value[len] = '\0'; } else { hdr_pp->value = (char *) system_malloc(length); hdr_pp->value[0]='\0'; } if ( hdr_pp->value == NULL) { return (AM_NO_MEMORY); } if (append) strcat(hdr_pp->value, the_key); else strcpy(hdr_pp->value, the_key); strcat(hdr_pp->value, ": "); strcat(hdr_pp->value, values); strcat(hdr_pp->value, "\r\n"); } else { if(key[0] != '\0' && hdr_pp->value != NULL) { char *ptr = strstr(hdr_pp->value, the_key); if(ptr != NULL) { char *end_ptr = ptr + strlen(the_key); while(*end_ptr != '\r' && *end_ptr != '\n') ++end_ptr; end_ptr += 2; while(*end_ptr != '\0') { *ptr = *end_ptr; ptr += 1; end_ptr += 1; } *ptr = '\0'; } } } } if(values != NULL && *values != '\0') { //Added by bn152013 for 6739097 pblock_nvinsert(the_key, (char *)values, rq->headers); } else { param_free(pblock_remove(the_key, rq->headers)); } return (AM_SUCCESS); }
static int do_redirect(Session *sn, Request *rq, am_status_t status, am_policy_result_t *policy_result, const char *original_url, const char* method, void* agent_config) { int retVal = REQ_ABORTED; char *redirect_url = NULL; const am_map_t advice_map = policy_result->advice_map; am_status_t ret = AM_SUCCESS; ret = am_web_get_url_to_redirect(status, advice_map, original_url, method, AM_RESERVED, &redirect_url, agent_config); if (ret == AM_SUCCESS && redirect_url != NULL) { char *advice_txt = NULL; if (B_FALSE == am_web_use_redirect_for_advice(agent_config) && policy_result->advice_string != NULL) { // Composite advice is sent as a POST ret = am_web_build_advice_response(policy_result, redirect_url, &advice_txt); am_web_log_debug("do_redirect(): policy status=%s,", "response[%s]", am_status_to_string(status), advice_txt); if (ret == AM_SUCCESS) { retVal = send_data(advice_txt, sn, rq); } else { am_web_log_error("do_redirect(): Error while building " "advice response body:%s", am_status_to_string(ret)); retVal = REQ_EXIT; } } else { // No composite advice or composite advice is redirected am_web_log_debug("do_redirect() policy status = %s, ", "redirection URL is %s", am_status_to_string(status), redirect_url); // we need to modify the redirect_url with the policy advice if (B_TRUE == am_web_use_redirect_for_advice(agent_config) && policy_result->advice_string != NULL) { char *redirect_url_with_advice = NULL; ret = am_web_build_advice_redirect_url(policy_result, redirect_url, &redirect_url_with_advice); if (ret == AM_SUCCESS) { redirect_url = redirect_url_with_advice; am_web_log_debug("do_redirect(): policy status=%s, " "redirect url with advice [%s]", am_status_to_string(status), redirect_url); } else { am_web_log_error("do_redirect(): Error while building " "the redirect url with advice:%s", am_status_to_string(ret)); } } /* redirection is enabled by the PathCheck directive */ /* Set the return code to 302 Redirect */ protocol_status(sn, rq, PROTOCOL_REDIRECT, NULL); /* set the new URL to redirect */ //pblock_nvinsert("url", redirect_url, rq->vars); pblock_nvinsert("escape", "no", rq->vars); param_free(pblock_remove("Location", rq->srvhdrs)); pblock_nvinsert("Location", redirect_url, rq->srvhdrs); protocol_start_response(sn, rq); am_web_free_memory(redirect_url); } } else if (ret == AM_NO_MEMORY) { /* Set the return code 500 Internal Server Error. */ protocol_status(sn, rq, PROTOCOL_SERVER_ERROR, NULL); am_web_log_error("do_redirect() Status code= %s.", am_status_to_string(status)); } else { /* Set the return code 403 Forbidden */ protocol_status(sn, rq, PROTOCOL_FORBIDDEN, NULL); am_web_log_info("do_redirect() Status code= %s.", am_status_to_string(status)); } return retVal; }
void param_free_l(param_t *p) { param_free(&p); }
PRStatus FcgiParser::parseAuthHeaders(pblock *pb) { Request *rq = request->getOrigRequest(); authHeaderPrefixLen = strlen(AUTH_HEADER_PREFIX); char *s; if(pb) { if((s = pblock_findval("status", pb))) { if((strlen(s) < 3) || (!isdigit(s[0]) || (!isdigit(s[1])) || (!isdigit(s[2])))) { s = NULL; } else { char ch = s[3]; s[3] = '\0'; int statusNum = atoi(s); s[3] = ch; rq->status_num = statusNum; if(statusNum == 200) authorized = PR_TRUE; } } if(!authorized) { protocol_status(request->getOrigSession(), request->getOrigRequest(), PROTOCOL_UNAUTHORIZED, NULL); } else { //retain only the headers starting with "Varaiable-" for (int i = 0; i < pb->hsize; i++) { pb_entry *p = pb->ht[i]; while (p) { const char *name = PL_strdup(p->param->name); const char *value = PL_strdup(p->param->value); if (*name == 'v' && (!PL_strcmp(name, "variable-"))) { pb_param *pparam = pblock_fr((char *)name, pb, PR_TRUE); param_free(pparam); name += authHeaderPrefixLen; // remove the prefix from name if(*name == 'r' && (!PL_strcmp(name, "remote_user"))) { pblock_nvinsert("auth-user", value, rq->vars); } if(*name == 'a' && (!PL_strcmp(name, "auth_type"))) { pblock_nvinsert("auth-type", value, rq->vars); } pblock_nvinsert(name, value, rq->headers); } PL_strfree((char *)name); PL_strfree((char *)value); p = p->next; } //while } //for } //if } else { lastError = INVALID_HTTP_HEADER; request->log(LOG_FAILURE, GetString(DBT_invalid_response)); return PR_FAILURE; } return PR_SUCCESS; }
/* * I hate myself and I want to die. * * This should be cleaned up considerably. Numerous flaws (e.g: word-size * mix). Unmanageable. Ugly. Fugly. Etc. * * Newer Varnish versions makes this redundant. * (Parses param.show -l and outputs json. Caller must issue free(); */ static char *vparams_show_json(char *raw) { char word[2048]; struct param_opt *tmp, *top; int pos = 0, i = 0; int state = 0; char *term = NULL; char *out = NULL, *out2 = NULL, *out3 = NULL; tmp = malloc(sizeof (struct param_opt)); top = NULL; tmp->next = NULL; /* * param.show -l output: * * V3: * (parameter) (value) \[(unit|)\] * Default is (value) * (description line 1) * .. * (description line n) * * V4/4.1: * (parameter) * Value is: (value) [\[(unit)\]] [\(default\)] * [Default is: (value)] * [Minimum is: (value)] * [Maximum is: (value)] * * (description line 1) * .. * (description line n) */ while(raw[pos]) { word[i++] = raw[pos]; assert(i<510); if (state == 0 && (raw[pos] == ' ' || raw[pos] == '\n')) { word[i-1] = '\0'; tmp->name = strdup(word); i = 0; while (raw[pos] == ' ' || raw[pos] == '\n') pos++; word[0] = raw[pos]; assert(strncmp("Value is: ", raw+pos, strlen("Value is: ")) == 0); pos += strlen("Value is: "); state = 1; pos--; } else if (state == 1 && (raw[pos] == '\n' || raw[pos] == '[')) { assert(i<510); i--; word[i] = '\0'; term = strrchr(word,'['); if (term) { assert(*(term-1) == ' '); *(term-1) = '\0'; } i = strlen(word); size_t dlen = strlen("(default)"); if (i > (int)dlen) { if (strncmp(word + i - dlen, "(default)", dlen) == 0) { i -= dlen; word[i] = '\0'; } } while(word[--i] == ' '); if (word[i] == '"') { assert(word[0] == '"'); memmove(word, word+1, i-1); i-=2; } word[i+1] = '\0'; assert(strchr(word,'"') == NULL); tmp->value = strdup(word); i = 0; if (raw[pos] == '\n') tmp->unit = strdup(""); else { pos++; while (raw[pos] != ']') word[i++] = raw[pos++]; word[i] = '\0'; tmp->unit = strdup(word); i = 0; } if (raw[pos] == '\n') pos++; term = strstr(raw+pos, "Default is: "); assert(term); pos = term-raw + strlen("Default is: "); if (raw[pos] == 0x01) { assert(raw[pos+1] == '\n'); pos++; } while (raw[pos] != '\n') { word[i++] = raw[pos++]; assert(i<2048); } assert(raw[pos] == '\n'); assert((isprint(word[0]) || i == 0)); word[i] = '\0'; if (word[i-1] == '"') { assert(word[0] == '"'); memmove(word, word+1, i-1); i-=2; } word[i] = '\0'; assert(strchr(word,'"') == NULL); tmp->def = strdup(word); i = 0; state = 0; while (!(raw[pos-1] == '\n' && !isspace(raw[pos]))) { if (raw[pos] == '\n') { pos++; word[i++] = '\\'; word[i++] = 'n'; state = 0; } else if (state == 0 && isspace(raw[pos])) { pos++; } else { state = 1; if (raw[pos] == '"') word[i++] = '\\'; if (raw[pos] == '\t') { word[i++] = '\\'; word[i++] = 't'; pos++; } else word[i++] = raw[pos++]; } } word[i] = '\0'; tmp->description = strdup(word); tmp->next = top; top = tmp; state = 0; i = 0; assert(strlen(tmp->name) < 30); tmp = malloc(sizeof (struct param_opt)); tmp->next = NULL; pos--; } pos++; } state = asprintf(&out3, "{\n"); assert(state); for (tmp = top; tmp != NULL; ) { param_assert(tmp); state = asprintf(&out, "\t\"%s\": {\n" "\t\t\"value\": \"%s\",\n" "\t\t\"default\": \"%s\",\n" "\t\t\"unit\": \"%s\",\n" "\t\t\"description\": \"%s\"\n" "\t}", tmp->name, tmp->value, tmp->def, tmp->unit, tmp->description); assert(state); state = asprintf(&out2, "%s%s%s", out3, out, (tmp->next) ? ",\n":""); assert(state); free(out); free(out3); out3 = out2; tmp = param_free(tmp); } state = asprintf(&out2, "%s\n}\n", out3); free(out3); return out2; }