View Issue Details

IDProjectCategoryView StatusLast Update
0002126libmicrohttpdpostprocessorpublic2012-01-31 16:52
Reporterwoof Assigned ToChristian Grothoff Due Date
PrioritynormalSeverityminorReproducibilityalways
Status closedResolutionfixed 
Product Version0.9.18 
Summary0002126: Per RFC2046, libmicrohttpd needs to handle garbage prior to first multipart boundary
DescriptionRFC2046 includes the following in 5.1.1 NOTE TO IMPLEMENTORS:

There appears to be room for additional information prior to the first boundary delimiter line and following the final boundary delimiter line. These areas should generally be left blank, and implementations must ignore anything that appears before the first boundary delimiter line or after the last one.

If anything precedes the first boundary delimiter, libmicrohttpd rejects the entire post.
Steps To ReproduceSend a multipart post with extra information before the first boundary, such as:

POST /somedata HTTP/1.1

Accept-Encoding: gzip,deflate

Content-Type: multipart/form-data; boundary=xyzzy

Content-Length: 187


Here is some extra data before the first boundary


--xyzzy

Content-Disposition: form-data; name="username"



barney

--xyzzy

Content-Disposition: form-data; name="password"



fife
Additional InformationI've coded a fix for this (see attached patch) that you can use or modify as you see fit.
TagsNo tags attached.
Attached Files
patch (2,764 bytes)   
--- postprocessor.c.orig	2012-01-30 10:05:44.000000000 -0700
+++ postprocessor.c	2012-01-30 10:06:35.000000000 -0700
@@ -39,6 +39,7 @@ enum PP_State
   PP_Error,
   PP_Done,
   PP_Init,
+  PP_NextBoundary,
 
   /* url encoding-states */
   PP_ProcessValue,
@@ -492,7 +493,8 @@ find_boundary (struct MHD_PostProcessor 
     }
   if ((0 != memcmp ("--", buf, 2)) || (0 != memcmp (&buf[2], boundary, blen)))
     {
-      pp->state = PP_Error;
+      if (pp->state != PP_Init)
+        pp->state = PP_Error;
       return MHD_NO;            /* expected boundary */
     }
   /* remove boundary from buffer */
@@ -823,6 +825,25 @@ post_process_multipart (struct MHD_PostP
           pp->state = PP_Error;
           return MHD_NO;
         case PP_Init:
+          /**
+           * Per RFC2046 5.1.1 NOTE TO IMPLEMENTORS, consume anything
+           * prior to the first multipart boundary:
+           *
+           * > There appears to be room for additional information prior
+           * > to the first boundary delimiter line and following the
+           * > final boundary delimiter line.  These areas should
+           * > generally be left blank, and implementations must ignore
+           * > anything that appears before the first boundary delimiter
+           * > line or after the last one.
+           */
+          if (MHD_NO == find_boundary (pp,
+                                       pp->boundary,
+                                       pp->blen,
+                                       &ioff,
+                                       PP_ProcessEntryHeaders, PP_Done))
+            ++ioff;
+          break;
+        case PP_NextBoundary:
           if (MHD_NO == find_boundary (pp,
                                        pp->boundary,
                                        pp->blen,
@@ -914,7 +935,7 @@ post_process_multipart (struct MHD_PostP
                                        pp->nlen,
                                        &ioff,
                                        PP_Nested_PerformMarking,
-                                       PP_Init /* or PP_Error? */ ))
+                                       PP_NextBoundary /* or PP_Error? */ ))
             {
               if (pp->state == PP_Error)
                 return MHD_NO;
@@ -955,7 +976,7 @@ post_process_multipart (struct MHD_PostP
                                                    pp->nested_boundary,
                                                    pp->nlen,
                                                    PP_Nested_PerformCleanup,
-                                                   PP_Init))
+                                                   PP_NextBoundary))
             {
               if (pp->state == PP_Error)
                 return MHD_NO;
patch (2,764 bytes)   

Activities

Christian Grothoff

2012-01-30 19:04

manager   ~0005406

Fixed in SVN 19546.

Issue History

Date ModifiedUsernameFieldChange
2012-01-30 17:25woofNew Issue
2012-01-30 17:25woofFile Added: patch
2012-01-30 18:50Christian GrothoffAssigned To => Christian Grothoff
2012-01-30 18:50Christian GrothoffStatusnew => assigned
2012-01-30 19:04Christian GrothoffNote Added: 0005406
2012-01-30 19:04Christian GrothoffStatusassigned => resolved
2012-01-30 19:04Christian GrothoffResolutionopen => fixed
2012-01-31 16:52Christian GrothoffStatusresolved => closed
2013-05-06 10:53Christian GrothoffCategorypostprocessor => libmicrohttpd postprocessor
2024-01-21 12:24Christian GrothoffCategorylibmicrohttpd postprocessor => postprocessor