libmicrohttpd
[Top][All Lists]
Advanced

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

Re: [libmicrohttpd] MHD_create_response_from_callback


From: Christian Grothoff
Subject: Re: [libmicrohttpd] MHD_create_response_from_callback
Date: Fri, 16 Sep 2011 13:41:02 +0200
User-agent: KMail/1.13.7 (Linux/2.6.39-1-amd64; KDE/4.6.5; x86_64; ; )

On Friday, September 16, 2011 11:46:15 AM Regis Louge wrote:
> Christian,
> 
> The purpose of the Web Server is to manage Services, as it is now it
> provides an interface for the clients for them to interact with those
> services, for example a performing a HTTP GET request on a Service will
> return its value and performing a HTTP PUT request will set this value to
> the given one. The Web Server can contain a lot of Services and have a lot
> of clients.
> 
> In addition to that, one of the feature that I want to add is to be able to
> receive notifications on value changes of certain services. To do so, each
> client should be able to perform a GET on the URI "/events" in order to
> engage the connection to these notifications. Then, whenever a Service
> changes value, the server checks if the client has subscribed to that
> service's notifications, and if so, it sends him a notification of the
> value change with the new value.
> 
> For now on, this works well thanks to MHD_create_response_from_callback.
> All clients receive notifications of the services that they subscribed to
> etc...
> 
> I have to admit that the choice of defining clients with IP addresses was
> not well thought,indeed I used IP address as unique identifiers for each
> client and didn't think of all the scenarios (even though the web server
> aims at being run in a Local Area Network) I remodeled the notifications
> part on the web server using Sessions, thank you for the advice !
> 
> Nevertheless, the segmentation fault still appears when I close and reopen
> another connection, MHD tells me that it is impossible to send data due to
> a "Broken Pipe", and goes into the request_completed callback. (the same
> segmentation fault in my previous mail)
> 
> I just downgraded my MHD to 0.9.13 and it works like a charm ! (tried with
> 0.9.14 and SVN HEAD) Any idea why ?

I doubt it is the different version, you might just have gotten lucky (memory 
corruption can cause non-deterministic bugs...).  In any case, let me again 
say that  if your code still does (as you wrote earlier):

if(client->connection != NULL)
 MHD_connection_close(client->connection,
   MHD_REQUEST_TERMINATED_WITH_ERROR);

you will have problems. MHD_connection_close is not in microhttpd.h and not an 
exported symbol so client code must not use it or face the music (i.e. 
crashes).

As for 'broken pipe' -- did you ever read this? 

http://www.gnu.org/s/libmicrohttpd/microhttpd.html#SIGPIPE

If not, this might be your problem (even though it is not a SIGSEGV in that 
case, but a SIGPIPE), unless you're on GNU/Linux.  If this is not the issue, 
try using valgrind to find out more about your segfault...

Happy hacking,

Christian
 
> 
> On Thu, Sep 15, 2011 at 2:57 PM, Christian Grothoff
> 
> <address@hidden>wrote:
> > Eh, MHD_connection_close is NOT part of the public API for good reasons.
> > 
> >  You MUST not use it, the symbol is not even exported by the library.
> > 
> > Getting segmentation faults from using it yourself is expected.  Do not
> > do that.
> > 
> > Also, I am getting more an more confused about what you're trying to do.
> > Naturally you CAN get two connections from the same source IP address at
> > the same time, and your server should support that (otherwise it is
> > simply broken).  MHD has no problem handling more than one connection
> > per IP at a time either.
> > 
> > 
> > I currently can only conclude that you're trying to do something with IP
> > addresses that you should manage with sessions/cookies and that your
> > application logic is most likely severely broken (based on not
> > understanding TCP/IP and/or HTTP) and thus you're trying to do these
> > strange things and come up with odd requirements like the 'instant'
> > cleanup on connection closure.
> > 
> > TCP-FIN is not 'instant' and a browser may send us a TCP-SYN before we
> > get the FIN, right? Not to mention, what would your system do with two
> > users behind NAT using the same IP address?
> > 
> > With SVN HEAD, MHD is now calling the response destroy handler (as well
> > as the 'connection completed' handlers) as soon as the OS tells us that
> > the connection is dead.  More cannot be done, and mucking around with
> > MHD internals is not going to improve the situation.  Also, you should
> > NEVER EVER store a 'struct MHD_Connection' in your own data structures,
> > that's virtually always a bug.  Instead, store a pointer to your data
> > structures in the 'void**' you're provided by MHD.
> > 
> > Happy hacking!
> > 
> > Christian
> > 
> > On 09/15/2011 09:15 AM, Regis Louge wrote:
> >> Hi,
> >> 
> >> I have updated my version to the 0.9.14 that contains this patch
> >> (without compilation error :) ). I managed to handle the disconnection
> >> reconnection of the client by storing the MHD_Connection in my structure
> >> and closing it manually whenever a call on "/push" is made from the same
> >> IP address and a previous connection was stored :
> >> 
> >> if(client->connection != NULL)
> >> MHD_connection_close(client->**connection,
> >> MHD_REQUEST_TERMINATED_WITH_**ERROR);
> >> client->connection = connection;
> >> 
> >> Now I encounter something really weird, indeed, if a client disconnects,
> >> I can "send" him a push notification without anything happening on my
> >> web server, but when I "send" him a second one I have this weird
> >> segmentation fault in :
> >> 
> >> int MHD_connection_handle_write (struct MHD_Connection *connection)
> >> 
> >> |_switch (connection->state)
> >> |
> >>      |_case MHD_CONNECTION_CHUNKED_BODY_**READY:
> >>           |_check_write_done (connection,
> >>           |
> >>                             (connection->response->total_**size ==
> >>                             
> >>                              connection->response_write_**position) ?
> >>                             
> >>                             MHD_CONNECTION_BODY_SENT :
> >>                             MHD_CONNECTION_CHUNKED_BODY_**UNREADY);
> >> 
> >> It is right after the connection closes so connection->state is supposed
> >> to be MHD_CONNECTION_CLOSED ?
> >> 
> >> Any idea what that would happen ? And why does the first push
> >> notification attempt don't fail ?
> >> 
> >> Thanks a lot
> >> 



reply via email to

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