Diff for /embedaddon/miniupnpd/upnpevents.c between versions 1.1.1.2 and 1.1.1.3

version 1.1.1.2, 2012/05/29 12:55:57 version 1.1.1.3, 2013/07/22 00:32:35
Line 1 Line 1
 /* $Id$ */  /* $Id$ */
 /* MiniUPnP project  /* MiniUPnP project
  * http://miniupnp.free.fr/ or http://miniupnp.tuxfamily.org/   * http://miniupnp.free.fr/ or http://miniupnp.tuxfamily.org/
 * (c) 2008-2011 Thomas Bernard * (c) 2008-2012 Thomas Bernard
  * This software is subject to the conditions detailed   * This software is subject to the conditions detailed
  * in the LICENCE file provided within the distribution */   * in the LICENCE file provided within the distribution */
   
Line 16 Line 16
 #include <sys/socket.h>  #include <sys/socket.h>
 #include <netinet/in.h>  #include <netinet/in.h>
 #include <arpa/inet.h>  #include <arpa/inet.h>
 #include <fcntl.h>  
 #include <errno.h>  #include <errno.h>
 #include "config.h"  #include "config.h"
 #include "upnpevents.h"  #include "upnpevents.h"
 #include "miniupnpdpath.h"  #include "miniupnpdpath.h"
 #include "upnpglobalvars.h"  #include "upnpglobalvars.h"
 #include "upnpdescgen.h"  #include "upnpdescgen.h"
   #include "upnputils.h"
   
 #ifdef ENABLE_EVENTS  #ifdef ENABLE_EVENTS
 /*enum subscriber_service_enum {  /*enum subscriber_service_enum {
Line 94  newSubscriber(const char * eventurl, const char * call Line 94  newSubscriber(const char * eventurl, const char * call
         else if(strcmp(eventurl, L3F_EVENTURL)==0)          else if(strcmp(eventurl, L3F_EVENTURL)==0)
                 tmp->service = EL3F;                  tmp->service = EL3F;
 #endif  #endif
   #ifdef ENABLE_6FC_SERVICE
           else if(strcmp(eventurl, WANIP6FC_EVENTURL)==0)
                   tmp->service = E6FC;
   #endif
   #ifdef ENABLE_DP_SERVICE
           else if(strcmp(eventurl, DP_EVENTURL)==0)
                   tmp->service = EDP;
   #endif
         else {          else {
                 free(tmp);                  free(tmp);
                 return NULL;                  return NULL;
Line 140  renewSubscription(const char * sid, int sidlen, int ti Line 148  renewSubscription(const char * sid, int sidlen, int ti
 {  {
         struct subscriber * sub;          struct subscriber * sub;
         for(sub = subscriberlist.lh_first; sub != NULL; sub = sub->entries.le_next) {          for(sub = subscriberlist.lh_first; sub != NULL; sub = sub->entries.le_next) {
                if(memcmp(sid, sub->uuid, 41) == 0) {                if((sidlen == 41) && (memcmp(sid, sub->uuid, 41) == 0)) {
                         sub->timeout = (timeout ? time(NULL) + timeout : 0);                          sub->timeout = (timeout ? time(NULL) + timeout : 0);
                         return 0;                          return 0;
                 }                  }
Line 155  upnpevents_removeSubscriber(const char * sid, int sidl Line 163  upnpevents_removeSubscriber(const char * sid, int sidl
         if(!sid)          if(!sid)
                 return -1;                  return -1;
         for(sub = subscriberlist.lh_first; sub != NULL; sub = sub->entries.le_next) {          for(sub = subscriberlist.lh_first; sub != NULL; sub = sub->entries.le_next) {
                if(memcmp(sid, sub->uuid, 41) == 0) {                if((sidlen == 41) && (memcmp(sid, sub->uuid, 41) == 0)) {
                         if(sub->notify) {                          if(sub->notify) {
                                 sub->notify->sub = NULL;                                  sub->notify->sub = NULL;
                         }                          }
Line 184  static void Line 192  static void
 upnp_event_create_notify(struct subscriber * sub)  upnp_event_create_notify(struct subscriber * sub)
 {  {
         struct upnp_event_notify * obj;          struct upnp_event_notify * obj;
        int flags;
         obj = calloc(1, sizeof(struct upnp_event_notify));          obj = calloc(1, sizeof(struct upnp_event_notify));
         if(!obj) {          if(!obj) {
                 syslog(LOG_ERR, "%s: calloc(): %m", "upnp_event_create_notify");                  syslog(LOG_ERR, "%s: calloc(): %m", "upnp_event_create_notify");
Line 202  upnp_event_create_notify(struct subscriber * sub) Line 210  upnp_event_create_notify(struct subscriber * sub)
                 syslog(LOG_ERR, "%s: socket(): %m", "upnp_event_create_notify");                  syslog(LOG_ERR, "%s: socket(): %m", "upnp_event_create_notify");
                 goto error;                  goto error;
         }          }
        if((flags = fcntl(obj->s, F_GETFL, 0)) < 0) {        if(!set_non_blocking(obj->s)) {
                syslog(LOG_ERR, "%s: fcntl(..F_GETFL..): %m",                syslog(LOG_ERR, "%s: set_non_blocking(): %m",
                        "upnp_event_create_notify");                         "upnp_event_create_notify");
                 goto error;                  goto error;
         }          }
         if(fcntl(obj->s, F_SETFL, flags | O_NONBLOCK) < 0) {  
                 syslog(LOG_ERR, "%s: fcntl(..F_SETFL..): %m",  
                        "upnp_event_create_notify");  
                 goto error;  
         }  
         if(sub)          if(sub)
                 sub->notify = obj;                  sub->notify = obj;
         LIST_INSERT_HEAD(&notifylist, obj, entries);          LIST_INSERT_HEAD(&notifylist, obj, entries);
Line 225  error: Line 228  error:
 static void  static void
 upnp_event_notify_connect(struct upnp_event_notify * obj)  upnp_event_notify_connect(struct upnp_event_notify * obj)
 {  {
        int i;        unsigned int i;
         const char * p;          const char * p;
         unsigned short port;          unsigned short port;
 #ifdef ENABLE_IPV6  #ifdef ENABLE_IPV6
Line 304  upnp_event_notify_connect(struct upnp_event_notify * o Line 307  upnp_event_notify_connect(struct upnp_event_notify * o
   
 static void upnp_event_prepare(struct upnp_event_notify * obj)  static void upnp_event_prepare(struct upnp_event_notify * obj)
 {  {
        static const char notifymsg[] =         static const char notifymsg[] =
                 "NOTIFY %s HTTP/1.1\r\n"                  "NOTIFY %s HTTP/1.1\r\n"
                 "Host: %s%s\r\n"                  "Host: %s%s\r\n"
                 "Content-Type: text/xml\r\n"                  "Content-Type: text/xml\r\n"
Line 351  static void upnp_event_prepare(struct upnp_event_notif Line 354  static void upnp_event_prepare(struct upnp_event_notif
         }          }
         obj->buffersize = 1024;          obj->buffersize = 1024;
         obj->buffer = malloc(obj->buffersize);          obj->buffer = malloc(obj->buffersize);
        /*if(!obj->buffer) {        if(!obj->buffer) {
        }*/                syslog(LOG_ERR, "%s: malloc returned NULL", "upnp_event_prepare");
                 if(xml) {
                         free(xml);
                 }
                 obj->state = EError;
                 return;
         }
         obj->tosend = snprintf(obj->buffer, obj->buffersize, notifymsg,          obj->tosend = snprintf(obj->buffer, obj->buffersize, notifymsg,
                                obj->path, obj->addrstr, obj->portstr, l+2,                                 obj->path, obj->addrstr, obj->portstr, l+2,
                                obj->sub->uuid, obj->sub->seq,                                 obj->sub->uuid, obj->sub->seq,
Line 367  static void upnp_event_prepare(struct upnp_event_notif Line 376  static void upnp_event_prepare(struct upnp_event_notif
 static void upnp_event_send(struct upnp_event_notify * obj)  static void upnp_event_send(struct upnp_event_notify * obj)
 {  {
         int i;          int i;
   
         syslog(LOG_DEBUG, "%s: sending event notify message to %s:%s",          syslog(LOG_DEBUG, "%s: sending event notify message to %s:%s",
                "upnp_event_send", obj->addrstr, obj->portstr);                 "upnp_event_send", obj->addrstr, obj->portstr);
         syslog(LOG_DEBUG, "%s: msg: %s",          syslog(LOG_DEBUG, "%s: msg: %s",
                "upnp_event_send", obj->buffer + obj->sent);                 "upnp_event_send", obj->buffer + obj->sent);
         i = send(obj->s, obj->buffer + obj->sent, obj->tosend - obj->sent, 0);          i = send(obj->s, obj->buffer + obj->sent, obj->tosend - obj->sent, 0);
         if(i<0) {          if(i<0) {
                syslog(LOG_NOTICE, "%s: send(): %m", "upnp_event_send");                if(errno != EAGAIN && errno != EWOULDBLOCK && errno != EINTR) {
                obj->state = EError;                        syslog(LOG_NOTICE, "%s: send(): %m", "upnp_event_send");
                return;                        obj->state = EError;
                         return;
                 } else {
                         /* EAGAIN or EWOULDBLOCK or EINTR : no data sent */
                         i = 0;
                 }
         }          }
        else if(i != (obj->tosend - obj->sent))        if(i != (obj->tosend - obj->sent))
                 syslog(LOG_NOTICE, "%s: %d bytes send out of %d",                  syslog(LOG_NOTICE, "%s: %d bytes send out of %d",
                        "upnp_event_send", i, obj->tosend - obj->sent);                         "upnp_event_send", i, obj->tosend - obj->sent);
         obj->sent += i;          obj->sent += i;
Line 390  static void upnp_event_recv(struct upnp_event_notify * Line 405  static void upnp_event_recv(struct upnp_event_notify *
         int n;          int n;
         n = recv(obj->s, obj->buffer, obj->buffersize, 0);          n = recv(obj->s, obj->buffer, obj->buffersize, 0);
         if(n<0) {          if(n<0) {
                syslog(LOG_ERR, "%s: recv(): %m", "upnp_event_recv");                if(errno != EAGAIN &&
                obj->state = EError;                   errno != EWOULDBLOCK &&
                    errno != EINTR) {
                         syslog(LOG_ERR, "%s: recv(): %m", "upnp_event_recv");
                         obj->state = EError;
                 }
                 return;                  return;
         }          }
         syslog(LOG_DEBUG, "%s: (%dbytes) %.*s", "upnp_event_recv",          syslog(LOG_DEBUG, "%s: (%dbytes) %.*s", "upnp_event_recv",
                n, n, obj->buffer);                 n, n, obj->buffer);
           /* TODO : do something with the data recevied ?
            * right now, n (number of bytes received) is ignored
            * We may need to recv() more bytes. */
         obj->state = EFinished;          obj->state = EFinished;
         if(obj->sub)          if(obj->sub)
                 obj->sub->seq++;                  obj->sub->seq++;
Line 404  static void upnp_event_recv(struct upnp_event_notify * Line 426  static void upnp_event_recv(struct upnp_event_notify *
 static void  static void
 upnp_event_process_notify(struct upnp_event_notify * obj)  upnp_event_process_notify(struct upnp_event_notify * obj)
 {  {
           int err;
           socklen_t len;
         switch(obj->state) {          switch(obj->state) {
         case EConnecting:          case EConnecting:
                 /* now connected or failed to connect */                  /* now connected or failed to connect */
                   len = sizeof(err);
                   if(getsockopt(obj->s, SOL_SOCKET, SO_ERROR, &err, &len) < 0) {
                           syslog(LOG_ERR, "%s: getsockopt: %m", "upnp_event_process_notify");
                           obj->state = EError;
                           break;
                   }
                   if(err != 0) {
                           errno = err;
                           syslog(LOG_WARNING, "%s: connect failed: %m", "upnp_event_process_notify");
                           obj->state = EError;
                           break;
                   }
                 upnp_event_prepare(obj);                  upnp_event_prepare(obj);
                upnp_event_send(obj);                if(obj->state == ESending)
                         upnp_event_send(obj);
                 break;                  break;
         case ESending:          case ESending:
                 upnp_event_send(obj);                  upnp_event_send(obj);
Line 421  upnp_event_process_notify(struct upnp_event_notify * o Line 458  upnp_event_process_notify(struct upnp_event_notify * o
                 obj->s = -1;                  obj->s = -1;
                 break;                  break;
         default:          default:
                syslog(LOG_ERR, "upnp_event_process_notify: unknown state");                syslog(LOG_ERR, "%s: unknown state", "upnp_event_process_notify");
         }          }
 }  }
   

Removed from v.1.1.1.2  
changed lines
  Added in v.1.1.1.3


FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>