Fawkes API
Fawkes Development Version
|
00001 00002 /*************************************************************************** 00003 * static_processor.cpp - Web request processor for static files 00004 * 00005 * Created: Mon Oct 13 23:41:24 2008 00006 * Copyright 2006-2008 Tim Niemueller [www.niemueller.de] 00007 * 00008 ****************************************************************************/ 00009 00010 /* This program is free software; you can redistribute it and/or modify 00011 * it under the terms of the GNU General Public License as published by 00012 * the Free Software Foundation; either version 2 of the License, or 00013 * (at your option) any later version. 00014 * 00015 * This program is distributed in the hope that it will be useful, 00016 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00017 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00018 * GNU Library General Public License for more details. 00019 * 00020 * Read the full text in the LICENSE.GPL file in the doc directory. 00021 */ 00022 00023 #include "static_processor.h" 00024 #include <webview/file_reply.h> 00025 #include <webview/error_reply.h> 00026 00027 #include <core/exception.h> 00028 #include <logging/logger.h> 00029 00030 #include <cstring> 00031 #include <cstdlib> 00032 #include <string> 00033 #include <unistd.h> 00034 #include <cerrno> 00035 #include <climits> 00036 00037 using namespace fawkes; 00038 00039 /** @class WebviewStaticRequestProcessor "static_processor.h" 00040 * Static file web processor. 00041 * This processor provides access to static files. 00042 * @author Tim Niemueller 00043 */ 00044 00045 /** Constructor. 00046 * @param baseurl Base URL where the static processor is mounted 00047 * @param htdocs_dir directory in the file system where to look for static files 00048 * @param logger logger 00049 */ 00050 WebviewStaticRequestProcessor::WebviewStaticRequestProcessor(const char *baseurl, 00051 const char *htdocs_dir, 00052 fawkes::Logger *logger) 00053 { 00054 __logger = logger; 00055 __baseurl = strdup(baseurl); 00056 __baseurl_len = strlen(__baseurl); 00057 __htdocs_dir = strdup(htdocs_dir); 00058 __htdocs_dir_len = strlen(__htdocs_dir); 00059 00060 } 00061 00062 /** Destructor. */ 00063 WebviewStaticRequestProcessor::~WebviewStaticRequestProcessor() 00064 { 00065 free(__baseurl); 00066 free(__htdocs_dir); 00067 } 00068 00069 00070 WebReply * 00071 WebviewStaticRequestProcessor::process_request(const char *url, 00072 const char *method, 00073 const char *version, 00074 const char *upload_data, 00075 size_t *upload_data_size, 00076 void **session_data) 00077 { 00078 if ( strncmp(__baseurl, url, __baseurl_len) == 0 ) { 00079 // It is in our URL prefix range 00080 std::string file_path = std::string(__htdocs_dir) + std::string(url).substr(__baseurl_len); 00081 00082 char rf[PATH_MAX]; 00083 char *realfile = realpath(file_path.c_str(), rf); 00084 if (! realfile ) { 00085 if (errno == ENOENT) { 00086 return new WebErrorPageReply(WebReply::HTTP_NOT_FOUND, "File not found"); 00087 } else if (errno == EACCES) { 00088 return new WebErrorPageReply(WebReply::HTTP_FORBIDDEN, "Access forbidden"); 00089 } else { 00090 char tmp[1024]; 00091 strerror_r(errno, tmp, sizeof(tmp)); 00092 return new WebErrorPageReply(WebReply::HTTP_INTERNAL_SERVER_ERROR, 00093 "File access failed: %s", tmp); 00094 } 00095 } else { 00096 if (strncmp(realfile, __htdocs_dir, __htdocs_dir_len) == 0) { 00097 try { 00098 DynamicFileWebReply *freply = new DynamicFileWebReply(file_path.c_str()); 00099 return freply; 00100 } catch (fawkes::Exception &e) { 00101 __logger->log_error("WebStaticReqProc", 00102 "Cannot fulfill request for file %s," 00103 " exception follows", url); 00104 __logger->log_error("WebStaticReqProc", e); 00105 return new WebErrorPageReply(WebReply::HTTP_INTERNAL_SERVER_ERROR, 00106 *(e.begin())); 00107 } 00108 } else { 00109 // Someone tries to trick us to give away files we don't want to give 00110 return new WebErrorPageReply(WebReply::HTTP_FORBIDDEN, 00111 "Access forbidden, breakout detected."); 00112 } 00113 } 00114 } else { 00115 // wrong base url, why the heck are we called!? 00116 __logger->log_error("WebStaticReqProc", "Called for invalid base url " 00117 "(url: %s, baseurl: %s)", url, __baseurl); 00118 return NULL; 00119 } 00120 }