Diff for /parser3/src/main/pa_request.C between versions 1.180 and 1.192

version 1.180, 2001/11/14 11:36:39 version 1.192, 2002/01/21 12:10:08
Line 7 Line 7
         $Id$          $Id$
 */  */
   
 #include "pa_config_includes.h"  
   
 extern "C" unsigned char pcre_default_tables[]; // pcre/chartables.c  
   
 #include "pa_sapi.h"  #include "pa_sapi.h"
 #include "pa_common.h"  #include "pa_common.h"
 #include "pa_request.h"  #include "pa_request.h"
Line 23  extern "C" unsigned char pcre_default_ta Line 19  extern "C" unsigned char pcre_default_ta
 #include "pa_vtable.h"  #include "pa_vtable.h"
 #include "pa_vfile.h"  #include "pa_vfile.h"
 #include "pa_dictionary.h"  #include "pa_dictionary.h"
 #include "pa_charset_manager.h"  #include "pa_charsets.h"
 #include "pa_charset_connection.h"  #include "pa_charset.h"
   
 // defines  
   
 #define ORIGIN_FILE_LINE_FORMAT "%.300s(%d)"  
   
 /// content type of exception response, when no @MAIN:exception handler defined  /// content type of exception response, when no @MAIN:exception handler defined
 const char *UNHANDLED_EXCEPTION_CONTENT_TYPE="text/plain";  const char *UNHANDLED_EXCEPTION_CONTENT_TYPE="text/plain";
Line 40  const char *ORIGINS_CONTENT_TYPE="text/p Line 32  const char *ORIGINS_CONTENT_TYPE="text/p
 Methoded *MOP_create(Pool&);  Methoded *MOP_create(Pool&);
   
 static void load_charset(const Hash::Key& akey, Hash::Val *avalue,   static void load_charset(const Hash::Key& akey, Hash::Val *avalue, 
                                                                                   void *info) {                                                                                    void *) {
         Value& value=*static_cast<Value *>(avalue);          charsets->load_charset(akey, static_cast<Value *>(avalue)->as_string());
         Hash& CTYPE=*static_cast<Hash *>(info);  
   
         Charset_connection& connection=  
                 charset_manager->get_connection(akey, value.as_string());  
   
         // charset->pcre_tables   
         CTYPE.put(akey, connection.pcre_tables());  
 }  }
   
 //  //
 Request::Request(Pool& apool,  Request::Request(Pool& apool,
                                  Info& ainfo,                                   Info& ainfo,
                                  String::Untaint_lang adefault_lang,                                   uchar adefault_lang,
                                  bool status_allowed) : Pooled(apool),                                   bool status_allowed) : Pooled(apool),
         stack(apool),          stack(apool),
         OP(*MOP_create(apool)),          OP(*MOP_create(apool)),
Line 66  Request::Request(Pool& apool, Line 51  Request::Request(Pool& apool,
         response(apool),          response(apool),
         cookie(apool),          cookie(apool),
         fclasses(apool),          fclasses(apool),
         CTYPE(apool),  
         fdefault_lang(adefault_lang), flang(adefault_lang),          fdefault_lang(adefault_lang), flang(adefault_lang),
         info(ainfo),          info(ainfo),
         post_data(0), post_size(0),          post_data(0), post_size(0),
Line 74  Request::Request(Pool& apool, Line 58  Request::Request(Pool& apool,
         default_content_type(0),          default_content_type(0),
         mime_types(0),          mime_types(0),
         main_class(0),          main_class(0),
         connection(0),          fconnection(0),
         classes_conf(apool),          classes_conf(apool),
         anti_endless_execute_recoursion(0),          anti_endless_execute_recoursion(0),
         trace(apool)          trace(apool)
   #ifdef RESOURCES_DEBUG
           ,sql_connect_time(0),sql_request_time(0)
   #endif
 {  {
           // default charsets
           pool().set_source_charset(*utf8_charset);
           pool().set_client_charset(*utf8_charset);
   
         // maybe expire old caches          // maybe expire old caches
         cache_managers->maybe_expire();          cache_managers->maybe_expire();
                   
Line 111  Request::Request(Pool& apool, Line 102  Request::Request(Pool& apool,
         classes().put(math.get_class()->base()->name(), &math);           classes().put(math.get_class()->base()->name(), &math); 
 }  }
   
   Request::~Request() {
   #ifdef XML
           // if for some strange reason xml generic errors failed to be reported, free them up
           if(const char *xml_generic_errors=xmlGenericErrors()) {
                   SAPI::log(pool(), "warning: unreported xmlGenericErrors: %s", xml_generic_errors);
                   free((void *)xml_generic_errors);
           }
   #endif
   }
   
   
 /**  /**
         load MAIN class, execute @main.          load MAIN class, execute @main.
         MAIN class consists of all the auto.p files we'd manage to find          MAIN class consists of all the auto.p files we'd manage to find
Line 126  void Request::core( Line 128  void Request::core(
                                    const char *root_config_filespec, bool root_config_fail_on_read_problem,                                     const char *root_config_filespec, bool root_config_fail_on_read_problem,
                                    const char *site_config_filespec, bool site_config_fail_on_read_problem,                                     const char *site_config_filespec, bool site_config_fail_on_read_problem,
                                    bool header_only) {                                     bool header_only) {
   
   #ifdef RESOURCES_DEBUG
   //measures
   struct timeval mt[10];
   //measure:before all
   gettimeofday(&mt[0],NULL);
   #endif
         try {          try {
                 char *auto_filespec=(char *)malloc(MAX_STRING);                  char *auto_filespec=(char *)malloc(MAX_STRING);
                                   
Line 138  void Request::core( Line 147  void Request::core(
                                 true/*ignore class_path*/, root_config_fail_on_read_problem,                                  true/*ignore class_path*/, root_config_fail_on_read_problem,
                                 main_class_name, main_class);                                  main_class_name, main_class);
                 }                  }
                   // charsets must only be specified in root config
                   // so that users would not interfere
                 if(main_class) {                  if(main_class) {
                         /* $MAIN:CHARSETS[                          /* $MAIN:CHARSETS[
                                         $.charsetname1[/full/path/to/charset/file.cfg]                                          $.charsetname1[/full/path/to/charset/file.cfg]
Line 147  void Request::core( Line 157  void Request::core(
                         */                          */
                         if(Value *vcharsets=main_class->get_element(*charsets_name)) {                          if(Value *vcharsets=main_class->get_element(*charsets_name)) {
                                 if(Hash *charsets=vcharsets->get_hash(0))                                  if(Hash *charsets=vcharsets->get_hash(0))
                                         charsets->for_each(load_charset, &CTYPE);                                          charsets->for_each(load_charset);
                                 else                                  else
                                         throw Exception(0, 0,                                          throw Exception(0, 0,
                                                 &vcharsets->name(),                                                  &vcharsets->name(),
                                                 "must be hash");                                                  "must be hash");
                         }                          }
                 }                  }
   
                 // configure root options                  // configure root options
                 //      until someone with less privileges have overriden them                  //      until someone with less privileges have overriden them
                 OP.configure_admin(*this);                  OP.configure_admin(*this);
Line 210  void Request::core( Line 219  void Request::core(
                 OP.configure_user(*this);                  OP.configure_user(*this);
                 methoded_array->configure_user(*this);                  methoded_array->configure_user(*this);
   
                 // $MAIN:DEFAULTS  
                 Value *defaults=main_class->get_element(*defaults_name);  
                 // value must be allocated on request's pool for that pool used on  
                 // meaning constructing @see attributed_meaning_to_string  
                 default_content_type=defaults?defaults->get_element(*content_type_name):0;  
                 // record default charset  
                 if(default_content_type)  
                         if(Hash *hash=default_content_type->get_hash(0))  
                                 if(Value *vcharset=(Value *)hash->get(*charset_name))  
                                         pool().set_charset(vcharset->as_string());                
   
                 if(Value *element=main_class->get_element(*user_html_name))  
                         if(Table *table=element->get_table())  
                                 pool().set_tag(NEW Dictionary(*table));  
   
                 // $MAIN:MIME-TYPES                  // $MAIN:MIME-TYPES
                 if(Value *element=main_class->get_element(*mime_types_name))                  if(Value *element=main_class->get_element(*mime_types_name))
                         if(Table *table=element->get_table())                          if(Table *table=element->get_table())
Line 236  void Request::core( Line 230  void Request::core(
                 // filling cookies                  // filling cookies
                 cookie.fill_fields(*this);                  cookie.fill_fields(*this);
   
   #ifdef RESOURCES_DEBUG
   //measure:after compile
   gettimeofday(&mt[1],NULL);
   #endif
                 // execute @main[]                  // execute @main[]
                 const String *body_string=execute_virtual_method(                  const String *body_string=execute_virtual_method(*main_class, *main_method_name);
                         *main_class, *main_method_name);  
                 if(!body_string)                  if(!body_string)
                         throw Exception(0,0,                          throw Exception(0,0,
                                 0,                                   0, 
                                 "'"MAIN_METHOD_NAME"' method not found");                                  "'"MAIN_METHOD_NAME"' method not found");
   
   #ifdef RESOURCES_DEBUG
                   //measure:after main
   gettimeofday(&mt[2],NULL);
   #endif
   
                 VString body_vstring_before_post_process(*body_string);                  VString body_vstring_before_post_process(*body_string);
                 VString *body_vstring_after_post_process=&body_vstring_before_post_process;                  VString *body_vstring_after_post_process=&body_vstring_before_post_process;
                   
                 // @postprocess                  // @postprocess
                 if(Value *value=main_class->get_element(*post_process_method_name))                  if(Value *value=main_class->get_element(*post_process_method_name))
                         if(Junction *junction=value->get_junction())                          if(Junction *junction=value->get_junction())
Line 259  void Request::core( Line 260  void Request::core(
                                         frame.store_param(method->name,                                           frame.store_param(method->name, 
                                                 &body_vstring_before_post_process);                                                  &body_vstring_before_post_process);
                                         body_vstring_after_post_process=                                          body_vstring_after_post_process=
                                                 NEW VString(*execute_method(frame, *method));                                                  NEW VString(execute_method(frame, *method));
                                 }                                  }
   
                 bool origins_mode=main_class->get_element(*origins_mode_name)!=0;                  bool origins_mode=main_class->get_element(*origins_mode_name)!=0;
Line 276  void Request::core( Line 277  void Request::core(
                         response.fields().put(*content_type_name,                           response.fields().put(*content_type_name, 
                                 NEW VString(*NEW String(pool(), ORIGINS_CONTENT_TYPE)));                                  NEW VString(*NEW String(pool(), ORIGINS_CONTENT_TYPE)));
   
   #ifdef RESOURCES_DEBUG
   //measure:after postprocess
   gettimeofday(&mt[3],NULL);              
   #endif
   
                 // OK. write out the result                  // OK. write out the result
                 output_result(*body_file, header_only);                  output_result(*body_file, header_only);
   
   #ifdef RESOURCES_DEBUG
                   //measure:after output_result
   gettimeofday(&mt[9],NULL);              
   t[9]=mt[9].tv_sec+mt[9].tv_usec/1000000.0;
   
   double t[10];
   for(int i=0;i<10;i++)
       t[i]=mt[i].tv_sec+mt[i].tv_usec/1000000.0;
   //measure:log2 compile,main,postprocess,output
   SAPI::log(pool(), "rmeasure: %s,%.2f,%.2f,%.2f %.2f,%.2f %.2f", 
   info.uri,
   t[1]-t[0],
   t[2]-t[1],
   t[3]-t[2],
   sql_connect_time,sql_request_time,
   t[9]-t[3]
   );
   #endif
         } catch(const Exception& e) { // request handling problem          } catch(const Exception& e) { // request handling problem
                 // we're returning not result, but error explanation                  // we're returning not result, but error explanation
                 try {                  try {
Line 308  void Request::core( Line 333  void Request::core(
   
                         // reset language to default                          // reset language to default
                         flang=fdefault_lang;                          flang=fdefault_lang;
                         if(flang==String::UL_USER_HTML)  
                                 flang=String::UL_HTML; // no _ & Co conversions in @exception[params]  
                                                   
                         // reset response                          // reset response
                         response.fields().clear();                          response.fields().clear();
Line 410  void Request::core( Line 433  void Request::core(
   
                                                         // future $response:body=                                                          // future $response:body=
                                                         //   execute ^exception[origin;source;comment;type;code;stack]                                                          //   execute ^exception[origin;source;comment;type;code;stack]
                                                         body_string=execute_method(frame, *method);                                                          body_string=&execute_method(frame, *method);
                                                 }                                                  }
                         }                          }
                                                   
Line 482  VStateless_class *Request::use_file(cons Line 505  VStateless_class *Request::use_file(cons
                 if(main_class)                  if(main_class)
                         if(Value *element=main_class->get_element(*class_path_name)) {                          if(Value *element=main_class->get_element(*class_path_name)) {
                                 if(element->is_string()) {                                  if(element->is_string()) {
                                         file_spec=file_readable(element->as_string(), file_name); // found at class_path?                                          file_spec=file_readable(absolute(element->as_string()), file_name); // found at class_path?
                                 } else if(Table *table=element->get_table()) {                                  } else if(Table *table=element->get_table()) {
                                         int size=table->size();                                          int size=table->size();
                                         for(int i=size; i--; ) {                                          for(int i=size; i--; ) {
                                                 const String& path=*static_cast<Array *>(table->get(i))->get_string(0);                                                  const String& path=*static_cast<Array *>(table->get(i))->get_string(0);
                                                 if(file_spec=file_readable(path, file_name))                                                  if(file_spec=file_readable(absolute(path), file_name))
                                                         break; // found along class_path                                                          break; // found along class_path
                                         }                                          }
                                 } else                                  } else
Line 547  const String& Request::absolute(const St Line 570  const String& Request::absolute(const St
 static void add_header_attribute(const Hash::Key& aattribute, Hash::Val *ameaning,   static void add_header_attribute(const Hash::Key& aattribute, Hash::Val *ameaning, 
                                                                  void *info) {                                                                   void *info) {
         Request& r=*static_cast<Request *>(info);          Request& r=*static_cast<Request *>(info);
         if(aattribute==*body_name)          if(aattribute==BODY_NAME
                   || aattribute==CHARSET_NAME)
                 return;                  return;
   
         Value& lmeaning=*static_cast<Value *>(ameaning);          Value& lmeaning=*static_cast<Value *>(ameaning);
Line 584  void Request::output_result(const VFile& Line 608  void Request::output_result(const VFile&
         // prepare header: $response:fields without :body          // prepare header: $response:fields without :body
         response.fields().for_each(add_header_attribute, this);          response.fields().for_each(add_header_attribute, this);
   
         // prepare...          // transcode
         const void *body=body_file.value_ptr();          const void *client_body;
         size_t content_length=body_file.value_size();          size_t client_content_length;
           Charset::transcode(pool(),
                   pool().get_source_charset(), body_file.value_ptr(), body_file.value_size(),
                   pool().get_client_charset(), client_body, client_content_length
           );
   
         // prepare header: content-length          // prepare header: content-length
         if(content_length) { // useful for redirecting [header "location: http://..."]          if(client_content_length) { // useful for redirecting [header "location: http://..."]
                 char content_length_cstr[MAX_NUMBER];                  char content_length_cstr[MAX_NUMBER];
                 snprintf(content_length_cstr, MAX_NUMBER, "%u", content_length);                  snprintf(content_length_cstr, MAX_NUMBER, "%u", client_content_length);
                 SAPI::add_header_attribute(pool(), "content-length", content_length_cstr);                  SAPI::add_header_attribute(pool(), "content-length", content_length_cstr);
         }          }
   
Line 600  void Request::output_result(const VFile& Line 628  void Request::output_result(const VFile&
                   
         // send body          // send body
         if(!header_only)          if(!header_only)
                 SAPI::send_body(pool(), body, content_length);                  SAPI::send_body(pool(), client_body, client_content_length);
 }  }
   
 const String& Request::mime_type_of(const char *user_file_name_cstr) {  const String& Request::mime_type_of(const char *user_file_name_cstr) {
Line 617  const String& Request::mime_type_of(cons Line 645  const String& Request::mime_type_of(cons
                 }                  }
         return *NEW String(pool(), "application/octet-stream");          return *NEW String(pool(), "application/octet-stream");
 }  }
   
 const unsigned char *Request::pcre_tables() {  
         if(unsigned char *result=(unsigned char *)CTYPE.get(pool().get_charset()))  
                 return result;  
   
         // this is not for pcre itself,   
         // it can do default, it's for string.lower&co  
         return pcre_default_tables;  
 }  

Removed from v.1.180  
changed lines
  Added in v.1.192


E-mail: