myserver-commit
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[myserver-commit] [SCM] GNU MyServer branch, master, updated. 6bc604a42f


From: Giuseppe Scrivano
Subject: [myserver-commit] [SCM] GNU MyServer branch, master, updated. 6bc604a42ff4baae96d50ab9a69f1bd9fab65be2
Date: Thu, 20 Aug 2009 20:03:34 +0000

This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "GNU MyServer".

The branch, master has been updated
       via  6bc604a42ff4baae96d50ab9a69f1bd9fab65be2 (commit)
       via  21c90b54dd09a03173e26d4777f156cd4e6496a4 (commit)
       via  601ef5ff695ba2f17e6af0aef1373b3a0838aab0 (commit)
       via  467202faae38a843a0de650684f41929e32c3e2d (commit)
       via  be666de939f6e5c037f0ae4a392f17bf2684a636 (commit)
      from  b1465eb76903a8499ccbd53c711e7e4461dfe2c2 (commit)

Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.

- Log -----------------------------------------------------------------


commit 6bc604a42ff4baae96d50ab9a69f1bd9fab65be2
Author: Giuseppe Scrivano <address@hidden>
Date:   Thu Aug 20 21:59:59 2009 +0200

    New plugin MIME magic.

diff --git a/plugins/src/mime_magic/README b/plugins/src/mime_magic/README
index 8b13789..48dcb2f 100755
--- a/plugins/src/mime_magic/README
+++ b/plugins/src/mime_magic/README
@@ -1 +1,5 @@
+This plugin makes possible to use libmagic to find a file MIME type.
+
+To use it, define such line in myserver.xml or in a virtual host:
+  <DEFINE name="mime.handler" value="mime_magic" />
 
diff --git a/plugins/src/mime_magic/SConscript 
b/plugins/src/mime_magic/SConscript
index 1110464..5ef5a78 100755
--- a/plugins/src/mime_magic/SConscript
+++ b/plugins/src/mime_magic/SConscript
@@ -6,8 +6,6 @@ local_listinc=[
       '../../../',
       '/usr/local/include',
       '/usr/include/',
-      '/usr/include/python2.5',
-      '/usr/local/include/python2.5',
       '/usr/local/include/libxml2',
       '/usr/include/libxml2',
       '.'
@@ -19,11 +17,16 @@ env = Environment(CPPPATH=local_listinc)
 
 conf = Configure(env, config_h="config.h")
 
-if conf.CheckHeader("magic.h"):
-    conf.Define('PYTHON', 1)
+
+if conf.CheckLib("magic") and conf.CheckHeader("magic.h"):
+    conf.Define('MAGIC', 1)
+else:
+    print "Cannot find the library magic"
+    raise
+
 
 env = conf.Finish()
 
-env.SharedLibrary(GetLaunchDir() + "/" + dest_dir + "/mime_magic.cpp", 
["mime_magic.cpp" ], SHLIBPREFIX="")
+env.SharedLibrary(GetLaunchDir() + "/" + dest_dir + "/mime_magic", 
["mime_magic.cpp" ], SHLIBPREFIX="")
 
 Command(GetLaunchDir() + "/" + dest_dir + "/README","README", Copy("$TARGET", 
"$SOURCE"))
diff --git a/plugins/src/mime_magic/mime_magic.cpp 
b/plugins/src/mime_magic/mime_magic.cpp
index f5d9342..3a2a155 100755
--- a/plugins/src/mime_magic/mime_magic.cpp
+++ b/plugins/src/mime_magic/mime_magic.cpp
@@ -14,6 +14,7 @@ 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, see <http://www.gnu.org/licenses/>.
 */
+
 #include <stdafx.h>
 #include <string.h>
 #include <include/server/server.h>
@@ -38,7 +39,13 @@ class MagicHandler : public MimeManagerHandler
 public:
   MagicHandler ()
   {
-    cookie = magic_open (MAGIC_SYMLINK); 
+
+  }
+
+  int load ()
+  {
+    cookie = magic_open (MAGIC_SYMLINK | MAGIC_MIME_TYPE);
+    return magic_load (cookie, NULL);
   }
 
   virtual ~MagicHandler ()
@@ -50,23 +57,25 @@ public:
     magic_close (cookie);
   }
 
-       virtual MimeRecord* getMIME (const char *file)
+       virtual MimeRecord *getMIME (const char *file)
   {
     MimeRecord *rec = NULL;
     lock.lock ();
     try
       {
-        /* FIXME: is reentrant and can be moved outside of the critical
-         * section?  */
+        /* FIXME: is this line reentrant and can be moved outside of the
+         * critical section?  */
         const char *type = magic_file (cookie, file);
-        rec = records.get (type);
-        if (!rec)
+        if (type)
           {
-            rec = new MimeRecord;
-            rec->mimeType.assign (type);
-            records.put (type, rec);
+            rec = records.get (type);
+            if (!rec)
+              {
+                rec = new MimeRecord;
+                rec->mimeType.assign (type);
+                records.put (rec->mimeType, rec);
+              }
           }
-
       }
     catch (...)
       {
@@ -87,7 +96,7 @@ private:
 
 EXPORTABLE(char*) name (char* name, u_long len)
 {
-       char* str = (char*)"mime_magic";
+       char* str = (char*) "mime_magic";
        if (name)
                strncpy (name, str, len);
        return str;
@@ -95,23 +104,29 @@ EXPORTABLE(char*) name (char* name, u_long len)
 
 EXPORTABLE(int) load (void* server)
 {
-  string name ("magic");
+       return 0;
+}
+
+EXPORTABLE(int) postLoad(void* server)
+{
+  string name ("mime_magic");
        Server* serverInstance = (Server*)server;
   MimeManager *mimeManager = serverInstance->getMimeManager ();
 
-  MagicHandler handler = new MagicHandler;
+  MagicHandler *handler = new MagicHandler;
+  if (handler->load ())
+    {
+      serverInstance->logWriteln (MYSERVER_LOG_MSG_ERROR,
+                                  _("cannot load mime magic configuration"));
+      return 1;
+    }
 
   mimeManager->registerHandler (name, handler);
 
        return 0;
 }
 
-EXPORTABLE(int) postLoad(void* server,void* parser)
-{
-       return 0;
-}
-
-EXPORTABLE(int) unLoad(void* parser)
+EXPORTABLE(int) unLoad()
 {
        return 0;
 }
diff --git a/plugins/src/mime_magic/plugin.xml 
b/plugins/src/mime_magic/plugin.xml
index f639ad9..9b6c606 100755
--- a/plugins/src/mime_magic/plugin.xml
+++ b/plugins/src/mime_magic/plugin.xml
@@ -1,9 +1,9 @@
 <?xml version="1.0"?>
 
-<PLUGIN>
-<NAME>mime_magic</NAME>
-<VERSION>0.1</VERSION>
-<AUTHOR>The Free Software Foundation Inc.</AUTHOR>
-<MAINTAINER>The Free Software Foundation Inc.</MAINTAINER>
-<DESCRIPTION>This plugin permits to check MIME types using the libmagic 
library</DESCRIPTION>
+<PLUGIN min-version="0.9" max-version="0.9">
+       <NAME>mime_magic</NAME>
+       <VERSION>0.1</VERSION>
+       <AUTHOR>The Free Software Foundation Inc.</AUTHOR>
+       <MAINTAINER>The Free Software Foundation Inc.</MAINTAINER>
+       <DESCRIPTION>This plugin permits to check MIME types using the libmagic 
library</DESCRIPTION>
 </PLUGIN>



commit 21c90b54dd09a03173e26d4777f156cd4e6496a4
Author: Giuseppe Scrivano <address@hidden>
Date:   Thu Aug 20 21:50:18 2009 +0200

    Delegate the function using the desired handler, not NULL.

diff --git a/myserver/src/conf/mime/mime_manager.cpp 
b/myserver/src/conf/mime/mime_manager.cpp
index e1c1b72..a83e149 100644
--- a/myserver/src/conf/mime/mime_manager.cpp
+++ b/myserver/src/conf/mime/mime_manager.cpp
@@ -402,7 +402,7 @@ void MimeManager::clearRecords ()
  */
 MimeRecord *MimeManager::getMIME (string const &filename, const char *handler)
 {
-  return getMIME (filename.c_str ());
+  return getMIME (filename.c_str (), handler);
 }
 
 /*!
@@ -416,7 +416,6 @@ MimeRecord *MimeManager::getMIME (const char *filename, 
const char *handler)
   string ext;
   u_long pos = 0;
 
-
   for (list<PathRegex*>::iterator it = pathRegex.begin ();
        it != pathRegex.end ();
        it++)
diff --git a/plugins/src/mime_magic/.svn/dir-prop-base 
b/plugins/src/mime_magic/.svn/dir-prop-base
new file mode 100755
index 0000000..3160658
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/dir-prop-base
@@ -0,0 +1,5 @@
+K 13
+svn:mergeinfo
+V 0
+
+END
diff --git a/plugins/src/mime_magic/.svn/entries 
b/plugins/src/mime_magic/.svn/entries
new file mode 100755
index 0000000..c0889e9
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/entries
@@ -0,0 +1,198 @@
+9
+
+dir
+2915
+svn+ssh://svn.savannah.gnu.org/myserver/trunk/plugins/src/http_checker
+svn+ssh://svn.savannah.gnu.org/myserver
+
+
+
+2008-10-26T19:37:37.786994Z
+2913
+dperrone
+has-props
+
+svn:special svn:externals svn:needs-lock
+
+
+
+
+
+
+
+
+
+
+
+c4c922ea-a70d-0410-937d-ec1daf91936c
+
+http_rules_sample.py
+file
+
+
+
+
+2008-10-26T19:53:56.000000Z
+e61d209f6980c329e3795139269735c4
+2007-06-27T17:27:50.877877Z
+2361
+rocky_10_balboa
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+178
+
+http_checker.cpp
+file
+
+
+
+
+2008-10-26T19:53:56.000000Z
+4e6fa7755d56cc869aca2ecbc983fe6d
+2008-10-26T19:37:37.786994Z
+2913
+dperrone
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+8318
+
+SConscript
+file
+
+
+
+
+2008-10-26T19:53:56.000000Z
+7af7e7f0ecaf27a4f285cb25693802b7
+2008-10-26T19:37:37.786994Z
+2913
+dperrone
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+833
+
+README
+file
+
+
+
+
+2008-10-26T19:53:56.000000Z
+c183d3026fc5de262d58657ce90a4dd2
+2007-06-27T17:27:50.877877Z
+2361
+rocky_10_balboa
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+1093
+
+plugin.xml
+file
+
+
+
+
+2008-10-26T19:53:56.000000Z
+12098a0843a40122c30920847a26d14f
+2008-10-26T19:37:37.786994Z
+2913
+dperrone
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+313
+
diff --git a/plugins/src/mime_magic/.svn/format 
b/plugins/src/mime_magic/.svn/format
new file mode 100755
index 0000000..ec63514
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/format
@@ -0,0 +1 @@
+9
diff --git a/plugins/src/mime_magic/.svn/text-base/README.svn-base 
b/plugins/src/mime_magic/.svn/text-base/README.svn-base
new file mode 100755
index 0000000..b68b7dc
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/text-base/README.svn-base
@@ -0,0 +1,40 @@
+A HTTP checker rule is added trough the main myserver.xml
+configuration file, a rule is a python script to execute on every HTTP
+request, for example this rule denies any access if the client
+used the host localhost:8080 to connect to the server.
+
+This plugin needs the executors/python plugin to be installed too.
+
+<HTTP_CHECKER_RULE>
+<![CDATA[
+from http_checker import get_header
+from http_checker import raise_error
+
+if get_header('Host') == "localhost:8080":
+       raise_error(401)
+]]>
+</HTTP_CHECKER_RULE>
+
+If the rules are complicated then it is possible to use an external
+python file to execute:
+
+<HTTP_CHECKER_RULE file="http_rules_sample.py" />
+
+
+Functions in the http_checker module:
+
+get_remote_port() - Get the client TCP port.
+
+get_local_port() - Get the local TCP port.
+
+get_remote_addr() - Get the remote IP address.
+
+get_local_addr() - Get the local IP address.
+
+set_header(header, value) - Set HTTP header field value.
+
+get_header(header) - Get HTTP header field value.
+
+send_redirect(page) - Send a redirect to another location.
+
+raise_error(error_code) - Raise HTTP error page.
diff --git a/plugins/src/mime_magic/.svn/text-base/SConscript.svn-base 
b/plugins/src/mime_magic/.svn/text-base/SConscript.svn-base
new file mode 100755
index 0000000..d63c425
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/text-base/SConscript.svn-base
@@ -0,0 +1,30 @@
+#-*- mode: python -*-
+Import('dest_dir','listinc')
+
+local_listinc=[
+      GetLaunchDir(),
+      '../../../',
+      '/usr/local/include',
+      '/usr/include/',
+      '/usr/include/python2.5',
+      '/usr/local/include/python2.5',
+      '/usr/local/include/libxml2',
+      '/usr/include/libxml2',
+      '.'
+      ]
+
+local_listinc.extend(listinc)
+
+env = Environment(CPPPATH=local_listinc)
+
+conf = Configure(env, config_h="config.h")
+
+if conf.CheckHeader("Python.h"):
+    conf.Define('PYTHON', 1)
+
+env = conf.Finish()
+
+env.SharedLibrary(GetLaunchDir() + "/" + dest_dir + "/http_checker", 
["http_checker.cpp" ], SHLIBPREFIX="")
+
+Command(GetLaunchDir() + "/" + dest_dir + "/README","README", Copy("$TARGET", 
"$SOURCE"))
+Command(GetLaunchDir() + "/" + dest_dir + 
"/http_rules_sample.py","http_rules_sample.py", Copy("$TARGET", "$SOURCE"))
diff --git a/plugins/src/mime_magic/.svn/text-base/http_checker.cpp.svn-base 
b/plugins/src/mime_magic/.svn/text-base/http_checker.cpp.svn-base
new file mode 100755
index 0000000..8c5a166
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/text-base/http_checker.cpp.svn-base
@@ -0,0 +1,326 @@
+/*
+MyServer
+Copyright (C) 2007 The Free Software Foundation Inc.
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+#include <stdafx.h>
+#include <string.h>
+#include <include/server/server.h>
+#include <include/base/multicast/multicast.h>
+#include <include/protocol/http/http.h>
+#include <include/plugin/plugin.h>
+#include <Python.h>
+
+#ifdef WIN32
+#define EXPORTABLE(x) x _declspec(dllexport)
+#else
+#define EXPORTABLE(x) extern "C" x
+#endif
+
+typedef int (*executePROC)(char*, u_long);
+typedef int (*executeFromFilePROC)(char*);
+
+
+struct ThreadData
+{
+       HttpThreadContext* td;
+       int ret;
+};
+
+static HashMap<ThreadID, ThreadData*> pythonThreadData;
+static Mutex mutex;
+
+typedef int (*INIT_MODULE)(char* name, PyMethodDef methods[]);
+static INIT_MODULE init;
+
+
+static ThreadData* getThreadData()
+{
+       ThreadID tid = Thread::threadID();
+       ThreadData* ret;
+       mutex.lock();
+       ret = pythonThreadData.get(tid);
+       mutex.unlock();
+       return ret;
+}
+
+static HttpThreadContext* getThreadContext()
+{
+       return getThreadData()->td;
+}
+
+static PyObject *get_remote_addr(PyObject *self, PyObject *args)
+{
+       HttpThreadContext* context = getThreadContext();
+               return Py_BuildValue((char*)"s", 
context->connection->getIpAddr());
+}
+
+static PyObject *get_remote_port(PyObject *self, PyObject *args)
+{
+       HttpThreadContext* context = getThreadContext();
+               return Py_BuildValue((char*)"i", 
context->connection->getPort());
+}
+
+static PyObject *get_local_addr(PyObject *self, PyObject *args)
+{
+       HttpThreadContext* context = getThreadContext();
+               return Py_BuildValue((char*)"s", 
context->connection->getLocalIpAddr());
+}
+
+static PyObject *get_local_port(PyObject *self, PyObject *args)
+{
+       HttpThreadContext* context = getThreadContext();
+               return Py_BuildValue((char*)"i", 
context->connection->getLocalPort());
+}
+
+
+static PyObject *get_header(PyObject *self, PyObject *args)
+{
+       char *header;
+       string value;
+       if (!PyArg_ParseTuple(args, (char*)"s", &header))
+               return NULL;
+
+       HttpThreadContext* context = getThreadContext();
+
+       context->request.getValue(header, &value);
+
+       return Py_BuildValue((char*)"s", value.c_str());
+}
+
+static PyObject *set_header(PyObject *self, PyObject *args)
+{
+       char *header;
+       char *value;
+       const char* ret;
+       if (!PyArg_ParseTuple(args, (char*)"ss", &header, &value))
+               return NULL;
+
+       HttpThreadContext* context = getThreadContext();
+
+       ret = context->request.setValue(header, value)->c_str();
+
+       return Py_BuildValue((char*)"s", ret);
+}
+
+static PyObject *raise_error(PyObject *self, PyObject *args)
+{
+       int error;
+       if (!PyArg_ParseTuple(args, (char*)"i", &error))
+               return NULL;
+
+       ThreadData* data = getThreadData();
+
+       if(data->ret)
+               return NULL;
+
+       data->td->http->raiseHTTPError(error);
+
+       data->ret = 1;
+
+       return Py_BuildValue((char*)"s", "");
+}
+
+static PyObject *send_redirect(PyObject *self, PyObject *args)
+{
+       char* dest;
+       if (!PyArg_ParseTuple(args, (char*)"s", &dest))
+               return NULL;
+
+       ThreadData* data = getThreadData();
+
+       if(data->ret)
+               return NULL;
+
+       data->td->http->sendHTTPRedirect(dest);
+
+       data->ret = 1;
+
+       return Py_BuildValue((char*)"s", dest);
+}
+
+static PyMethodDef httpCheckerMethods[] = {
+       {(char*)"get_remote_port", get_remote_port, METH_VARARGS, (char*)"Get 
the remote TCP port"},
+       {(char*)"get_local_port", get_local_port, METH_VARARGS, (char*)"Get the 
local TCP port"},
+       {(char*)"get_remote_addr", get_remote_addr, METH_VARARGS, (char*)"Get 
the remote IP address"},
+       {(char*)"get_local_addr", get_local_addr, METH_VARARGS, (char*)"Get the 
local IP address"},
+       {(char*)"get_header", get_header, METH_VARARGS, (char*)"Get HTTP header 
field value"},
+       {(char*)"set_header", set_header, METH_VARARGS, (char*)"Set HTTP header 
field value"},
+       {(char*)"send_redirect", send_redirect, METH_VARARGS, (char*)"Send a 
redirect to another location"},
+       {(char*)"raise_error", raise_error, METH_VARARGS, (char*)"Raise HTTP 
error page"},
+       {NULL, NULL, 0, NULL}
+};
+
+
+class HttpObserver : public Multicast<string, void*, int>
+{
+       struct Item
+       {
+               string data;
+               bool file;
+       };
+public:
+
+       virtual int updateMulticast(MulticastRegistry<string, void*, int>* reg, 
string& msg, void* arg)
+       {
+               HttpThreadContext *td = (HttpThreadContext*)arg;
+               ThreadID tid = Thread::threadID();
+               list<Item>::iterator it;
+               mutex.lock();
+               ThreadData threadData = {td, 0};
+               pythonThreadData.put(tid, &threadData);
+               mutex.unlock();
+
+               init((char*)"http_checker", httpCheckerMethods);
+
+               for(it = rules.begin(); it != rules.end(); it++)
+               {
+                       if((*it).file) 
+                       {
+                               executeFromFilePROC execute = 
((executeFromFilePROC)python->getDirectMethod((char*)"executeFromFile"));
+                               if (execute)
+                                 execute((char*)(*it).data.c_str());
+                       }else
+                       {
+                               executePROC execute = 
((executePROC)python->getDirectMethod((char*)"execute"));
+                               
+                               if (execute)
+                                 execute((char*)(*it).data.c_str(), 
(*it).data.length());
+                       }
+               }
+               return threadData.ret;
+       }
+
+       void addRule(const char* rule, bool file)
+       {
+               Item it;
+               it.data.assign(rule);
+               it.file = file;
+               rules.push_back(it);
+       }
+
+       void setPythonExecutor(Plugin* python){this->python = python;}
+
+private:
+       list<Item> rules;
+       Plugin* python;
+};
+
+static HttpObserver observer;
+
+EXPORTABLE(char*) name(char* name, u_long len)
+{
+       char* str = (char*)"http_checker";
+       if(name)
+               strncpy(name, str, len);
+       return str;
+}
+
+EXPORTABLE(int) load(void* server,void* parser)
+{
+       Server* serverInstance = (Server*)server;
+       HttpStaticData* staticData =(HttpStaticData*) 
serverInstance->getGlobalData("http-static");
+       string msg("new-http-request");
+       string pythonName("python");
+       Plugin* python;
+       XmlParser* configuration;
+       xmlDocPtr xmlDoc;
+       if(!staticData)
+       {
+               serverInstance->logLockAccess();
+               serverInstance->logPreparePrintError();
+               serverInstance->logWriteln("HttpChecker: Invalid HTTP static 
data");
+               serverInstance->logEndPrintError();
+               serverInstance->logUnlockAccess();
+               return -1;
+       }
+       python = serverInstance->getPluginsManager()->getPlugin(pythonName);
+
+       if(!python)
+       {
+               serverInstance->logLockAccess();
+               serverInstance->logPreparePrintError();
+               serverInstance->logWriteln("HttpChecker: Cannot find 
executors::python");
+               serverInstance->logEndPrintError();
+               serverInstance->logUnlockAccess();
+               return -1;
+       }
+       observer.setPythonExecutor(python);
+
+       staticData->addMulticast(msg, &observer);
+
+       init = (INIT_MODULE) python->getDirectMethod((char*)"initModule");
+
+       if(!init)
+       {
+               serverInstance->logLockAccess();
+               serverInstance->logPreparePrintError();
+               serverInstance->logWriteln("HttpChecker: Cannot find method 
initModule in executors::python");
+               serverInstance->logEndPrintError();
+               serverInstance->logUnlockAccess();
+               return -1;
+       }
+       configuration = serverInstance->getConfiguration();
+       xmlDoc = configuration->getDoc();
+
+       for(xmlNodePtr ptr = xmlDoc->children->next->children; ptr; ptr = 
ptr->next)
+       {
+               if(!xmlStrcmp(ptr->name, (const xmlChar *)"HTTP_CHECKER_RULE"))
+               {
+                       bool file = false;
+                       xmlAttrPtr properties = ptr->properties;
+                       char* data = 0;
+                       while(properties)
+                       {
+                               if(!xmlStrcmp(properties->name, (const xmlChar 
*)"file"))
+                               {
+                                       if(properties->children && 
properties->children->content)
+                                               data = 
(char*)properties->children->content;
+
+                                       file = true;
+                               }
+                               properties = properties->next;
+                       }
+
+                       if(!file && ptr->children && ptr->children->next && 
ptr->children->next->content)
+                               data = (char*)ptr->children->next->content;
+
+                       if(!data)
+                       {
+                               serverInstance->logLockAccess();
+                               serverInstance->logPreparePrintError();
+                               serverInstance->logWriteln("HttpChecker: 
Invalid rule");
+                               serverInstance->logEndPrintError();
+                               serverInstance->logUnlockAccess();
+                               return -1;
+                       }
+
+                       observer.addRule(data, file);
+               }
+
+       }
+
+       mutex.init();
+
+       return 0;
+}
+EXPORTABLE(int) postLoad(void* server,void* parser)
+{
+       return 0;
+}
+EXPORTABLE(int) unLoad(void* parser)
+{
+       mutex.destroy();
+       return 0;
+}
diff --git 
a/plugins/src/mime_magic/.svn/text-base/http_rules_sample.py.svn-base 
b/plugins/src/mime_magic/.svn/text-base/http_rules_sample.py.svn-base
new file mode 100755
index 0000000..dbf5ead
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/text-base/http_rules_sample.py.svn-base
@@ -0,0 +1,6 @@
+from http_checker import *
+
+# This simple rule returns a 404 error page to every request from the
+# host 192.168.0.2.
+if get_remote_addr() == "192.168.0.2":
+    raise_error(404)
diff --git a/plugins/src/mime_magic/.svn/text-base/plugin.xml.svn-base 
b/plugins/src/mime_magic/.svn/text-base/plugin.xml.svn-base
new file mode 100755
index 0000000..8af05d9
--- /dev/null
+++ b/plugins/src/mime_magic/.svn/text-base/plugin.xml.svn-base
@@ -0,0 +1,10 @@
+<?xml version="1.0"?>
+
+<PLUGIN>
+<NAME>http_checker</NAME>
+<VERSION>0.1</VERSION>
+<AUTHOR>The Free Software Foundation Inc.</AUTHOR>
+<MAINTAINER>The Free Software Foundation Inc.</MAINTAINER>
+<DESCRIPTION>This plugin permits to validate HTTP requests using 
python</DESCRIPTION>
+<DEPENDS>python</DEPENDS>
+</PLUGIN>
diff --git a/plugins/src/mime_magic/README b/plugins/src/mime_magic/README
new file mode 100755
index 0000000..8b13789
--- /dev/null
+++ b/plugins/src/mime_magic/README
@@ -0,0 +1 @@
+
diff --git a/plugins/src/mime_magic/SConscript 
b/plugins/src/mime_magic/SConscript
new file mode 100755
index 0000000..1110464
--- /dev/null
+++ b/plugins/src/mime_magic/SConscript
@@ -0,0 +1,29 @@
+#-*- mode: python -*-
+Import('dest_dir','listinc')
+
+local_listinc=[
+      GetLaunchDir(),
+      '../../../',
+      '/usr/local/include',
+      '/usr/include/',
+      '/usr/include/python2.5',
+      '/usr/local/include/python2.5',
+      '/usr/local/include/libxml2',
+      '/usr/include/libxml2',
+      '.'
+      ]
+
+local_listinc.extend(listinc)
+
+env = Environment(CPPPATH=local_listinc)
+
+conf = Configure(env, config_h="config.h")
+
+if conf.CheckHeader("magic.h"):
+    conf.Define('PYTHON', 1)
+
+env = conf.Finish()
+
+env.SharedLibrary(GetLaunchDir() + "/" + dest_dir + "/mime_magic.cpp", 
["mime_magic.cpp" ], SHLIBPREFIX="")
+
+Command(GetLaunchDir() + "/" + dest_dir + "/README","README", Copy("$TARGET", 
"$SOURCE"))
diff --git a/plugins/src/mime_magic/mime_magic.cpp 
b/plugins/src/mime_magic/mime_magic.cpp
new file mode 100755
index 0000000..f5d9342
--- /dev/null
+++ b/plugins/src/mime_magic/mime_magic.cpp
@@ -0,0 +1,117 @@
+/*
+MyServer
+Copyright (C) 2007, 2009 The Free Software Foundation Inc.
+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 3 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, see <http://www.gnu.org/licenses/>.
+*/
+#include <stdafx.h>
+#include <string.h>
+#include <include/server/server.h>
+#include <include/base/multicast/multicast.h>
+#include <include/protocol/http/http.h>
+#include <include/plugin/plugin.h>
+#include <include/conf/mime/mime_manager.h>
+#include <include/base/hash_map/hash_map.h>
+#include <magic.h>
+
+#ifdef WIN32
+#define EXPORTABLE(x) x _declspec(dllexport)
+#else
+#define EXPORTABLE(x) extern "C" x
+#endif
+
+typedef int (*executePROC)(char*, u_long);
+typedef int (*executeFromFilePROC)(char*);
+
+class MagicHandler : public MimeManagerHandler
+{
+public:
+  MagicHandler ()
+  {
+    cookie = magic_open (MAGIC_SYMLINK); 
+  }
+
+  virtual ~MagicHandler ()
+  {
+    HashMap<string, MimeRecord*>::Iterator it = records.begin ();
+    for (; it != records.end (); it++)
+      delete *it;
+
+    magic_close (cookie);
+  }
+
+       virtual MimeRecord* getMIME (const char *file)
+  {
+    MimeRecord *rec = NULL;
+    lock.lock ();
+    try
+      {
+        /* FIXME: is reentrant and can be moved outside of the critical
+         * section?  */
+        const char *type = magic_file (cookie, file);
+        rec = records.get (type);
+        if (!rec)
+          {
+            rec = new MimeRecord;
+            rec->mimeType.assign (type);
+            records.put (type, rec);
+          }
+
+      }
+    catch (...)
+      {
+        lock.unlock ();
+        return NULL;
+      }
+
+    lock.unlock ();
+
+    return rec;
+  }
+
+private:
+  magic_t cookie;
+  Mutex lock;
+  HashMap<string, MimeRecord*> records;
+};
+
+EXPORTABLE(char*) name (char* name, u_long len)
+{
+       char* str = (char*)"mime_magic";
+       if (name)
+               strncpy (name, str, len);
+       return str;
+}
+
+EXPORTABLE(int) load (void* server)
+{
+  string name ("magic");
+       Server* serverInstance = (Server*)server;
+  MimeManager *mimeManager = serverInstance->getMimeManager ();
+
+  MagicHandler handler = new MagicHandler;
+
+  mimeManager->registerHandler (name, handler);
+
+       return 0;
+}
+
+EXPORTABLE(int) postLoad(void* server,void* parser)
+{
+       return 0;
+}
+
+EXPORTABLE(int) unLoad(void* parser)
+{
+       return 0;
+}
diff --git a/plugins/src/mime_magic/plugin.xml 
b/plugins/src/mime_magic/plugin.xml
new file mode 100755
index 0000000..f639ad9
--- /dev/null
+++ b/plugins/src/mime_magic/plugin.xml
@@ -0,0 +1,9 @@
+<?xml version="1.0"?>
+
+<PLUGIN>
+<NAME>mime_magic</NAME>
+<VERSION>0.1</VERSION>
+<AUTHOR>The Free Software Foundation Inc.</AUTHOR>
+<MAINTAINER>The Free Software Foundation Inc.</MAINTAINER>
+<DESCRIPTION>This plugin permits to check MIME types using the libmagic 
library</DESCRIPTION>
+</PLUGIN>



commit 601ef5ff695ba2f17e6af0aef1373b3a0838aab0
Author: Giuseppe Scrivano <address@hidden>
Date:   Thu Aug 20 21:49:57 2009 +0200

    Fixed some error messages.

diff --git a/myserver/src/base/dynamic_lib/dynamiclib.cpp 
b/myserver/src/base/dynamic_lib/dynamiclib.cpp
index da69dcd..7e480f8 100644
--- a/myserver/src/base/dynamic_lib/dynamiclib.cpp
+++ b/myserver/src/base/dynamic_lib/dynamiclib.cpp
@@ -1,6 +1,6 @@
 /*
 MyServer
-Copyright (C) 2005, 2007, 2008 Free Software Foundation, Inc.
+Copyright (C) 2005, 2007, 2008, 2009 Free Software Foundation, Inc.
 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 3 of the License, or
@@ -18,35 +18,36 @@ along with this program.  If not, see 
<http://www.gnu.org/licenses/>.
 #include <include/base/dynamic_lib/dynamiclib.h>
 
 /*!
- *Initialize class internal data.
+ * Initialize class internal data.
  */
-DynamicLibrary::DynamicLibrary()
+DynamicLibrary::DynamicLibrary ()
 {
   handle = 0;
 }
 
 /*!
- *Destroy the object.
+ * Destroy the object.
  */
-DynamicLibrary::~DynamicLibrary()
+DynamicLibrary::~DynamicLibrary ()
 {
-  close();
+  close ();
 }
 
 /*!
- *Load the specified dynamic library. It returns 0 on success.
- *\param filename Name of the file to load.
- *\param globally Set if the library is loaded globally.
+ * Load the specified dynamic library. It returns 0 on success.
+ * \param filename Name of the file to load.
+ * \param globally Set if the library is loaded globally.
  */
-int DynamicLibrary::loadLibrary(const char* filename, int globally)
+int DynamicLibrary::loadLibrary (const char* filename, int globally)
 {
-  fileName.assign(filename);
+  fileName.assign (filename);
 #ifdef WIN32
-  handle = LoadLibrary(filename);
+  handle = LoadLibrary (filename);
 #endif
+
 #ifdef HAVE_DL
   int flag = 0;
-  if(globally)
+  if (globally)
     flag = RTLD_NOW | RTLD_GLOBAL;
   else
     flag = RTLD_LOCAL | RTLD_LAZY;
@@ -55,51 +56,51 @@ int DynamicLibrary::loadLibrary(const char* filename, int 
globally)
   flag |= RTLD_DEEPBIND;
 #endif
 
-  handle = dlopen(filename, flag);
+  handle = dlopen (filename, flag);
 #endif
   return handle ? 0 : 1;
 }
 
 /*!
- *Get a pointer to the specified function. Returns 0 on errors or 
- *the function address. 
+ *Get a pointer to the specified function. Returns 0 on errors or
+ *the function address.
  *\param fnName Function name to find.
  */
-void* DynamicLibrary::getProc(const char* fnName)
+void* DynamicLibrary::getProc (const char* fnName)
 {
-  if(!handle)
+  if (!handle)
     return 0;
 #ifdef WIN32
-    return (void*) GetProcAddress((HMODULE)handle, fnName); 
+    return (void*) GetProcAddress ((HMODULE)handle, fnName);
 #endif
 #ifdef HAVE_DL
-    return (void*) dlsym(handle, fnName);
+    return (void*) dlsym (handle, fnName);
 #endif
 }
 
 /*!
  *Close the library. Returns 0 on success.
  */
-int DynamicLibrary::close()
+int DynamicLibrary::close ()
 {
   int ret = 1;
-  if(!handle)
+  if (!handle)
     return 1;
 #ifdef WIN32
-    ret = FreeLibrary((HMODULE)handle) ? 0 : 1; 
+    ret = FreeLibrary ((HMODULE)handle) ? 0 : 1;
 #endif
 #ifdef HAVE_DL
-    ret = dlclose(handle);
+    ret = dlclose (handle);
 #endif
     handle = 0;
-    fileName.assign("");
+    fileName.assign ("");
     return ret;
 }
 
 /*!
- *Return if the object has a valid handle.
+ * Return if the object has a valid handle.
  */
-int DynamicLibrary::validHandle()
+int DynamicLibrary::validHandle ()
 {
   return handle ? 1 : 0;
 }
diff --git a/myserver/src/plugin/plugin.cpp b/myserver/src/plugin/plugin.cpp
index f79c0bf..ee6c601 100755
--- a/myserver/src/plugin/plugin.cpp
+++ b/myserver/src/plugin/plugin.cpp
@@ -66,7 +66,6 @@ int Plugin::load (Server* server)
  */
 int Plugin::preLoad (string& file, bool global)
 {
-
   return hinstLib.loadLibrary (file.c_str (), global ? 1 : 0);
 }
 
diff --git a/myserver/src/plugin/plugins_manager.cpp 
b/myserver/src/plugin/plugins_manager.cpp
index ef625c8..b69dda2 100755
--- a/myserver/src/plugin/plugins_manager.cpp
+++ b/myserver/src/plugin/plugins_manager.cpp
@@ -214,7 +214,7 @@ PluginsManager::preLoad (Server* server, string& resource)
                 {
                   ret |= 1;
                   server->logWriteln (MYSERVER_LOG_MSG_ERROR,
-                                   _("Error loading plugin %s"), name.c_str 
());
+                               _("Error loading plugin %s"), libname.c_str ());
                 }
               else
                 pinfo->setPlugin (plugin);
@@ -257,7 +257,6 @@ PluginsManager::loadInfo (Server* server, string& name, 
string& path)
     }
   XmlParser xml;
 
-
   if (xml.open (path, true))
     {
       server->logWriteln (MYSERVER_LOG_MSG_ERROR,
@@ -287,7 +286,6 @@ PluginsManager::loadInfo (Server* server, string& name, 
string& path)
 
       string sMinVer ((char*)minVersion);
       pinfo->setMyServerMinVersion (PluginInfo::convertVersion (&sMinVer));
-      xmlMemFree ((void*)minVersion);
     }
   else
     {
@@ -297,8 +295,6 @@ PluginsManager::loadInfo (Server* server, string& name, 
string& path)
       return NULL;
     }
 
-
-
   if (xmlHasProp (nodes->nodeTab[0], (const xmlChar*) "max-version"))
     {
       xmlChar* maxVersion = xmlGetProp (nodes->nodeTab[0],
@@ -306,7 +302,6 @@ PluginsManager::loadInfo (Server* server, string& name, 
string& path)
 
       string sMaxVer ((char*)maxVersion);
       pinfo->setMyServerMaxVersion (PluginInfo::convertVersion (&sMaxVer));
-      xmlMemFree ((void*)maxVersion);
     }
   else
     {
@@ -436,8 +431,8 @@ PluginsManager::preLoadPlugin (string& file, Server* 
server, bool global)
   if (plugin->preLoad (file, global))
     {
       server->logWriteln (MYSERVER_LOG_MSG_ERROR,
-                          _("Error pre-loading plugin %s, invalid plugin.xml"),
-                          name.c_str ());
+                          _("Error pre-loading plugin %s"),
+                          file.c_str ());
       delete plugin;
       return NULL;
     }
@@ -448,8 +443,8 @@ PluginsManager::preLoadPlugin (string& file, Server* 
server, bool global)
   else
     {
       server->logWriteln (MYSERVER_LOG_MSG_ERROR,
-                          _("Error pre-loading plugin %s, invalid plugin.xml"),
-                          name.c_str ());
+                          _("Error pre-loading plugin %s"),
+                          file.c_str ());
       delete plugin;
       return NULL;
     }



commit 467202faae38a843a0de650684f41929e32c3e2d
Author: Giuseppe Scrivano <address@hidden>
Date:   Thu Aug 20 19:39:50 2009 +0200

    HTTP uses the specified handler for MIME types.

diff --git a/myserver/src/protocol/http/http.cpp 
b/myserver/src/protocol/http/http.cpp
index a423d5e..54d60c2 100644
--- a/myserver/src/protocol/http/http.cpp
+++ b/myserver/src/protocol/http/http.cpp
@@ -1554,12 +1554,14 @@ Internal Server Error\n\
  */
 MimeRecord* Http::getMIME (string &filename)
 {
+  /*TODO: document the "mime.handler" option.  */
+  const char *handler = td->securityToken.getHashedData ("mime.handler",
+                      MYSERVER_VHOST_CONF | MYSERVER_SERVER_CONF, NULL);
+
   if (staticHttp.allowVhostMime && td->connection->host->isMIME ())
-    {
-      return td->connection->host->getMIME ()->getMIME (filename);
-    }
+    return td->connection->host->getMIME ()->getMIME (filename);
 
-  return Server::getInstance ()->getMimeManager ()->getMIME (filename);
+  return Server::getInstance ()->getMimeManager ()->getMIME (filename, 
handler);
 }
 
 /*!



commit be666de939f6e5c037f0ae4a392f17bf2684a636
Author: Giuseppe Scrivano <address@hidden>
Date:   Thu Aug 20 19:33:54 2009 +0200

    The MimeManager can have external handlers now.

diff --git a/myserver/include/conf/mime/mime_manager.h 
b/myserver/include/conf/mime/mime_manager.h
index a626f6b..96b35db 100644
--- a/myserver/include/conf/mime/mime_manager.h
+++ b/myserver/include/conf/mime/mime_manager.h
@@ -27,16 +27,19 @@ along with this program.  If not, see 
<http://www.gnu.org/licenses/>.
 
 
 #ifdef WIN32
-#include <windows.h>
+# include <windows.h>
 #endif
-extern "C" {
+
+extern "C"
+{
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
 #include <ctype.h>
+
 #ifdef WIN32
-#include <tchar.h>
-#include <io.h>
+# include <tchar.h>
+# include <io.h>
 #endif
 }
 
@@ -72,6 +75,15 @@ struct MimeRecord
   const char* getHashedData(string &name);
 };
 
+
+class MimeManagerHandler
+{
+public:
+       virtual MimeRecord* getMIME (const char *file){return NULL;}
+  virtual MimeRecord* getMIME (string const &file)
+  {return getMIME (file.c_str ());}
+};
+
 class MimeManager
 {
 public:
@@ -81,11 +93,10 @@ public:
 
   u_long loadXML (XmlParser* parser);
        u_long loadXML (const char *filename);
-       u_long loadXML (string &filename)
-    {return loadXML (filename.c_str ());}
+       u_long loadXML (string &filename) {return loadXML (filename.c_str ());}
 
-       MimeRecord* getMIME (const char *ext);
-  MimeRecord* getMIME (string const &ext);
+       MimeRecord* getMIME (const char *file, const char *handler = NULL);
+  MimeRecord* getMIME (string const &file, const char *handler = NULL);
 
   bool isLoaded ();
        void clean ();
@@ -93,10 +104,14 @@ public:
 
   static MimeRecord *readRecord (xmlNodePtr node);
 
+  void registerHandler (string &name, MimeManagerHandler *handler);
+
 protected:
        const char *getFilename ();
        void clearRecords ();
+
 private:
+  HashMap<string, MimeManagerHandler*> handlers;
   bool loaded;
   HashMap<string, int> extIndex;
   vector<MimeRecord*> records;
@@ -106,4 +121,4 @@ private:
        string filename;
 };
 
-#endif 
+#endif
diff --git a/myserver/src/conf/mime/mime_manager.cpp 
b/myserver/src/conf/mime/mime_manager.cpp
index 53392e7..e1c1b72 100644
--- a/myserver/src/conf/mime/mime_manager.cpp
+++ b/myserver/src/conf/mime/mime_manager.cpp
@@ -26,7 +26,7 @@ along with this program.  If not, see 
<http://www.gnu.org/licenses/>.
 #include <algorithm>
 
 #ifdef WIN32
-#define MIME_LOWER_CASE
+# define MIME_LOWER_CASE
 #endif
 
 using namespace std;
@@ -42,7 +42,7 @@ MimeRecord::MimeRecord ()
 }
 
 /*!
- *Destroy the object.
+ * Destroy the object.
  */
 MimeRecord::~MimeRecord ()
 {
@@ -50,32 +50,33 @@ MimeRecord::~MimeRecord ()
 }
 
 /*!
- *Add a filter to the list of filters to apply on this MIME type.
- *Return zero if the filters was not added.
+ * Add a filter to the list of filters to apply on this MIME type.
+ * Return zero if the filters was not added.
  */
-int MimeRecord::addFilter (const char* n, bool acceptDuplicate) 
+int MimeRecord::addFilter (const char* n, bool acceptDuplicate)
 {
-  if(!acceptDuplicate)
+  if (!acceptDuplicate)
   {
-    list<string>::iterator i = filters.begin();
-    for( ; i != filters.end() ;i++ )
+    list<string>::iterator i = filters.begin ();
+    for (; i != filters.end (); i++)
     {
-      if(!stringcmpi(*i, n))
+      if (!stringcmpi (*i, n))
         return 0;
     }
   }
-  filters.push_back(n);
+
+  filters.push_back (n);
   return 1;
 }
 
 /*!
- *Copy constructor.
+ * Copy constructor.
  */
 MimeRecord::MimeRecord (MimeRecord& m)
 {
   list<string>::iterator i = m.filters.begin ();
 
-  filters.clear (); 
+  filters.clear ();
 
   for( ; i != m.filters.end (); i++)
   {
@@ -84,7 +85,7 @@ MimeRecord::MimeRecord (MimeRecord& m)
 
   i = m.extensions.begin ();
 
-  extensions.clear (); 
+  extensions.clear ();
 
   for( ; i != m.extensions.end (); i++)
   {
@@ -95,7 +96,7 @@ MimeRecord::MimeRecord (MimeRecord& m)
   mimeType.assign (m.mimeType);
   cmdName.assign (m.cmdName);
   cgiManager.assign (m.cgiManager);
-} 
+}
 
 /*!
   *Clear the used memory.
@@ -104,30 +105,30 @@ void MimeRecord::clear ()
 {
   filters.clear ();
   extensions.clear ();
-  mimeType.assign (""); 
+  mimeType.assign ("");
   cmdName.assign ("");
   cgiManager.assign ("");
 
-  for (list<Regex*>::iterator it = pathRegex.begin (); 
-       it != pathRegex.end (); 
+  for (list<Regex*>::iterator it = pathRegex.begin ();
+       it != pathRegex.end ();
        it++)
   {
     delete *it;
   }
 
-  HashMap<string, string*>::Iterator it = hashedData.begin();
-  for (;it != hashedData.end(); it++)
+  HashMap<string, string*>::Iterator it = hashedData.begin ();
+  for (;it != hashedData.end (); it++)
   {
     delete (*it);
   }
-  hashedData.clear();
+  hashedData.clear ();
 
 
   pathRegex.clear ();
-}  
+}
 
 /*!
- *Get the value stored in the hash dictionary for the `name' key.
+ * Get the value stored in the hash dictionary for the `name' key.
  */
 const char* MimeRecord::getHashedData(string &name)
 {
@@ -139,15 +140,15 @@ const char* MimeRecord::getHashedData(string &name)
 }
 
 /*!
- *Get the name of the file opened by the class.
+ * Get the name of the used file.
  */
 const char *MimeManager::getFilename ()
 {
-  return filename.c_str();
+  return filename.c_str ();
 }
 
 /*!
- *Read a MIME record from a XML node.
+ * Read a MIME record from a XML node.
  */
 MimeRecord *MimeManager::readRecord (xmlNodePtr node)
 {
@@ -158,30 +159,27 @@ MimeRecord *MimeManager::readRecord (xmlNodePtr node)
 
   for (attrs = node->properties; attrs; attrs = attrs->next)
   {
-    if (!xmlStrcmp (attrs->name, (const xmlChar *)"handler") && 
+    if (!xmlStrcmp (attrs->name, (const xmlChar *)"handler") &&
         attrs->children && attrs->children->content)
       rc->cmdName.assign ((const char*)attrs->children->content);
- 
-    if (!xmlStrcmp (attrs->name, (const xmlChar *)"self") && 
+
+    if (!xmlStrcmp (attrs->name, (const xmlChar *)"self") &&
         attrs->children && attrs->children->content)
-      rc->selfExecuted = xmlStrcmp (attrs->children->content, 
+      rc->selfExecuted = xmlStrcmp (attrs->children->content,
                                     (const xmlChar *)"YES");
-   
-    if (!xmlStrcmp (attrs->name, (const xmlChar *)"param") && 
+
+    if (!xmlStrcmp (attrs->name, (const xmlChar *)"param") &&
         attrs->children && attrs->children->content)
       rc->cgiManager.assign ((const char*)attrs->children->content);
   }
 
-
- 
-
   for ( ;lcur; lcur = lcur->next)
   {
     if (lcur->name && !xmlStrcmp(lcur->name, (const xmlChar *)"EXTENSION"))
     {
       for (attrs = lcur->properties; attrs; attrs = attrs->next)
       {
-        if (!xmlStrcmp (attrs->name, (const xmlChar *)"value") && 
+        if (!xmlStrcmp (attrs->name, (const xmlChar *)"value") &&
             attrs->children && attrs->children->content)
         {
           string ext ((const char*)attrs->children->content);
@@ -197,11 +195,11 @@ MimeRecord *MimeManager::readRecord (xmlNodePtr node)
 
       for (attrs = lcur->properties; attrs; attrs = attrs->next)
       {
-        if (!xmlStrcmp (attrs->name, (const xmlChar *)"name") && 
+        if (!xmlStrcmp (attrs->name, (const xmlChar *)"name") &&
             attrs->children && attrs->children->content)
           name = (const char*)attrs->children->content;
 
-        if (!xmlStrcmp (attrs->name, (const xmlChar *)"value") && 
+        if (!xmlStrcmp (attrs->name, (const xmlChar *)"value") &&
             attrs->children && attrs->children->content)
           value = (const char*)attrs->children->content;
       }
@@ -219,7 +217,7 @@ MimeRecord *MimeManager::readRecord (xmlNodePtr node)
     {
       for (attrs = lcur->properties; attrs; attrs = attrs->next)
       {
-        if (!xmlStrcmp (attrs->name, (const xmlChar *)"regex") && 
+        if (!xmlStrcmp (attrs->name, (const xmlChar *)"regex") &&
             attrs->children && attrs->children->content)
         {
           Regex *r = new Regex;
@@ -236,11 +234,9 @@ MimeRecord *MimeManager::readRecord (xmlNodePtr node)
     {
       for (attrs = lcur->properties; attrs; attrs = attrs->next)
       {
-        if (!xmlStrcmp (attrs->name, (const xmlChar *)"value") && 
+        if (!xmlStrcmp (attrs->name, (const xmlChar *)"value") &&
             attrs->children && attrs->children->content)
-        {
           rc->addFilter ((const char*)attrs->children->content);
-        }
       }
     }
   }
@@ -249,8 +245,8 @@ MimeRecord *MimeManager::readRecord (xmlNodePtr node)
 }
 
 /*!
- *Load the MIME types from a XML file. Returns the number of
- *MIME types loaded successfully.
+ * Load the MIME types from a XML file. Returns the number of
+ * MIME types loaded successfully.
  */
 u_long MimeManager::loadXML (const char *fn)
 {
@@ -265,15 +261,15 @@ u_long MimeManager::loadXML (const char *fn)
   filename.assign (fn);
 
   ret = loadXML (&parser);
-  
+
   parser.close ();
-  
+
   return ret;
 }
 
 /*!
- *Load the MIME types from a XML parser object. Returns the number 
- *of MIME types loaded successfully.
+ * Load the MIME types from a XML parser object. Returns the number
+ * of MIME types loaded successfully.
  */
 u_long MimeManager::loadXML (XmlParser* parser)
 {
@@ -282,12 +278,12 @@ u_long MimeManager::loadXML (XmlParser* parser)
 
   clearRecords ();
 
-  doc = parser->getDoc();
+  doc = parser->getDoc ();
   node = doc->children->children;
 
-  for(; node; node = node->next )
+  for (; node; node = node->next)
   {
-    if(xmlStrcmp(node->name, (const xmlChar *)"MIME"))
+    if (xmlStrcmp (node->name, (const xmlChar *)"MIME"))
       continue;
 
     MimeRecord *rc = readRecord (node);
@@ -295,7 +291,7 @@ u_long MimeManager::loadXML (XmlParser* parser)
     if (rc)
       addRecord (rc);
   }
-  
+
   /*! Store the loaded status. */
   loaded = true;
 
@@ -303,7 +299,7 @@ u_long MimeManager::loadXML (XmlParser* parser)
 }
 
 /*!
- *Destroy the object.
+ * Destroy the object.
  */
 MimeManager::~MimeManager ()
 {
@@ -311,7 +307,7 @@ MimeManager::~MimeManager ()
 }
 
 /*!
- *Clean the memory allocated by the structure.
+ * Clean the memory allocated by the structure.
  */
 void MimeManager::clean ()
 {
@@ -324,7 +320,7 @@ void MimeManager::clean ()
 }
 
 /*!
- *Constructor of the class.
+ * Constructor of the class.
  */
 MimeManager::MimeManager ()
 {
@@ -332,8 +328,8 @@ MimeManager::MimeManager ()
 }
 
 /*!
- *Add a new record.
- *\return Return the position for the new record.
+ * Add a new record.
+ * \return Return the position for the new record.
  */
 int MimeManager::addRecord (MimeRecord *mr)
 {
@@ -341,54 +337,53 @@ int MimeManager::addRecord (MimeRecord *mr)
 
   records.push_back (mr);
 
-  for (list<string>::iterator it = mr->extensions.begin (); it != 
mr->extensions.end (); it++)
-  {
-    string &ext = *it;
+  for (list<string>::iterator it = mr->extensions.begin ();
+       it != mr->extensions.end (); it++)
+    {
+      string &ext = *it;
 
 #ifdef MIME_LOWER_CASE
-    transform (ext.begin(), ext.end(), ext.begin(), ::tolower);
+      transform (ext.begin(), ext.end(), ext.begin(), ::tolower);
 #endif
+      extIndex.put (ext, position);
+    }
 
-    extIndex.put (ext, position);
-  }
-
-  for (list<Regex*>::iterator it = mr->pathRegex.begin (); 
-       it != mr->pathRegex.end (); 
-       it++)
-  {
-    PathRegex *pr = new PathRegex;
-    pr->regex = *it;
-    pr->record = position;
+  for (list<Regex*>::iterator it = mr->pathRegex.begin ();
+       it != mr->pathRegex.end (); it++)
+    {
+      PathRegex *pr = new PathRegex;
+      pr->regex = *it;
+      pr->record = position;
 
-    pathRegex.push_back (pr);
-  }
+      pathRegex.push_back (pr);
+    }
 
   return position;
 }
 
 /*!
- *Remove all the stored records.
+ * Remove all the stored records.
  */
 void MimeManager::clearRecords ()
 {
   vector <MimeRecord*>::iterator i = records.begin ();
 
   while (i != records.end ())
-  {
-    MimeRecord *r = *i;
+    {
+      MimeRecord *r = *i;
+      if (r)
+        delete r;
+      i++;
+    }
 
-    if (r)
-      delete r;
-    
-    i++;
-  }
+  for (list<PathRegex*>::iterator it = pathRegex.begin ();
+       it != pathRegex.end (); it++)
+    delete *it;
 
-  for (list<PathRegex*>::iterator it = pathRegex.begin (); 
-       it != pathRegex.end (); 
-       it++)
-  {
+
+  for (HashMap<string, MimeManagerHandler*>::Iterator it = handlers.begin ();
+       it != handlers.end (); it++)
     delete *it;
-  }
 
   pathRegex.clear ();
   records.clear ();
@@ -400,51 +395,76 @@ void MimeManager::clearRecords ()
 }
 
 /*!
- *Get the MIME type to use on the specified file.
+ * Get the MIME type to use on the specified file.
+ * \param filename Find the MIME type for this file.
+ * \param handler If specified, indicate an external handler to use
+ * if the mime cannot be found locally.
  */
-MimeRecord *MimeManager::getMIME (const char *filename)
+MimeRecord *MimeManager::getMIME (string const &filename, const char *handler)
 {
-  string str (filename);
-  return getMIME (filename);
+  return getMIME (filename.c_str ());
 }
 
 /*!
- *Get the MIME type to use on the specified file.
+ * Get the MIME type to use on the specified file.
+ * \param filename Find the MIME type for this file.
+ * \param handler If specified, indicate an external handler to use
+ * if the mime cannot be found locally.
  */
-MimeRecord *MimeManager::getMIME (string const &filename)
+MimeRecord *MimeManager::getMIME (const char *filename, const char *handler)
 {
   string ext;
   u_long pos = 0;
-  
 
-  for (list<PathRegex*>::iterator it = pathRegex.begin (); 
-       it != pathRegex.end (); 
+
+  for (list<PathRegex*>::iterator it = pathRegex.begin ();
+       it != pathRegex.end ();
        it++)
   {
     PathRegex *pr = *it;
     regmatch_t pm;
 
-    if (pr->regex->exec(filename.c_str (), 1, &pm, 0) == 0)
+    if (pr->regex->exec (filename, 1, &pm, 0) == 0)
     {
       pos = pr->record;
       break;
     }
   }
- 
+
   if (pos == 0)
-  {
-    FilesUtility::getFileExt (ext, filename);
-    pos = extIndex.get (ext.c_str ());
-  }
+    {
+      FilesUtility::getFileExt (ext, filename);
+      pos = extIndex.get (ext.c_str ());
+    }
 
   if (pos)
     return records [pos];
 
+  if (handler)
+    {
+      MimeManagerHandler *h = handlers.get (handler);
+      if (h)
+        return h->getMIME (filename);
+    }
+
   return NULL;
 }
 
 /*!
- *Returns the number of MIME types loaded.
+ * Register an external handler under the specified name.
+ *
+ * \param name Handler name.
+ * \param handler Handler object to register.
+ */
+void MimeManager::registerHandler (string &name, MimeManagerHandler *handler)
+{
+  MimeManagerHandler *old = handlers.put (name, handler);
+  if (old)
+    delete old;
+}
+
+/*!
+ * Returns the number of MIME types loaded.
  */
 u_long MimeManager::getNumMIMELoaded ()
 {
@@ -452,7 +472,7 @@ u_long MimeManager::getNumMIMELoaded ()
 }
 
 /*!
- *Check if the MIME manager is loaded.
+ * Check if the MIME manager is loaded.
  */
 bool MimeManager::isLoaded ()
 {

-----------------------------------------------------------------------

Summary of changes:
 myserver/include/conf/mime/mime_manager.h          |   33 ++-
 myserver/src/base/dynamic_lib/dynamiclib.cpp       |   55 ++--
 myserver/src/conf/mime/mime_manager.cpp            |  223 ++++++++------
 myserver/src/plugin/plugin.cpp                     |    1 -
 myserver/src/plugin/plugins_manager.cpp            |   15 +-
 myserver/src/protocol/http/http.cpp                |   10 +-
 plugins/src/mime_magic/.svn/dir-prop-base          |    5 +
 plugins/src/mime_magic/.svn/entries                |  198 ++++++++++++
 plugins/src/mime_magic/.svn/format                 |    1 +
 .../.svn/text-base/README.svn-base}                |    0
 .../.svn/text-base/SConscript.svn-base}            |    0
 .../.svn/text-base/http_checker.cpp.svn-base       |  326 ++++++++++++++++++++
 .../.svn/text-base/http_rules_sample.py.svn-base}  |    0
 .../.svn/text-base/plugin.xml.svn-base}            |    4 +-
 plugins/src/mime_magic/README                      |    5 +
 .../src/{rules_checker => mime_magic}/SConscript   |   11 +-
 plugins/src/mime_magic/mime_magic.cpp              |  132 ++++++++
 plugins/src/mime_magic/plugin.xml                  |    9 +
 18 files changed, 871 insertions(+), 157 deletions(-)
 create mode 100755 plugins/src/mime_magic/.svn/dir-prop-base
 create mode 100755 plugins/src/mime_magic/.svn/entries
 create mode 100755 plugins/src/mime_magic/.svn/format
 copy plugins/src/{http_checker/README => 
mime_magic/.svn/text-base/README.svn-base} (100%)
 mode change 100644 => 100755
 copy plugins/src/{http_checker/SConscript => 
mime_magic/.svn/text-base/SConscript.svn-base} (100%)
 mode change 100644 => 100755
 create mode 100755 
plugins/src/mime_magic/.svn/text-base/http_checker.cpp.svn-base
 copy plugins/src/{http_checker/http_rules_sample.py => 
mime_magic/.svn/text-base/http_rules_sample.py.svn-base} (100%)
 mode change 100644 => 100755
 copy plugins/src/{http_checker/plugin.xml => 
mime_magic/.svn/text-base/plugin.xml.svn-base} (72%)
 mode change 100644 => 100755
 create mode 100755 plugins/src/mime_magic/README
 copy plugins/src/{rules_checker => mime_magic}/SConscript (65%)
 mode change 100644 => 100755
 create mode 100755 plugins/src/mime_magic/mime_magic.cpp
 create mode 100755 plugins/src/mime_magic/plugin.xml


hooks/post-receive
-- 
GNU MyServer




reply via email to

[Prev in Thread] Current Thread [Next in Thread]