Beispiel #1
0
/*=========================================================================*/
int SLPDDatabaseDeReg(SLPMessage msg)
/* Remove a service registration from the database                         */
/*                                                                         */
/* msg  - (IN) message interpreting an SrvDereg message                    */
/*                                                                         */
/* Returns  -   Zero on success.  Non-zero on failure                      */
/*=========================================================================*/
{
    SLPDatabaseHandle   dh;
    SLPDatabaseEntry*   entry;
    SLPSrvReg*          entryreg;
    SLPSrvDeReg*        dereg;

    dh = SLPDatabaseOpen(&G_SlpdDatabase.database);
    if ( dh )
    {
        /* dereg is the SrvDereg being deregistered */
        dereg = &(msg->body.srvdereg);

        /*---------------------------------------------*/
        /* Check to see if there is an identical entry */
        /*---------------------------------------------*/
        while ( 1 )
        {
            entry = SLPDatabaseEnum(dh);
            if ( entry == NULL ) break;

            /* entry reg is the SrvReg message from the database */
            entryreg = &(entry->msg->body.srvreg);

            if ( SLPCompareString(entryreg->urlentry.urllen,
                                  entryreg->urlentry.url,
                                  dereg->urlentry.urllen,
                                  dereg->urlentry.url) == 0 )
            {
                if ( SLPIntersectStringList(entryreg->scopelistlen,
                                            entryreg->scopelist,
                                            dereg->scopelistlen,
                                            dereg->scopelist) > 0 )
                {

                    /* Check to ensure the source addr is the same as */
                    /* the original */
                    if ( G_SlpdProperty.checkSourceAddr &&
                         memcmp(&(entry->msg->peer.sin_addr),
                                &(msg->peer.sin_addr),
                                sizeof(struct in_addr)) )
                    {
                        SLPDatabaseClose(dh);
                        return SLP_ERROR_AUTHENTICATION_FAILED;
                    }

#ifdef ENABLE_SLPv2_SECURITY
                    if ( entryreg->urlentry.authcount &&
                         entryreg->urlentry.authcount != dereg->urlentry.authcount )
                    {
                        SLPDatabaseClose(dh);
                        return SLP_ERROR_AUTHENTICATION_FAILED;
                    }
#endif                    
                    /* remove the registration from the database */
                    SLPDatabaseRemove(dh,entry);                   
                    SLPDLogRegistration("Deregistration",entry);
                    break;
                }
            }
        }

        SLPDatabaseClose(dh);

        if ( entry==NULL )
        {
            return SLP_ERROR_INVALID_REGISTRATION;
        }
    }

    return 0;
}
Beispiel #2
0
/** Process a DA service request message.
 *
 * @param[in] message - The message to process.
 * @param[out] sendbuf - The response buffer to fill.
 * @param[in] errorcode - The error code from the client request.
 *
 * @return Zero on success, or a non-zero SLP error on failure.
 *
 * @internal
 */
static int ProcessDASrvRqst(SLPMessage * message, SLPBuffer * sendbuf, int errorcode)
{
   SLPBuffer tmp = 0;
   SLPMessage * msg = 0;
   void * eh = 0;
   /* TODO should really be a configurable property, maybe G_SlpdProperty.MTU? Left at 4096 to retain same behaviour */
   size_t initial_buffer_size = 4096;
   size_t grow_size = initial_buffer_size;

   /* Special case for when libslp asks slpd (through the loopback) about
      a known DAs. Fill sendbuf with DAAdverts from all known DAs.        
    */
   if (SLPNetIsLoopback(&message->peer))
   {
      *sendbuf = SLPBufferRealloc(*sendbuf, initial_buffer_size);
      if (*sendbuf == 0)
         return SLP_ERROR_INTERNAL_ERROR;

      if (errorcode == 0)
      {
         /* Note: The weird *sendbuf code is making a single SLPBuffer
            that contains multiple DAAdverts.  This is a special
            process that only happens for the DA SrvRqst through
            loopback to the SLPAPI
          */

         /*If we are a DA, always have ourself at the start of the list, so the
           lib requests can be handled locally for speed */
         if(G_SlpdProperty.isDA)
         {
            struct sockaddr_storage loaddr;

            if(SLPNetIsIPV4())
            {
               int addr = INADDR_LOOPBACK;
               SLPNetSetAddr(&loaddr, AF_INET, G_SlpdProperty.port, &addr);
            }
            else
			{
               SLPNetSetAddr(&loaddr, AF_INET6, G_SlpdProperty.port, &slp_in6addr_loopback);
			}

            if(0 == SLPDKnownDAGenerateMyDAAdvert(&loaddr, 0, 0, 0, message->header.xid, &tmp))
            {
               memcpy((*sendbuf)->curpos, tmp->start, tmp->end - tmp->start);
               (*sendbuf)->curpos = ((*sendbuf)->curpos) + (tmp->end - tmp->start);
               SLPBufferFree(tmp);
               tmp = 0;
            }
			else 
			{
				SLPDLog("Unable to add initial DAAdvert due to error\n");
			}
         }

         eh = SLPDKnownDAEnumStart();
         if (eh)
         {
            while (1)
            {
               /* iterate over all database entries */
               if (SLPDKnownDAEnum(eh, &msg, &tmp) == 0) 
			   {
                  break;
			   }

               /* if we resize succesfully.. */
               if( CheckAndResizeBuffer(sendbuf, tmp, grow_size) == 0 )
               {
            	   /* buffer should now be resized to an appropriate size to handle all current database entries */

                   /* TRICKY: Fix up the XID and clear the flags. */
                   tmp->curpos = tmp->start + 10;
                   TO_UINT16(tmp->curpos, message->header.xid);
                   if (*(tmp->start) == 1)
                       *(tmp->start + 4) = 0;
                   else
                       TO_UINT16(tmp->start + 5, 0);   

    			   /* copy all data out of tmp into the sendbuf */
                   memcpy((*sendbuf)->curpos, tmp->start, tmp->end - tmp->start);
    			   /* increment the current position in sendbuf */
                   (*sendbuf)->curpos = ((*sendbuf)->curpos) + (tmp->end - tmp->start);
               }
               else
               {
            	   errorcode = SLP_ERROR_INTERNAL_ERROR;
               }
            }
            SLPDKnownDAEnumEnd(eh);
         }
 		/* tmp can store database entries which should not be freed by anyone else so reset the pointer to prevent double deletion */
 		tmp = 0;

 		/* Tack on a "terminator" DAAdvert
 		   Note that this function *always* returns the error code passed as its second parameter (or SLP_ERROR_INTERNAL_ERROR if the buffer fails to resize)
 		   The errorcode is also inserted into the srvrply header by this function
 		*/
 		SLPDKnownDAGenerateMyDAAdvert(&message->localaddr, SLP_ERROR_INTERNAL_ERROR, 0, 0, message->header.xid, &tmp);

 		/* if we resize succesfully.. */
        if ( CheckAndResizeBuffer(sendbuf, tmp, grow_size) == 0 )
        {
     		memcpy((*sendbuf)->curpos, tmp->start, tmp->end - tmp->start);
     		(*sendbuf)->curpos = ((*sendbuf)->curpos) + (tmp->end - tmp->start);

     		/* mark the end of the sendbuf */
     		(*sendbuf)->end = (*sendbuf)->curpos;

        }
        else
        {
     	   errorcode = SLP_ERROR_INTERNAL_ERROR;
        }

        SLPBufferFree(tmp);
 		tmp = 0;
      }
      return errorcode;
   }
   
   /* Normal case where a remote Agent asks for a DA */

   *sendbuf = SLPBufferRealloc(*sendbuf, G_SlpdProperty.MTU);
   if (*sendbuf == 0)
      return SLP_ERROR_INTERNAL_ERROR;
   if (G_SlpdProperty.isDA)
   {
      if (message->body.srvrqst.scopelistlen == 0 
            || SLPIntersectStringList(message->body.srvrqst.scopelistlen,
                  message->body.srvrqst.scopelist, G_SlpdProperty.useScopesLen,
                  G_SlpdProperty.useScopes))
      {
         errorcode = SLPDKnownDAGenerateMyDAAdvert(&message->localaddr, 
               errorcode, 0, 0, message->header.xid, sendbuf);           
      }
      else
         errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
   }
   else
      errorcode = SLP_ERROR_MESSAGE_NOT_SUPPORTED;       

   /* don't return errorcodes to multicast messages */
   if (errorcode != 0)
   {
      if (message->header.flags & SLP_FLAG_MCAST 
            || SLPNetIsMCast(&(message->peer)))
         (*sendbuf)->end = (*sendbuf)->start;
   }
   return errorcode;
}
Beispiel #3
0
/** Process a general service registration message.
 *
 * @param[in] message - The message to process.
 * @param[in] recvbuf - The buffer associated with @p message.
 * @param[out] sendbuf - The response buffer to fill.
 * @param[in] errorcode - The error code from the client request.
 *
 * @return A non-zero value if @p message should be silently dropped.
 *
 * @internal
 */
static int ProcessSrvReg(SLPMessage * message, SLPBuffer recvbuf, 
      SLPBuffer * sendbuf, int errorcode)
{
   SLPBuffer result = *sendbuf;

   /* If errorcode is set, we can not be sure that message is good
      Go directly to send response code  also do not process mcast
      srvreg or srvdereg messages
    */
   if (errorcode || message->header.flags & SLP_FLAG_MCAST 
         || SLPNetIsMCast(&(message->peer)))
      goto RESPOND;

   /* make sure that we handle the scope */
   if (SLPIntersectStringList(message->body.srvreg.scopelistlen, 
         message->body.srvreg.scopelist, G_SlpdProperty.useScopesLen,
         G_SlpdProperty.useScopes))
   {

#ifdef ENABLE_SLPv2_SECURITY

      /* Validate the authblocks       */
      errorcode = SLPAuthVerifyUrl(G_SlpdSpiHandle, 0,
            &message->body.srvreg.urlentry);
      if (errorcode == 0)
      {
         errorcode = SLPAuthVerifyString(G_SlpdSpiHandle, 0,
               message->body.srvreg.attrlistlen, 
               message->body.srvreg.attrlist,
               message->body.srvreg.authcount,
               message->body.srvreg.autharray);
      }
      if (errorcode == 0)
#endif
      {
         /* Put the registration in the database. */

         /* TRICKY: Remember the recvbuf was duplicated back in
          * SLPDProcessMessage 
          */
         if (SLPNetIsLoopback(&(message->peer)))
            message->body.srvreg.source= SLP_REG_SOURCE_LOCAL;
         else
            message->body.srvreg.source = SLP_REG_SOURCE_REMOTE;

         errorcode = SLPDDatabaseReg(message, recvbuf);
      }
   }
   else
      errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;

RESPOND:    

   /* don't send back reply anything multicast SrvReg (set result empty) */
   if (message->header.flags & SLP_FLAG_MCAST 
         || SLPNetIsMCast(&(message->peer)))
   {
      result->end = result->start;
      goto FINISHED;
   }

   /* ensure the buffer is big enough to handle the whole srvack */
   result = SLPBufferRealloc(result, message->header.langtaglen + 16);
   if (result == 0)
   {
      errorcode = SLP_ERROR_INTERNAL_ERROR;
      goto FINISHED;
   }

   /* Add the header */

   /* version */
   *result->curpos++ = 2;

   /* function id */
   *result->curpos++ = SLP_FUNCT_SRVACK;

   /* length */
   PutUINT24(&result->curpos, message->header.langtaglen + 16);

   /* flags */
   PutUINT16(&result->curpos, 0);

   /* ext offset */
   PutUINT24(&result->curpos, 0);

   /* xid */
   PutUINT16(&result->curpos, message->header.xid);

   /* lang tag len */
   PutUINT16(&result->curpos, message->header.langtaglen);

   /* lang tag */
   memcpy(result->curpos, message->header.langtag, 
         message->header.langtaglen);
   result->curpos += message->header.langtaglen;

   /* Add the errorcode */
   PutUINT16(&result->curpos, errorcode);

FINISHED:

   *sendbuf = result;
   return errorcode;
}
Beispiel #4
0
/*-------------------------------------------------------------------------*/
int ProcessSrvDeReg(struct sockaddr_in* peeraddr,
                    SLPMessage message,
                    SLPBuffer* sendbuf,
                    int errorcode)
/*                                                                         */
/* Returns: non-zero if message should be silently dropped                 */
/*-------------------------------------------------------------------------*/
{
    SLPBuffer result = *sendbuf;

    /*--------------------------------------------------------------*/
    /* If errorcode is set, we can not be sure that message is good */
    /* Go directly to send response code  also do not process mcast */
    /* srvreg or srvdereg messages                                  */
    /*--------------------------------------------------------------*/
    if(errorcode || message->header.flags & SLP_FLAG_MCAST)
    {
        goto RESPOND;
    }


    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------------------------------------*/
    if(SLPIntersectStringList(message->body.srvdereg.scopelistlen,
                              message->body.srvdereg.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes))
    {
        /*-------------------------------*/
        /* TODO: Validate the authblocks */
        /*-------------------------------*/

        /*--------------------------------------*/
        /* remove the service from the database */
        /*--------------------------------------*/
        if(SLPDDatabaseDeReg(&(message->body.srvdereg)) == 0)
        {
            errorcode = 0;
        }
        else
        {
            errorcode = SLP_ERROR_INTERNAL_ERROR;
        }
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    RESPOND:
    /*---------------------------------------------------------*/
    /* don't do anything multicast SrvDeReg (set result empty) */
    /*---------------------------------------------------------*/
    if(message->header.flags & SLP_FLAG_MCAST ||
       ISMCAST(peeraddr->sin_addr))
    {

        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvack */
    /*------------------------------------------------------------*/
    result = SLPBufferRealloc(result,message->header.langtaglen + 16);
    if(result == 0)
    {
        errorcode = SLP_ERROR_INTERNAL_ERROR;
        goto FINISHED;
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVACK;
    /*length*/
    ToUINT24(result->start + 2,message->header.langtaglen + 16);
    /*flags*/
    ToUINT16(result->start + 5,0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);

    /*-------------------*/
    /* Add the errorcode */
    /*-------------------*/
    ToUINT16(result->start + 14 + message->header.langtaglen, errorcode);

    FINISHED:
    *sendbuf = result;
    return errorcode;
}
Beispiel #5
0
/*-------------------------------------------------------------------------*/
int ProcessSrvTypeRqst(struct sockaddr_in* peeraddr,
                       SLPMessage message,
                       SLPBuffer* sendbuf,
                       int errorcode)
/*-------------------------------------------------------------------------*/
{
    int                     i;
    int                     size         = 0;
    int                     count        = 0;
    int                     found        = 0;
    SLPDDatabaseSrvType*    srvtypearray = 0;
    SLPBuffer               result       = *sendbuf;


    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if(SLPIntersectStringList(message->body.srvtyperqst.prlistlen,
                              message->body.srvtyperqst.prlist,
                              G_SlpdProperty.interfacesLen,
                              G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /* TODO: check the spi list of the message and return                  */
    /*       AUTHENTICATION_UNKNOWN since we do not do authentication yet  */

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if(SLPIntersectStringList(message->body.srvtyperqst.scopelistlen,
                              message->body.srvtyperqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) != 0)
    {
        /*------------------------------------*/
        /* Find service types in the database */
        /*------------------------------------*/
        while(found == count)
        {
            count += G_SlpdProperty.maxResults;

            if(srvtypearray) free(srvtypearray);
            srvtypearray = (SLPDDatabaseSrvType*)malloc(sizeof(SLPDDatabaseSrvType) * count);
            if(srvtypearray == 0)
            {
                found       = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }

            found = SLPDDatabaseFindType(&(message->body.srvtyperqst), srvtypearray, count);
            if(found < 0)
            {
                found = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }
        }

        /* remember the amount found if is really big for next time */
        if(found > G_SlpdProperty.maxResults)
        {
            G_SlpdProperty.maxResults = found;
        }
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if(found == 0 ||
       errorcode != 0)
    {
        if(message->header.flags & SLP_FLAG_MCAST ||
           ISMCAST(peeraddr->sin_addr))
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }

    /*-----------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvtyperply */
    /*-----------------------------------------------------------------*/
    size = message->header.langtaglen + 18; /* 14 bytes for header     */
                                            /*  2 bytes for error code */
                                            /*  2 bytes for srvtype
                                                list length  */
    for(i=0;i<found;i++)
    {
        size += srvtypearray[i].typelen + 1; /* 1 byte for comma  */
    }
    if(found)
        size--;         /* remove the extra comma */
    result = SLPBufferRealloc(result,size);
    if(result == 0)
    {
        found = 0;
        errorcode = SLP_ERROR_INTERNAL_ERROR;
        goto FINISHED;
    }


    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVTYPERPLY;
    /*length*/
    ToUINT24(result->start + 2,size);
    /*flags*/
    ToUINT16(result->start + 5,
             size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);

    /*-----------------------------*/
    /* Add rest of the SrvTypeRply */
    /*-----------------------------*/
    result->curpos = result->start + 14 + message->header.langtaglen;

    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos += 2;

    /* length of srvtype-list */
    ToUINT16(result->curpos, size - (message->header.langtaglen + 18));
    result->curpos += 2;

    if(errorcode == 0)
    {
        for(i=0;i<found;i++)
        {
            memcpy(result->curpos, srvtypearray[i].type,
                   srvtypearray[i].typelen);
            result->curpos += srvtypearray[i].typelen;
            if(i < found - 1)
                *result->curpos++ = ',';
        }
    }

    FINISHED:   
    if(srvtypearray) free(srvtypearray);
    *sendbuf = result;
    return errorcode;
}
Beispiel #6
0
/*=========================================================================*/
int SLPDDatabaseReg(SLPSrvReg* srvreg,
                    int fresh,
                    pid_t pid,
                    uid_t uid)
/* Add a service registration to the database                              */
/*                                                                         */
/* srvreg   -   (IN) pointer to the SLPSrvReg to be added to the database  */
/*                                                                         */
/* fresh    -   (IN) pass in nonzero if the registration is fresh.         */
/*                                                                         */
/* pid      -   (IN) process id of the process that registered the service */
/*                                                                         */
/* uid      -   (IN) user id of the user that registered the service       */
/*                                                                         */
/* Returns  -   Zero on success.  non-zero on error                        */
/*                                                                         */
/* NOTE:        All registrations are treated as fresh regardless of the   */
/*              setting of the fresh parameter                             */
/*=========================================================================*/
{
    int                result = 0;
    SLPDDatabaseEntry* entry  = (SLPDDatabaseEntry*)G_DatabaseList.head;

    /* Check to see if there is already an identical entry */
    while(entry)
    {
        if(SLPCompareString(entry->urllen,
                            entry->url,
                            srvreg->urlentry.urllen,
                            srvreg->urlentry.url) == 0)
        {
            if(SLPIntersectStringList(entry->scopelistlen,
                                      entry->scopelist,
                                      srvreg->scopelistlen,
                                      srvreg->scopelist) > 0)
            {
                SLPListUnlink(&G_DatabaseList,(SLPListItem*)entry);
                break;
            } 
        }             
        
        entry = (SLPDDatabaseEntry*) entry->listitem.next;
    }
    

    /* if no identical entry are found, create a new one */
    if(entry == 0)
    {
        entry = (SLPDDatabaseEntry*)malloc(sizeof(SLPDDatabaseEntry));
        if(entry == 0)
        {
            return -1;
        }
        memset(entry,0,sizeof(SLPDDatabaseEntry));
    }
    
    /* copy info from the message from the wire to the database entry */
    entry->pid          = pid;
    entry->uid          = uid;
    entry->scopelistlen = srvreg->scopelistlen;
    entry->scopelist    = (char*)memdup(srvreg->scopelist,srvreg->scopelistlen);
    entry->lifetime     = srvreg->urlentry.lifetime;
    entry->urllen       = srvreg->urlentry.urllen;
    entry->url          = (char*)memdup(srvreg->urlentry.url, srvreg->urlentry.urllen);
    entry->srvtypelen   = srvreg->srvtypelen;
    entry->srvtype      = (char*)memdup(srvreg->srvtype,srvreg->srvtypelen);
    entry->attrlistlen  = srvreg->attrlistlen;
    if (entry->attrlistlen)
	entry->attrlist = (char*)memdup(srvreg->attrlist,srvreg->attrlistlen);
    
    /* check for malloc() failures */
    if(entry->scopelist == 0 ||
       entry->url == 0 ||
       entry->srvtype == 0 ||
       (entry->attrlistlen && entry->attrlist == 0))
    {
        FreeEntry(entry);
        return -1;
    }
    
    /* link the new (or modified) entry into the list */
    SLPListLinkHead(&G_DatabaseList,(SLPListItem*)entry);

    /* traceReg if necessary */
    if(G_SlpdProperty.traceReg)
    {
        SLPDLogTraceReg("SrvReg", entry);
    }

    return result;
}
Beispiel #7
0
/*-------------------------------------------------------------------------*/
int ProcessSrvRqst(struct sockaddr_in* peeraddr,
                   SLPMessage message,
                   SLPBuffer* sendbuf,
                   int errorcode)
/*-------------------------------------------------------------------------*/
{
    int                     i;
    int                     size        = 0;
    int                     count       = 0;
    int                     found       = 0;
    SLPDDatabaseSrvUrl*     srvarray    = 0;
    SLPBuffer               result      = *sendbuf;

    /*--------------------------------------------------------------*/
    /* If errorcode is set, we can not be sure that message is good */
    /* Go directly to send response code                            */
    /*--------------------------------------------------------------*/
    if(errorcode)
    {
        goto RESPOND;
    }

    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if(SLPIntersectStringList(message->body.srvrqst.prlistlen,
                              message->body.srvrqst.prlist,
                              G_SlpdProperty.interfacesLen,
                              G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------------------*/
    /* Check to to see if a this is a special SrvRqst */
    /*------------------------------------------------*/
    if(SLPCompareString(message->body.srvrqst.srvtypelen,
                        message->body.srvrqst.srvtype,
                        23,
                        "service:directory-agent") == 0)
    {
        errorcode = ProcessDASrvRqst(peeraddr, message, sendbuf, errorcode);
        return errorcode;
    }
    if(SLPCompareString(message->body.srvrqst.srvtypelen,
                        message->body.srvrqst.srvtype,
                        21,
                        "service:service-agent") == 0)
    {
        errorcode = ProcessSASrvRqst(peeraddr, message, sendbuf, errorcode);
        return errorcode;
    }

    /* TODO: check the spi list of the message and return                  */
    /*       AUTHENTICATION_UNKNOWN since we do not do authentication yet  */

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if(SLPIntersectStringList(message->body.srvrqst.scopelistlen,
                              message->body.srvrqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) != 0)
    {
        /*-------------------------------*/
        /* Find services in the database */
        /*-------------------------------*/
        while(found == count)
        {
            count += G_SlpdProperty.maxResults;

            if(srvarray) free(srvarray);
            srvarray = (SLPDDatabaseSrvUrl*)malloc(sizeof(SLPDDatabaseSrvUrl) * count);
            if(srvarray == 0)
            {
                found       = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }

            found = SLPDDatabaseFindSrv(&(message->body.srvrqst), srvarray, count);
            if(found < 0)
            {
                found = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }
        }

        /* remember the amount found if is really big for next time */
        if(found > G_SlpdProperty.maxResults)
        {
            G_SlpdProperty.maxResults = found;
        }
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }


    RESPOND:
    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if(found == 0 ||
       errorcode != 0)
    {
        if(message->header.flags & SLP_FLAG_MCAST ||
           ISMCAST(peeraddr->sin_addr))
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }

    /*-------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvrply */
    /*-------------------------------------------------------------*/
    size = message->header.langtaglen + 18; /* 14 bytes for header     */
                                            /*  2 bytes for error code */
                                            /*  2 bytes for url count  */
    if(errorcode == 0)
    {
        for(i=0;i<found;i++)
        {
            size += srvarray[i].urllen + 6; /*  1 byte for reserved  */
            /*  2 bytes for lifetime */
            /*  2 bytes for urllen   */
            /*  1 byte for authcount */

            /* TODO: Fix this for authentication */
        } 
        result = SLPBufferRealloc(result,size);
        if(result == 0)
        {
            found = 0;
            errorcode = SLP_ERROR_INTERNAL_ERROR;
            goto FINISHED;
        }
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVRPLY;
    /*length*/
    ToUINT24(result->start + 2, size);
    /*flags*/
    ToUINT16(result->start + 5,
             size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);


    /*-------------------------*/
    /* Add rest of the SrvRply */
    /*-------------------------*/
    result->curpos = result->start + 14 + message->header.langtaglen;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos = result->curpos + 2;
    /* urlentry count */
    ToUINT16(result->curpos, found);
    result->curpos = result->curpos + 2;
    for(i=0;i<found;i++)
    {
        /* url-entry reserved */
        *result->curpos = 0;        
        result->curpos = result->curpos + 1;
        /* url-entry lifetime */
        ToUINT16(result->curpos,srvarray[i].lifetime);
        result->curpos = result->curpos + 2;
        /* url-entry urllen */
        ToUINT16(result->curpos,srvarray[i].urllen);
        result->curpos = result->curpos + 2;
        /* url-entry url */
        memcpy(result->curpos,srvarray[i].url,srvarray[i].urllen);
        result->curpos = result->curpos + srvarray[i].urllen;
        /* url-entry authcount */
        *result->curpos = 0;        
        result->curpos = result->curpos + 1;

        /* TODO: put in authentication stuff too */
    }

    FINISHED:   
    if(srvarray) free(srvarray);

    *sendbuf = result;
    return errorcode;
}
Beispiel #8
0
/*-------------------------------------------------------------------------*/
void ProcessSrvDeReg(SLPDPeerInfo* peerinfo,
                     SLPMessage message,
                     SLPBuffer result)
/*-------------------------------------------------------------------------*/
{
    int errorcode;

    if(message->header.flags & SLP_FLAG_MCAST)
    {
        /* don't do anything multicast SrvDeReg (set result empty) */
        result->end = result->start;
        return;
    }

    /*------------------------------------------*/
    /* TODO: make sure that we handle the scope */
    /*------------------------------------------*/
    if(SLPIntersectStringList(message->body.srvdereg.scopelistlen,
                              message->body.srvdereg.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes))
    {
        /*-------------------------------*/
        /* TODO: Validate the authblocks */
        /*-------------------------------*/
        
        /*--------------------------------------*/
        /* remove the service from the database */
        /*--------------------------------------*/
        if(SLPDDatabaseDeReg(&(message->body.srvdereg)) == 0)
        {
             errorcode = 0;
        }
        else
        {
            errorcode = SLP_ERROR_INTERNAL_ERROR;
        }
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    /*------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvack */
    /*------------------------------------------------------------*/
    result = SLPBufferRealloc(result,message->header.langtaglen + 16);
    
    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVACK;
    /*length*/
    ToUINT24(result->start + 2,message->header.langtaglen + 16);
    /*flags*/
    ToUINT16(result->start + 5,0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);
    
    /*-------------------*/
    /* Add the errorcode */
    /*-------------------*/
    ToUINT16(result->start + 14 + message->header.langtaglen, errorcode);
}
Beispiel #9
0
/*-------------------------------------------------------------------------*/
void ProcessAttrRqst(SLPDPeerInfo* peerinfo,
                     SLPMessage message,
                     SLPBuffer result)
/*-------------------------------------------------------------------------*/
{
    int                     i;
    int                     attrlistlen = 0;
    int                     size        = 0;
    int                     count       = 0;
    int                     found       = 0;
    SLPDDatabaseAttr*       attrarray   = 0;
    int                     errorcode   = 0;
    

    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if(SLPIntersectStringList(message->body.attrrqst.prlistlen,
                              message->body.attrrqst.prlist,
                              G_SlpdProperty.interfacesLen,
                              G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        return;
    }

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if(SLPIntersectStringList(message->body.attrrqst.scopelistlen,
                              message->body.attrrqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) == 0)
    {
        result->end = result->start;
        return;
    }
    
    /*-------------------------------*/
    /* Find attributes in the database */
    /*-------------------------------*/
    while(found == count)
    {
        count += SLPDPROCESS_RESULT_COUNT;
        
        if(attrarray) free(attrarray);
        attrarray = (SLPDDatabaseAttr*)malloc(sizeof(SLPDDatabaseAttr) * count);
        if(attrarray == 0)
        {
            found       = 0;
            errorcode   = SLP_ERROR_INTERNAL_ERROR;
            break;
        }
        
        found = SLPDDatabaseFindAttr(&(message->body.attrrqst), attrarray, count);
        if(found < 0)
        {
            found = 0;
            errorcode   = SLP_ERROR_INTERNAL_ERROR;
            break;
        }
    }

    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if(found <= 0 && (message->header.flags & SLP_FLAG_MCAST))
    {
        if(attrarray) free(attrarray);
        result->end = result->start;
        return;
    }

    /*--------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole attrrply */
    /*--------------------------------------------------------------*/
    size = message->header.langtaglen + 20; /* 14 bytes for header     */
                                            /*  2 bytes for error code */
                                            /*  2 bytes for attr-list len */
                                            /*  2 bytes for the authblockcount */
    for (i=0;i<found;i++)
    {
        attrlistlen += attrarray[i].attrlen;
    }
    size += attrlistlen;
    

    /*-------------------*/
    /* Alloc the  buffer */
    /*-------------------*/
    result = SLPBufferRealloc(result,size);
    if(result == 0)
    {
        found = 0;
        errorcode = SLP_ERROR_INTERNAL_ERROR;
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_ATTRRPLY;
    /*length*/
    ToUINT24(result->start + 2,size);
    /*flags*/
    ToUINT16(result->start + 5,
             size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);
    
    /*--------------------------*/
    /* Add rest of the AttrRqst */
    /*--------------------------*/
    result->curpos = result->start + 14 + message->header.langtaglen;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos = result->curpos + 2;
    /* attr-list len */
    ToUINT16(result->curpos, attrlistlen);
    result->curpos = result->curpos + 2;
    for(i=0;i<found;i++)
    {
        memcpy(result->curpos,attrarray[i].attr,attrarray[i].attrlen);
        result->curpos = result->curpos + attrarray[i].attrlen;
    }
    
    /* TODO: no auth block */
    ToUINT16(result->curpos, 0);

    if(attrarray) free(attrarray);
}        
Beispiel #10
0
/*-------------------------------------------------------------------------*/
void ProcessDASrvRqst(SLPDPeerInfo* peerinfo,
                      SLPMessage message,
                      SLPBuffer result)
/*-------------------------------------------------------------------------*/
{
    int size = 0;
   
    if(G_SlpdProperty.isDA == 0)
    {
        /*----------------------------------------------------------------*/
        /* Do not send error codes or empty replies to multicast requests */
        /*----------------------------------------------------------------*/
        if(message->header.flags & SLP_FLAG_MCAST)
        {
            result->end = result->start;
            return;
        }   

	ProcessSrvRqstError(message, result, SLP_ERROR_MESSAGE_NOT_SUPPORTED);
	return;
    }

    if(message->body.srvrqst.scopelistlen == 0 ||
       SLPIntersectStringList(message->body.srvrqst.scopelistlen,
                              message->body.srvrqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) != 0 )
    {
        /*----------------------*/
        /* Send back a DAAdvert */
        /*----------------------*/

        /* increment the value for DATimestamp */
        G_SlpdProperty.DATimestamp += 1;
        if(G_SlpdProperty.DATimestamp == 0) 
        {
           G_SlpdProperty.DATimestamp = 1;
        }  

        /*-------------------------------------------------------------*/
        /* ensure the buffer is big enough to handle the whole srvrply */
        /*-------------------------------------------------------------*/
        size = message->header.langtaglen + 29; /* 14 bytes for header     */
                                                /*  2 errorcode  */
                                                /*  4 bytes for timestamp */
                                                /*  2 bytes for url len */
                                                /*  2 bytes for scope list len */
                                                /*  2 bytes for attr list len */
                                                /*  2 bytes for spi str len */
                                                /*  1 byte for authblock count */

        size += G_SlpdProperty.myUrlLen;
        size += G_SlpdProperty.useScopesLen;
        /* TODO:  - we don't use attributes yet */
        /* size += G_SlpdProperty.SAAttributes; */
       
        result = SLPBufferRealloc(result,size);
        if(result == 0)
        {
	        /* TODO: out of memory, what should we do here! */
	        return;
        }

        /*----------------*/
        /* Add the header */
        /*----------------*/
        /*version*/
        *(result->start)       = 2;
        /*function id*/
        *(result->start + 1)   = SLP_FUNCT_DAADVERT;
        /*length*/
        ToUINT24(result->start + 2, size);
        /*flags*/
        ToUINT16(result->start + 5,
        size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
        /*ext offset*/
        ToUINT24(result->start + 7,0);
        /*xid*/
        ToUINT16(result->start + 10,message->header.xid);
        /*lang tag len*/
        ToUINT16(result->start + 12,message->header.langtaglen);
        /*lang tag*/
        memcpy(result->start + 14,
               message->header.langtag,
               message->header.langtaglen);
        
        /*--------------------------*/
        /* Add rest of the DAAdvert */
        /*--------------------------*/
        result->curpos = result->start + 14 + message->header.langtaglen;
        /* error code */
        ToUINT16(result->curpos,0);
        result->curpos = result->curpos + 2;
        /* timestamp */
        ToUINT32(result->curpos,G_SlpdProperty.DATimestamp);
        result->curpos = result->curpos + 4;
        /* url len */                       
        ToUINT16(result->curpos, G_SlpdProperty.myUrlLen);
        result->curpos = result->curpos + 2;
        /* url */
        memcpy(result->curpos,G_SlpdProperty.myUrl,G_SlpdProperty.myUrlLen);
        result->curpos = result->curpos + G_SlpdProperty.myUrlLen;
        /* scope list len */
        ToUINT16(result->curpos, G_SlpdProperty.useScopesLen);
        result->curpos = result->curpos + 2;
        /* scope list */
        memcpy(result->curpos,G_SlpdProperty.useScopes,G_SlpdProperty.useScopesLen);
        result->curpos = result->curpos + G_SlpdProperty.useScopesLen;
        /* attr list len */
        ToUINT16(result->curpos, 0);
        result->curpos = result->curpos + 2;
        /* attr list */
        /* memcpy(result->start,G_SlpdProperty.DAAttributes,G_SlpdProperty.DAAttributesLen) */
        /* result->curpos = result->curpos + G_SlpdProperty.DAAttributesLen */
        /* SPI List */
        ToUINT16(result->curpos,0);
        result->curpos = result->curpos + 2;
        /* authblock count */
        *(result->curpos) = 0;
        result->curpos = result->curpos + 1;
    }
    else
    {
        ProcessSrvRqstError(message, result, SLP_ERROR_SCOPE_NOT_SUPPORTED);
    }
}
Beispiel #11
0
/*-------------------------------------------------------------------------*/
void ProcessSrvRqst(SLPDPeerInfo* peerinfo,
                    SLPMessage message,
                    SLPBuffer result)
/*-------------------------------------------------------------------------*/
{
    int                     i;
    int                     size        = 0;
    int                     count       = 0;
    int                     found       = 0;
    SLPDDatabaseSrvUrl*     srvarray    = 0;
    int                     errorcode   = 0;
    

    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if(SLPIntersectStringList(message->body.srvrqst.prlistlen,
                              message->body.srvrqst.prlist,
                              G_SlpdProperty.interfacesLen,
                              G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------------------*/
    /* Check to to see if a this is a special SrvRqst */
    /*------------------------------------------------*/
    if(SLPCompareString(message->body.srvrqst.srvtypelen,
			message->body.srvrqst.srvtype,
			23,
			"service:directory-agent") == 0)
    {
        ProcessDASrvRqst(peerinfo,
                         message,
                         result);
        goto FINISHED;
    }
    if(SLPCompareString(message->body.srvrqst.srvtypelen,
			message->body.srvrqst.srvtype,
			21,
			"service:service-agent") == 0)
    {
        ProcessSASrvRqst(peerinfo,
			 message,
			 result);
        goto FINISHED;
    }
   
    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if(SLPIntersectStringList(message->body.srvrqst.scopelistlen,
                              message->body.srvrqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) != 0)
    {
        /*-------------------------------*/
        /* Find services in the database */
        /*-------------------------------*/
        while(found == count)
        {
            count += SLPDPROCESS_RESULT_COUNT;
        
            if(srvarray) free(srvarray);
            srvarray = (SLPDDatabaseSrvUrl*)malloc(sizeof(SLPDDatabaseSrvUrl) * count);
            if(srvarray == 0)
            {
                found       = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }
        
            found = SLPDDatabaseFindSrv(&(message->body.srvrqst), srvarray, count);
            if(found < 0)
            {
                found = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }
        }
    }
    else
    { 
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }
   
    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if(found <= 0 && (message->header.flags & SLP_FLAG_MCAST))
    {
        result->end = result->start;
        goto FINISHED;
    }   


    /*-------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvrply */
    /*-------------------------------------------------------------*/
    size = message->header.langtaglen + 18; /* 14 bytes for header     */
                                            /*  2 bytes for error code */
                                            /*  2 bytes for url count  */ 
    for(i=0;i<found;i++)
    {
        size += srvarray[i].urllen + 6; /*  1 byte for reserved  */
                                                /*  2 bytes for lifetime */
                                                /*  2 bytes for urllen   */
                                                /*  1 byte for authcount */
        
        /* TODO: Fix this for authentication */
    } 
    result = SLPBufferRealloc(result,size);
    if(result == 0)
    {
        found = 0;
        errorcode = SLP_ERROR_INTERNAL_ERROR;
    }

    
    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVRPLY;
    /*length*/
    ToUINT24(result->start + 2, size);
    /*flags*/
    ToUINT16(result->start + 5,
             size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);
    
    
    /*-------------------------*/
    /* Add rest of the SrvRply */
    /*-------------------------*/
    result->curpos = result->start + 14 + message->header.langtaglen;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos = result->curpos + 2;
    /* urlentry count */
    ToUINT16(result->curpos, found);
    result->curpos = result->curpos + 2;
    for(i=0;i<found;i++)
    {
        /* url-entry reserved */
        *result->curpos = 0;        
        result->curpos = result->curpos + 1;
        /* url-entry lifetime */
        ToUINT16(result->curpos,srvarray[i].lifetime);
        result->curpos = result->curpos + 2;
        /* url-entry urllen */
        ToUINT16(result->curpos,srvarray[i].urllen);
        result->curpos = result->curpos + 2;
        /* url-entry url */
        memcpy(result->curpos,srvarray[i].url,srvarray[i].urllen);
        result->curpos = result->curpos + srvarray[i].urllen;
        /* url-entry authcount */
        *result->curpos = 0;        
        result->curpos = result->curpos + 1;

        /* TODO: put in authentication stuff too */
    }
    
    FINISHED:   
    if(srvarray) free(srvarray);
}
Beispiel #12
0
/*=========================================================================*/
int SLPDDatabaseAttrRqstStart(SLPMessage msg,
                              SLPDDatabaseAttrRqstResult** result)
/* Find attributes in the database                                         */
/*                                                                         */
/* msg      (IN) the AttrRqst to find.                                     */
/*                                                                         */
/* result   (OUT) pointer result structure                                 */
/*                                                                         */
/* Returns  - Zero on success. Non-zero on failure                         */
/*                                                                         */
/* Note:    Caller must pass *result to SLPDDatabaseAttrRqstEnd() to       */
/*          free                                                           */
/*=========================================================================*/
{
    SLPDatabaseHandle           dh;
    SLPDatabaseEntry*           entry;
    SLPSrvReg*                  entryreg;
    SLPAttrRqst*                attrrqst;
#ifdef ENABLE_SLPv2_SECURITY
    int                         i;
#endif

    *result = xmalloc(sizeof(SLPDDatabaseAttrRqstResult));
    if ( *result == NULL )
    {
        return SLP_ERROR_INTERNAL_ERROR;
    }
    memset(*result,0,sizeof(SLPDDatabaseAttrRqstResult));

    dh = SLPDatabaseOpen(&G_SlpdDatabase.database);
    if ( dh )
    {
        (*result)->reserved = dh;

        /* attrrqst is the AttrRqst being made */
        attrrqst = &(msg->body.attrrqst);

        while ( 1 )
        {
            entry = SLPDatabaseEnum(dh);
            if ( entry == NULL )
            {
                return 0;
            }

            /* entry reg is the SrvReg message from the database */
            entryreg = &(entry->msg->body.srvreg);


            if ( SLPCompareString(attrrqst->urllen,
                                  attrrqst->url,
                                  entryreg->urlentry.urllen,
                                  entryreg->urlentry.url) == 0 ||
                 SLPCompareSrvType(attrrqst->urllen,
                                   attrrqst->url,
                                   entryreg->srvtypelen,
                                   entryreg->srvtype) == 0 )
            {
                if ( SLPIntersectStringList(attrrqst->scopelistlen,
                                            attrrqst->scopelist,
                                            entryreg->scopelistlen,
                                            entryreg->scopelist) )
                {
                    if ( attrrqst->taglistlen == 0 )
                    {
#ifdef ENABLE_SLPv2_SECURITY
                        if ( attrrqst->spistrlen )
                        {
                            for ( i=0; i< entryreg->authcount;i++ )
                            {
                                if ( SLPCompareString(attrrqst->spistrlen,
                                                      attrrqst->spistr,
                                                      entryreg->autharray[i].spistrlen,
                                                      entryreg->autharray[i].spistr) == 0 )
                                {
                                    break;
                                }
                            }
                            if ( i == entryreg->authcount )
                            {
                                continue;
                            }
                        }
#endif
                        /* Send back what was registered */
                        (*result)->attrlistlen = entryreg->attrlistlen;
                        (*result)->attrlist = (char*)entryreg->attrlist;
                        (*result)->authcount = entryreg->authcount;
                        (*result)->autharray = entryreg->autharray;                        
                    }
#ifdef ENABLE_PREDICATES
                    else
                    {
                        /* Send back a partial list as specified by taglist */
                        if ( SLPDFilterAttributes(entryreg->attrlistlen,
                                                  entryreg->attrlist,
                                                  attrrqst->taglistlen,
                                                  attrrqst->taglist,
                                                  &(*result)->attrlistlen,
                                                  &(*result)->attrlist) == 0 )
                        {
                            (*result)->ispartial = 1;
                            break;
                        }
                    }
#endif
                }
            }
        }
    }

    return 0;
}
Beispiel #13
0
/*=========================================================================*/
int SLPDDatabaseSrvTypeRqstStart(SLPMessage msg,
                                 SLPDDatabaseSrvTypeRqstResult** result)
/* Find service types in the database                                      */
/*                                                                         */
/* msg      (IN) the SrvTypRqst to find.                                   */
/*                                                                         */
/* result   (OUT) pointer result structure                                 */
/*                                                                         */
/* Returns  - Zero on success. Non-zero on failure                         */
/*                                                                         */
/* Note:    Caller must pass *result to SLPDDatabaseSrvtypeRqstEnd() to    */
/*          free                                                           */
/*=========================================================================*/
{
    SLPDatabaseHandle           dh;
    SLPDatabaseEntry*           entry;
    SLPSrvReg*                  entryreg;
    SLPSrvTypeRqst*             srvtyperqst;

    dh = SLPDatabaseOpen(&G_SlpdDatabase.database);
    if ( dh )
    {
        /* srvtyperqst is the SrvTypeRqst being made */
        srvtyperqst = &(msg->body.srvtyperqst);

        while ( 1 )
        {
            /*-----------------------------------------------------------------*/
            /* Allocate result with generous srvtypelist of url entry pointers */
            /*-----------------------------------------------------------------*/
            *result = (SLPDDatabaseSrvTypeRqstResult*) xrealloc(*result, sizeof(SLPDDatabaseSrvTypeRqstResult) + G_SlpdDatabase.srvtypelistlen);
            if ( *result == NULL )
            {
                /* out of memory */
                SLPDatabaseClose(dh);
                return SLP_ERROR_INTERNAL_ERROR;
            }
            (*result)->srvtypelist = (char*)((*result) + 1);
            (*result)->srvtypelistlen = 0;
            (*result)->reserved = dh;

            /*-------------------------------------------------*/
            /* Rewind enumeration in case we had to reallocate */
            /*-------------------------------------------------*/
            SLPDatabaseRewind(dh);

            while ( 1 )
            {
                entry = SLPDatabaseEnum(dh);
                if ( entry == NULL )
                {
                    /* This is the only successful way out */
                    return 0;
                }

                /* entry reg is the SrvReg message from the database */
                entryreg = &(entry->msg->body.srvreg);

                if ( SLPCompareNamingAuth(entryreg->srvtypelen,
                                          entryreg->srvtype,
                                          srvtyperqst->namingauthlen,
                                          srvtyperqst->namingauth) == 0 && 
                     SLPIntersectStringList(srvtyperqst->scopelistlen,
                                            srvtyperqst->scopelist,
                                            entryreg->scopelistlen,
                                            entryreg->scopelist) &&
                     SLPContainsStringList((*result)->srvtypelistlen, 
                                           (*result)->srvtypelist,
                                           entryreg->srvtypelen,
                                           entryreg->srvtype) == 0 )
                {
                    /* Check to see if we allocated a big enough srvtypelist */
                    if ( (*result)->srvtypelistlen + entryreg->srvtypelen > G_SlpdDatabase.srvtypelistlen )
                    {
                        /* Oops we did not allocate a big enough result */
                        G_SlpdDatabase.srvtypelistlen *= 2;
                        break;
                    }

                    /* Append a comma if needed */
                    if ( (*result)->srvtypelistlen )
                    {
                        (*result)->srvtypelist[(*result)->srvtypelistlen] = ',';
                        (*result)->srvtypelistlen += 1;
                    }
                    /* Append the service type */
                    memcpy(((*result)->srvtypelist) + (*result)->srvtypelistlen,
                           entryreg->srvtype,
                           entryreg->srvtypelen);
                    (*result)->srvtypelistlen += entryreg->srvtypelen;
                }
            }
        }

        SLPDatabaseClose(dh);
    }

    return 0;
}
Beispiel #14
0
/*=========================================================================*/
int SLPDDatabaseSrvRqstStart(SLPMessage msg,
                             SLPDDatabaseSrvRqstResult** result)
/* Find services in the database                                           */
/*                                                                         */
/* msg      (IN) the SrvRqst to find.                                      */
/*                                                                         */
/* result   (OUT) pointer result structure                                 */
/*                                                                         */
/* Returns  - Zero on success. Non-zero on failure                         */
/*                                                                         */
/* Note:    Caller must pass *result to SLPDDatabaseSrvRqstEnd() to free   */
/*=========================================================================*/
{
    SLPDatabaseHandle           dh;
    SLPDatabaseEntry*           entry;
    SLPSrvReg*                  entryreg;
    SLPSrvRqst*                 srvrqst;
#ifdef ENABLE_SLPv2_SECURITY
    int                         i;
#endif


    /* start with the result set to NULL just to be safe */
    *result = NULL;

    dh = SLPDatabaseOpen(&G_SlpdDatabase.database);
    if ( dh )
    {
        /* srvrqst is the SrvRqst being made */
        srvrqst = &(msg->body.srvrqst);

        while ( 1 )
        {
            /*-----------------------------------------------------------*/
            /* Allocate result with generous array of url entry pointers */
            /*-----------------------------------------------------------*/
            *result = (SLPDDatabaseSrvRqstResult*) xrealloc(*result, sizeof(SLPDDatabaseSrvRqstResult) + (sizeof(SLPUrlEntry*) * G_SlpdDatabase.urlcount));
            if ( *result == NULL )
            {
                /* out of memory */
                SLPDatabaseClose(dh);
                return SLP_ERROR_INTERNAL_ERROR;
            }
            (*result)->urlarray = (SLPUrlEntry**)((*result) + 1);
            (*result)->urlcount = 0;
            (*result)->reserved = dh;

            /*-------------------------------------------------*/
            /* Rewind enumeration in case we had to reallocate */
            /*-------------------------------------------------*/
            SLPDatabaseRewind(dh);

            /*-----------------------------------------*/
            /* Check to see if there is matching entry */
            /*-----------------------------------------*/
            while ( 1 )
            {
                entry = SLPDatabaseEnum(dh);
                if ( entry == NULL )
                {
                    /* This is the only successful way out */
                    return 0;
                }

                /* entry reg is the SrvReg message from the database */
                entryreg = &(entry->msg->body.srvreg);

                /* check the service type */
                if ( SLPCompareSrvType(srvrqst->srvtypelen,
                                       srvrqst->srvtype,
                                       entryreg->srvtypelen,
                                       entryreg->srvtype) == 0 &&
                     SLPIntersectStringList(entryreg->scopelistlen,
                                            entryreg->scopelist,
                                            srvrqst->scopelistlen,
                                            srvrqst->scopelist) > 0 )
                {
#ifdef ENABLE_PREDICATES
                    if ( SLPDPredicateTest(msg->header.version,
                                           entryreg->attrlistlen,
                                           entryreg->attrlist,
                                           srvrqst->predicatelen,
                                           srvrqst->predicate) )
#endif
                    {

#ifdef ENABLE_SLPv2_SECURITY
                        if ( srvrqst->spistrlen )
                        {
                            for ( i=0; i< entryreg->urlentry.authcount;i++ )
                            {
                                if ( SLPCompareString(srvrqst->spistrlen,
                                                      srvrqst->spistr,
                                                      entryreg->urlentry.autharray[i].spistrlen,
                                                      entryreg->urlentry.autharray[i].spistr) == 0 )
                                {
                                    break;
                                }
                            }
                            if ( i == entryreg->urlentry.authcount )
                            {
                                continue;
                            }
                        }
#endif
                        if ( (*result)->urlcount + 1 > G_SlpdDatabase.urlcount )
                        {
                            /* Oops we did not allocate a big enough result */
                            G_SlpdDatabase.urlcount *= 2;
                            break;
                        }

                        (*result)->urlarray[(*result)->urlcount] = &(entryreg->urlentry);
                        (*result)->urlcount ++;
                    }
                }
            }
        }
    }

    return 0;
}
Beispiel #15
0
/*-------------------------------------------------------------------------*/
int v1ProcessAttrRqst(struct sockaddr_in* peeraddr,
                      SLPMessage message,
                      SLPBuffer* sendbuf,
                      int errorcode)
/*-------------------------------------------------------------------------*/
{
    SLPDDatabaseAttrRqstResult* db              = 0;
    int                         attrlen     = 0;
    int                         size        = 0;
    SLPBuffer                   result      = *sendbuf;

    /*--------------------------------------------------------------*/
    /* If errorcode is set, we can not be sure that message is good */
    /* Go directly to send response code                            */
    /*--------------------------------------------------------------*/
    if (errorcode)
    {
        goto RESPOND;
    }

    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if (SLPIntersectStringList(message->body.attrrqst.prlistlen,
                               message->body.attrrqst.prlist,
                               G_SlpdProperty.interfacesLen,
                               G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if (SLPIntersectStringList(message->body.attrrqst.scopelistlen,
                               message->body.attrrqst.scopelist,
                               G_SlpdProperty.useScopesLen,
                               G_SlpdProperty.useScopes))
    {
        /*---------------------------------*/
        /* Find attributes in the database */
        /*---------------------------------*/
        errorcode = SLPDDatabaseAttrRqstStart(message,&db);
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    RESPOND:
    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if (message->header.flags & SLP_FLAG_MCAST)
    {
        if (errorcode != 0 || db->attrlistlen == 0)
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }

    /*--------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole attrrply */
    /*--------------------------------------------------------------*/
    size = 16; /* 12 bytes for header, 2 bytes for error code, 2 bytes
                for attr-list len */
    if (errorcode == 0)
    {

        attrlen = INT_MAX;
        errorcode = SLPv1ToEncoding(0, &attrlen,
                                    message->header.encoding,  
                                    db->attrlist,
                                    db->attrlistlen);
        size += attrlen;
    }

    /*-------------------*/
    /* Alloc the  buffer */
    /*-------------------*/
    result = SLPBufferRealloc(result,size);
    if (result == 0)
    {
        errorcode = SLP_ERROR_INTERNAL_ERROR;
        goto FINISHED;
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 1;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_ATTRRPLY;
    /*length*/
    ToUINT16(result->start + 2, size);
    /*flags - TODO set the flags correctly */
    *(result->start + 4) = message->header.flags |
                           (size > SLP_MAX_DATAGRAM_SIZE ? SLPv1_FLAG_OVERFLOW : 0);  
    /*dialect*/
    *(result->start + 5) = 0;
    /*language code*/
    memcpy(result->start + 6, message->header.langtag, 2);
    ToUINT16(result->start + 8, message->header.encoding);
    /*xid*/
    ToUINT16(result->start + 10, message->header.xid);

    /*--------------------------*/
    /* Add rest of the AttrRply */
    /*--------------------------*/
    result->curpos = result->start + 12;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos = result->curpos + 2; 
    if (errorcode == 0)
    {
        /* attr-list len */
        ToUINT16(result->curpos, attrlen);
        result->curpos = result->curpos + 2;
        attrlen = size;
        SLPv1ToEncoding(result->curpos, &attrlen,
                        message->header.encoding,
                        db->attrlist,
                        db->attrlistlen);
        result->curpos = result->curpos + attrlen; 
    }

    FINISHED:
    *sendbuf = result;
    if (db) SLPDDatabaseAttrRqstEnd(db);

    return errorcode;
}        
Beispiel #16
0
/*=========================================================================*/
int SLPDDatabaseReg(SLPSrvReg* srvreg, unsigned int regtype)
/* Add a service registration to the database                              */
/*                                                                         */
/* srvreg   -   (IN) pointer to the SLPSrvReg to be added to the database  */
/*                                                                         */
/* regtype  -   (IN) registration types or'ed together:                    */
/*                   SLPDDATABASE_REG_FRESH                                */
/*                   SLPDDATABASE_REG_LOCAL                                */
/*                   SLPDDATABASE_REG_STATIC                               */
/*                                                                         */
/* Returns  -   Zero on success.  > 0 if something is wrong with srvreg    */
/*              < 0 if out of memory                                       */
/*                                                                         */
/* NOTE:        All registrations are treated as fresh regardless of the   */
/*              setting of the fresh parameter                             */
/*=========================================================================*/
{
    int                result = -1;
    SLPDDatabaseEntry* entry  = (SLPDDatabaseEntry*)G_DatabaseList.head;

    /* Check to see if there is already an identical entry */
    while(entry)
    {
        if(SLPCompareString(entry->urllen,
                            entry->url,
                            srvreg->urlentry.urllen,
                            srvreg->urlentry.url) == 0)
        {
            if(SLPIntersectStringList(entry->scopelistlen,
                                      entry->scopelist,
                                      srvreg->scopelistlen,
                                      srvreg->scopelist) > 0)
            {
                SLPListUnlink(&G_DatabaseList,(SLPListItem*)entry);
                break;
            }
        }

        entry = (SLPDDatabaseEntry*) entry->listitem.next;
    }

    /* if no identical entry are found, create a new one */
    if(entry == 0)
    {
        entry = SLPDDatabaseEntryAlloc();
        if(entry == 0)
        {
            /* Out of memory */
            goto FAILURE;
        }
    }

    /*----------------------------------------------------------------*/
    /* copy info from the message from the wire to the database entry */
    /*----------------------------------------------------------------*/

    /* scope */
    if(entry->scopelistlen >= srvreg->scopelistlen)
    {
        memcpy(entry->scopelist,srvreg->scopelist,srvreg->scopelistlen);
    }
    else
    {
        if(entry->scopelist) free(entry->scopelist);
        entry->scopelist = (char*)memdup(srvreg->scopelist,srvreg->scopelistlen);
        if(entry->scopelist == 0) goto FAILURE;
    }
    entry->scopelistlen = srvreg->scopelistlen;

    /* URL */
    if(entry->urllen >= srvreg->urlentry.urllen)
    {
        memcpy(entry->url,srvreg->urlentry.url,srvreg->urlentry.urllen);
    }
    else
    {
        if(entry->url) free(entry->url);
        entry->url = (char*)memdup(srvreg->urlentry.url,srvreg->urlentry.urllen);
        if(entry->url == 0) goto FAILURE;
    }
    entry->urllen = srvreg->urlentry.urllen;

    /* lifetime */
    entry->lifetime     = srvreg->urlentry.lifetime;

    /* is local */
    entry->regtype      = regtype;

    /* SrvType */
    if(entry->srvtypelen >= srvreg->srvtypelen)
    {
        memcpy(entry->srvtype,srvreg->srvtype,srvreg->srvtypelen);
    }
    else
    {
        if(entry->srvtype) free(entry->srvtype);
        entry->srvtype = (char*)memdup(srvreg->srvtype,srvreg->srvtypelen);
        if(entry->srvtype == 0) goto FAILURE;
    }
    entry->srvtypelen = srvreg->srvtypelen;

    /* Attributes */
    if(srvreg->attrlistlen)
    {
#ifdef USE_PREDICATES




        /* Tricky: perform an in place null termination of the attrlist */
        /*         Remember this squishes the authblock count           */
        ((char*)srvreg->attrlist)[srvreg->attrlistlen] = 0;
        if(SLPAttrFreshen(entry->attr, srvreg->attrlist) != SLP_OK)
        {
            result = 1;
            goto FAILURE;
        }

        /* Serialize all attributes into entry->attrlist */
        if(entry->attrlist)
        {
            free(entry->attrlist);
            entry->attrlist = 0;
            entry->attrlistlen = 0;
        }
        if(SLPAttrSerialize(entry->attr,
                            "",
                            &entry->attrlist,
                            entry->attrlistlen,
                            &entry->attrlistlen,
                            SLP_FALSE))
        {
            goto FAILURE;
        }
#else
        if(entry->attrlistlen >= srvreg->attrlistlen)
        {
            memcpy(entry->attrlist,srvreg->attrlist,srvreg->attrlistlen);
        }
        else
        {
            if(entry->attrlist) free(entry->attrlist);
            entry->attrlist = memdup(srvreg->attrlist,srvreg->attrlistlen);
            if(entry->attrlist == 0) goto FAILURE;
        }
        entry->attrlistlen = srvreg->attrlistlen;
#endif
    }

    /* link the new (or modified) entry into the list */
    SLPListLinkHead(&G_DatabaseList,(SLPListItem*)entry);

    /* traceReg if necessary */
    SLPDLogTraceReg("Registered", entry);

    return 0;

FAILURE:
    if(entry)
    {
        SLPDDatabaseEntryFree(entry);
    }

    return result;
}
Beispiel #17
0
/*-------------------------------------------------------------------------*/
int v1ProcessSrvTypeRqst(struct sockaddr_in* peeraddr,
                         SLPMessage message,
                         SLPBuffer* sendbuf,
                         int errorcode)
/*-------------------------------------------------------------------------*/
{
    char*                           type;
    char*                           end;
    char*                           slider;
    int                             i;
    int                             typelen;
    int                             numsrvtypes = 0;
    int                             size        = 0;
    SLPDDatabaseSrvTypeRqstResult*  db          = 0;
    SLPBuffer                       result      = *sendbuf;


    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if (SLPIntersectStringList(message->body.srvtyperqst.prlistlen,
                               message->body.srvtyperqst.prlist,
                               G_SlpdProperty.interfacesLen,
                               G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------------------------------------*/
    if (SLPIntersectStringList(message->body.srvtyperqst.scopelistlen,
                               message->body.srvtyperqst.scopelist,
                               G_SlpdProperty.useScopesLen,
                               G_SlpdProperty.useScopes) != 0)
    {
        /*------------------------------------*/
        /* Find service types in the database */
        /*------------------------------------*/
        errorcode = SLPDDatabaseSrvTypeRqstStart(message, &db);
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if (message->header.flags & SLP_FLAG_MCAST)
    {
        if (errorcode != 0 || db->srvtypelistlen == 0)
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }


    /*-----------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvtyperply */
    /*-----------------------------------------------------------------*/
    size = 16; /* 12 bytes for header, 2 bytes for error code, 2 bytes
                  for num of service types */
    if (errorcode == 0)
    {
        if (db->srvtypelistlen)
        {
            /* there has to be at least one service type*/
            numsrvtypes = 1;

            /* count the rest of the service types */
            type = db->srvtypelist;
            for (i=0; i< db->srvtypelistlen; i++)
            {
                if (type[i] == ',')
                {
                    numsrvtypes += 1;
                }
            }

            /* figure out how much memory is required for srvtype strings */
            typelen = INT_MAX;
            errorcode = SLPv1ToEncoding(0,
                                        &typelen,
                                        message->header.encoding,  
                                        db->srvtypelist,
                                        db->srvtypelistlen);

            /* TRICKY: we add in the numofsrvtypes + 1 to make room for the */
            /* type length.  We can do this because the ',' of the comma    */
            /* delimited list is one byte.                                  */
            size = size + typelen + numsrvtypes + 1;
        }
        else
        {
            numsrvtypes = 0;
        }
    }

    /*-----------------*/
    /* Allocate memory */
    /*-----------------*/
    result = SLPBufferRealloc(result,size);
    if (result == 0)
    {
        errorcode = SLP_ERROR_INTERNAL_ERROR;
        goto FINISHED;
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 1;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVTYPERPLY;
    /*length*/
    ToUINT16(result->start + 2, size);
    /*flags - TODO set the flags correctly */
    *(result->start + 4) = message->header.flags |
                           (size > SLP_MAX_DATAGRAM_SIZE ? SLPv1_FLAG_OVERFLOW : 0);  
    /*dialect*/
    *(result->start + 5) = 0;
    /*language code*/
    memcpy(result->start + 6, message->header.langtag, 2);
    ToUINT16(result->start + 8, message->header.encoding);
    /*xid*/
    ToUINT16(result->start + 10, message->header.xid);

    /*-----------------------------*/
    /* Add rest of the SrvTypeRply */
    /*-----------------------------*/
    result->curpos = result->start + 12;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos += 2;
    if (errorcode == 0)
    {
        /* num of service types */
        ToUINT16(result->curpos, numsrvtypes);
        result->curpos += 2;

        /* service type strings */
        type = db->srvtypelist;
        slider = db->srvtypelist;
        end = &(type[db->srvtypelistlen]);
        for (i=0;i<numsrvtypes; i++)
        {
            while (slider < end && *slider != ',') slider++;

            typelen = size;
            /* put in the encoded service type */
            SLPv1ToEncoding(result->curpos + 2, 
                            &typelen,
                            message->header.encoding,
                            type,
                            slider - type);
            /* slip in the typelen */
            ToUINT16(result->curpos, typelen);
            result->curpos += 2;
            result->curpos += typelen;

            slider ++; /* skip comma */
            type = slider;
        }

        /* TODO - make sure we don't return generic types */
    }

    FINISHED:   
    if (db) SLPDDatabaseSrvTypeRqstEnd(db);

    *sendbuf = result;

    return errorcode;
}
Beispiel #18
0
/*=========================================================================*/
int SLPDDatabaseFindSrv(SLPSrvRqst* srvrqst,
                        SLPDDatabaseSrvUrl* result,
                        int count)
/* Find services in the database                                           */
/*                                                                         */
/* srvrqst  (IN) the request to find.                                      */
/*                                                                         */
/* result   (OUT) pointer to an array of result structures that receives   */
/*                results                                                  */
/*                                                                         */
/* count    (IN)  number of elements in the result array                   */
/*                                                                         */
/* Returns  - The number of services found or < 0 on error.  If the number */
/*            of services found is exactly equal to the number of elements */
/*            in the array, the call may be repeated with a larger array.  */
/*=========================================================================*/
{
    SLPDDatabaseEntry*  entry;
    int                 found;

#ifdef USE_PREDICATES




    /* Tricky: perform an in place null termination of the predicate string */
    /*         Remember this squishes the high byte of spilistlen which is  */
    /*         not a problem because it was already copied                  */
    if(srvrqst->predicate)
    {
        ((char*)srvrqst->predicate)[srvrqst->predicatelen] = 0;
    }
#endif

    /*---------------*/
    /* Test services */
    /*---------------*/
    found = 0;
    entry = (SLPDDatabaseEntry*)G_DatabaseList.head;
    while(entry)
    {
        if(SLPCompareSrvType(srvrqst->srvtypelen,
                             srvrqst->srvtype,
                             entry->srvtypelen,
                             entry->srvtype) == 0)
        {
            if(SLPIntersectStringList(srvrqst->scopelistlen,
                                      srvrqst->scopelist,
                                      entry->scopelistlen,
                                      entry->scopelist))
            {
#ifdef USE_PREDICATES
                if(srvrqst->predicate &&
                        entry->attr &&
                        SLPDPredicateTest(srvrqst->predicatever,
                                          srvrqst->predicate, entry->attr) == 0)
#endif
                {
                    result[found].lifetime = entry->lifetime;
                    result[found].urllen = entry->urllen;
                    result[found].url = entry->url;
                    found ++;
                    if(found >= count)
                    {
                        break;
                    }
                }
            }
        }

        entry = (SLPDDatabaseEntry*)entry->listitem.next;
    }

    return found;
}
Beispiel #19
0
/*-------------------------------------------------------------------------*/
int ProcessDASrvRqst(struct sockaddr_in* peeraddr,
                     SLPMessage message,
                     SLPBuffer* sendbuf,
                     int errorcode)
/*-------------------------------------------------------------------------*/
{
    SLPDAEntry      daentry;
    SLPBuffer       tmp     = 0;
    SLPDAEntry*     entry   = 0;
    void*           i       = 0;

    /* set up local data */
    memset(&daentry,0,sizeof(daentry));    

    /*---------------------------------------------------------------------*/
    /* Special case for when libslp asks slpd (through the loopback) about */
    /* a known DAs. Fill sendbuf with DAAdverts from all known DAs.        */
    /*---------------------------------------------------------------------*/
    if(ISLOCAL(peeraddr->sin_addr))
    {
        /* TODO: be smarter about how much memory is allocated here! */
        /* 4096 may not be big enough to handle all DAAdverts        */
        *sendbuf = SLPBufferRealloc(*sendbuf, 4096);
        if(*sendbuf == 0)
        {
            return SLP_ERROR_INTERNAL_ERROR;
        }

        if(errorcode == 0)
        {

            /* Note: The weird *sendbuf code is making a single SLPBuffer */
            /*       that contains multiple DAAdverts.  This is a special */
            /*       process that only happens for the DA SrvRqst through */
            /*       loopback to the SLPAPI                               */
            while(SLPDKnownDAEnum(&i,&entry) == 0)
            {
                if(SLPDKnownDAEntryToDAAdvert(errorcode,
                                              message->header.xid,
                                              entry,
                                              &tmp) == 0)
                {
                    if(((*sendbuf)->curpos) + (tmp->end - tmp->start) > (*sendbuf)->end)
                    {
                        break;
                    }

                    memcpy((*sendbuf)->curpos, tmp->start, tmp->end - tmp->start);
                    (*sendbuf)->curpos = ((*sendbuf)->curpos) + (tmp->end - tmp->start);
                }
            }

            /* Tack on a "terminator" DAAdvert */
            SLPDKnownDAEntryToDAAdvert(SLP_ERROR_INTERNAL_ERROR,
                                       message->header.xid,
                                       &daentry,
                                       &tmp);
            if(((*sendbuf)->curpos) + (tmp->end - tmp->start) <= (*sendbuf)->end)
            {
                memcpy((*sendbuf)->curpos, tmp->start, tmp->end - tmp->start);
                (*sendbuf)->curpos = ((*sendbuf)->curpos) + (tmp->end - tmp->start);
            }

            /* mark the end of the sendbuf */
            (*sendbuf)->end = (*sendbuf)->curpos;


            if(tmp)
            {
                SLPBufferFree(tmp);
            }
        }

        return errorcode;
    }


    /*---------------------------------------------------------------------*/
    /* Normal case where a remote Agent asks for a DA                      */
    /*---------------------------------------------------------------------*/
    if(G_SlpdProperty.isDA)
    {
        if(message->body.srvrqst.scopelistlen == 0 ||
           SLPIntersectStringList(message->body.srvrqst.scopelistlen, 
                                  message->body.srvrqst.scopelist,
                                  G_SlpdProperty.useScopesLen,
                                  G_SlpdProperty.useScopes))
        {
            /* fill out real structure */
            G_SlpdProperty.DATimestamp += 1;
            daentry.bootstamp = G_SlpdProperty.DATimestamp;
            daentry.langtaglen = G_SlpdProperty.localeLen;
            daentry.langtag = (char*)G_SlpdProperty.locale;
            daentry.urllen = G_SlpdProperty.myUrlLen;
            daentry.url = (char*)G_SlpdProperty.myUrl;
            daentry.scopelistlen = G_SlpdProperty.useScopesLen;
            daentry.scopelist = (char*)G_SlpdProperty.useScopes;
            daentry.attrlistlen = 0;
            daentry.attrlist = 0;
            daentry.spilistlen = 0;
            daentry.spilist = 0;
        }
        else
        {
            errorcode =  SLP_ERROR_SCOPE_NOT_SUPPORTED;
        }
    }
    else
    {
        errorcode = SLP_ERROR_MESSAGE_NOT_SUPPORTED;       
    }

    /* don't return errorcodes to multicast messages */
    if(errorcode != 0)
    {
        if(message->header.flags & SLP_FLAG_MCAST ||
           ISMCAST(peeraddr->sin_addr))
        {
            (*sendbuf)->end = (*sendbuf)->start;
            return errorcode;
        }
    }

    errorcode = SLPDKnownDAEntryToDAAdvert(errorcode,
                                           message->header.xid,
                                           &daentry,
                                           sendbuf);

    return errorcode;
}
Beispiel #20
0
/*=========================================================================*/
int SLPDDatabaseFindType(SLPSrvTypeRqst* srvtyperqst,
                         SLPDDatabaseSrvType* result,
                         int count)
/* Find service types                                                      */
/*                                                                         */
/* srvtyperqst  (IN) the request to find.                                  */
/*                                                                         */
/* result   (OUT) pointer to an array of result structures that receives   */
/*                results                                                  */
/*                                                                         */
/* count    (IN)  number of elements in the result array                   */
/*                                                                         */
/* Returns  - The number of srvtypes found or <0 on error.  If the number  */
/*            of srvtypes found is exactly equal to the number of elements */
/*            in the array, the call may be repeated with a larger array.  */
/*=========================================================================*/
{
    SLPDDatabaseEntry*  entry;
    int                 found;
    int                 i;


    found = 0;
    entry = (SLPDDatabaseEntry*)G_DatabaseList.head;
    while(entry)
    {
        if(SLPCompareNamingAuth(entry->srvtypelen, entry->srvtype,
                                srvtyperqst->namingauthlen,
                                srvtyperqst->namingauth) == 0)
        {
            if(SLPIntersectStringList(srvtyperqst->scopelistlen,
                                      srvtyperqst->scopelist,
                                      entry->scopelistlen,
                                      entry->scopelist))
            {
                for(i = 0; i < found; i++)
                {
                    if(SLPCompareString(result[i].typelen,
                                        result[i].type,
                                        entry->srvtypelen,
                                        entry->srvtype) == 0)
                    {
                        break;
                    }
                }

                if(i == found)
                {
                    result[found].type = entry->srvtype;
                    result[found].typelen = entry->srvtypelen;
                    found++;
                    if(found >= count)
                    {
                        break;
                    }
                }
            }
        }

        entry = (SLPDDatabaseEntry*)entry->listitem.next;
    }

    return found;
}
Beispiel #21
0
/*-------------------------------------------------------------------------*/
int ProcessSASrvRqst(struct sockaddr_in* peeraddr,
                     SLPMessage message,
                     SLPBuffer* sendbuf,
                     int errorcode)
/*-------------------------------------------------------------------------*/
{
    int size = 0;
    SLPBuffer result = *sendbuf;

    if(message->body.srvrqst.scopelistlen == 0 ||
       SLPIntersectStringList(message->body.srvrqst.scopelistlen,
                              message->body.srvrqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) != 0)
    {
        /*----------------------*/
        /* Send back a SAAdvert */
        /*----------------------*/

        /*--------------------------------------------------------------*/
        /* ensure the buffer is big enough to handle the whole SAAdvert */
        /*--------------------------------------------------------------*/
        size = message->header.langtaglen + 21; /* 14 bytes for header     */
                                                /*  2 bytes for url count  */
                                                /*  2 bytes for scope list len */
                                                /*  2 bytes for attr list len */
                                                /*  1 byte for authblock count */
        size += G_SlpdProperty.myUrlLen;
        size += G_SlpdProperty.useScopesLen;
        /* TODO: size += G_SlpdProperty.SAAttributes */

        result = SLPBufferRealloc(result,size);
        if(result == 0)
        {
            /* TODO: out of memory, what should we do here! */
            errorcode = SLP_ERROR_INTERNAL_ERROR;
            goto FINISHED;
        }

        /*----------------*/
        /* Add the header */
        /*----------------*/
        /*version*/
        *(result->start)       = 2;
        /*function id*/
        *(result->start + 1)   = SLP_FUNCT_SAADVERT;
        /*length*/
        ToUINT24(result->start + 2, size);
        /*flags*/
        ToUINT16(result->start + 5,
                 size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
        /*ext offset*/
        ToUINT24(result->start + 7,0);
        /*xid*/
        ToUINT16(result->start + 10,message->header.xid);
        /*lang tag len*/
        ToUINT16(result->start + 12,message->header.langtaglen);
        /*lang tag*/
        memcpy(result->start + 14,
               message->header.langtag,
               message->header.langtaglen);

        /*--------------------------*/
        /* Add rest of the SAAdvert */
        /*--------------------------*/
        result->curpos = result->start + 14 + message->header.langtaglen;
        /* url len */
        ToUINT16(result->curpos, G_SlpdProperty.myUrlLen);
        result->curpos = result->curpos + 2;
        /* url */
        memcpy(result->curpos,G_SlpdProperty.myUrl,G_SlpdProperty.myUrlLen);
        result->curpos = result->curpos + G_SlpdProperty.myUrlLen;
        /* scope list len */
        ToUINT16(result->curpos, G_SlpdProperty.useScopesLen);
        result->curpos = result->curpos + 2;
        /* scope list */
        memcpy(result->curpos,G_SlpdProperty.useScopes,G_SlpdProperty.useScopesLen);
        result->curpos = result->curpos + G_SlpdProperty.useScopesLen;
        /* attr list len */
        /* ToUINT16(result->curpos,G_SlpdProperty.SAAttributesLen) */
        ToUINT16(result->curpos, 0);
        result->curpos = result->curpos + 2;
        /* attr list */
        /* memcpy(result->start,G_SlpdProperty.SAAttributes,G_SlpdProperty.SAAttributesLen) */
        /* authblock count */
        *(result->curpos) = 0;
    }

    FINISHED:

    *sendbuf = result;

    return errorcode;
}
Beispiel #22
0
/*=========================================================================*/
int SLPDDatabaseFindAttr(SLPAttrRqst* attrrqst,
                         SLPDDatabaseAttr* result)
/* Find attributes                                                         */
/*                                                                         */
/* srvtyperqst  (IN) the request to find.                                  */
/*                                                                         */
/* result   (OUT) pointer to a result structure that receives              */
/*                results                                                  */
/*                                                                         */
/* Returns  -   1 on success, zero if not found, negative on error         */
/*=========================================================================*/
{
    SLPDDatabaseEntry*  entry   = 0;
    int                 found   = 0;

    found = 0;
    entry = (SLPDDatabaseEntry*)G_DatabaseList.head;
    while(entry)
    {
        if(SLPCompareString(attrrqst->urllen,
                            attrrqst->url,
                            entry->urllen,
                            entry->url) == 0 ||
                SLPCompareSrvType(attrrqst->urllen,
                                  attrrqst->url,
                                  entry->srvtypelen,
                                  entry->srvtype) == 0)
        {
            if(SLPIntersectStringList(attrrqst->scopelistlen,
                                      attrrqst->scopelist,
                                      entry->scopelistlen,
                                      entry->scopelist))
            {
#ifdef USE_PREDICATES
                if(attrrqst->taglistlen && entry->attr)
                {
                    /* serialize into entry->partiallist and return partiallist */
                    int count;
                    SLPError err;

                    /* TRICKY: null terminate the taglist. This is squishes the spistrlen */
                    /*         which is not a problem because it was already copied       */
                    ((char*)attrrqst->taglist)[attrrqst->taglistlen] = 0;
                    err = SLPAttrSerialize(entry->attr,
                                           attrrqst->taglist,
                                           &entry->partiallist,
                                           entry->partiallistlen,
                                           &count,
                                           SLP_FALSE);
                    if(err == SLP_BUFFER_OVERFLOW)
                    {
                        /* free previously allocated memory */
                        free(entry->partiallist);
                        entry->partiallist = 0;
                        entry->partiallistlen = 0;

                        /* SLPAttrSerialize will allocate memory for us */
                        err = SLPAttrSerialize(entry->attr,
                                               attrrqst->taglist,
                                               &entry->partiallist,
                                               entry->partiallistlen,
                                               &entry->partiallistlen,
                                               SLP_FALSE);
                        entry->partiallistlen = count;
                    }

                    if(err == SLP_OK)
                    {
                        result->attrlistlen = entry->partiallistlen;
                        result->attrlist = entry->partiallist;
                        found = 1;
                        break;
                    }
                }
                else
#endif

                {
                    result->attrlistlen = entry->attrlistlen;
                    result->attrlist = entry->attrlist;
                    found = 1;
                    break;
                }
            }
        }

        entry = (SLPDDatabaseEntry*)entry->listitem.next;
    }

    return found;
}
Beispiel #23
0
/*-------------------------------------------------------------------------*/
int ProcessAttrRqst(struct sockaddr_in* peeraddr,
                    SLPMessage message,
                    SLPBuffer* sendbuf,
                    int errorcode)
/*-------------------------------------------------------------------------*/
{
    SLPDDatabaseAttr        attr;
    int                     size        = 0;
    int                     found       = 0;
    SLPBuffer               result      = *sendbuf;

    /*--------------------------------------------------------------*/
    /* If errorcode is set, we can not be sure that message is good */
    /* Go directly to send response code                            */
    /*--------------------------------------------------------------*/
    if(errorcode)
    {
        goto RESPOND;
    }

    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if(SLPIntersectStringList(message->body.attrrqst.prlistlen,
                              message->body.attrrqst.prlist,
                              G_SlpdProperty.interfacesLen,
                              G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /* TODO: check the spi list of the message and return                  */
    /*       AUTHENTICATION_UNKNOWN since we do not do authentication yet  */

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if(SLPIntersectStringList(message->body.attrrqst.scopelistlen,
                              message->body.attrrqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes))
    {
        /*-------------------------------*/
        /* Find attributes in the database */
        /*-------------------------------*/
        found = SLPDDatabaseFindAttr(&(message->body.attrrqst), &attr);
        if(found < 0)
        {
            found = 0;
            errorcode   = SLP_ERROR_INTERNAL_ERROR;
        }
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }


    RESPOND:
    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if(found == 0 ||
       errorcode != 0)
    {
        if(message->header.flags & SLP_FLAG_MCAST ||
           ISMCAST(peeraddr->sin_addr))
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }

    /*--------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole attrrply */
    /*--------------------------------------------------------------*/
    size = message->header.langtaglen + 20; /* 14 bytes for header     */
                                            /*  2 bytes for error code */
                                            /*  2 bytes for attr-list len */
                                            /*  2 bytes for the authblockcount */
    size += attr.attrlistlen;

    /*-------------------*/
    /* Alloc the  buffer */
    /*-------------------*/
    result = SLPBufferRealloc(result,size);
    if(result == 0)
    {
        found = 0;
        errorcode = SLP_ERROR_INTERNAL_ERROR;
        goto FINISHED;
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 2;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_ATTRRPLY;
    /*length*/
    ToUINT24(result->start + 2,size);
    /*flags*/
    ToUINT16(result->start + 5,
             size > SLP_MAX_DATAGRAM_SIZE ? SLP_FLAG_OVERFLOW : 0);
    /*ext offset*/
    ToUINT24(result->start + 7,0);
    /*xid*/
    ToUINT16(result->start + 10,message->header.xid);
    /*lang tag len*/
    ToUINT16(result->start + 12,message->header.langtaglen);
    /*lang tag*/
    memcpy(result->start + 14,
           message->header.langtag,
           message->header.langtaglen);

    /*--------------------------*/
    /* Add rest of the AttrRqst */
    /*--------------------------*/
    result->curpos = result->start + 14 + message->header.langtaglen;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos = result->curpos + 2;
    /* attr-list len */
    ToUINT16(result->curpos, attr.attrlistlen);
    result->curpos = result->curpos + 2;
    memcpy(result->curpos, attr.attrlist, attr.attrlistlen);
    result->curpos = result->curpos + attr.attrlistlen;


    /* TODO: no auth block */
    ToUINT16(result->curpos, 0);

    FINISHED:
    *sendbuf = result;

    return errorcode;
}        
Beispiel #24
0
/*-------------------------------------------------------------------------*/
int v1ProcessSrvTypeRqst(struct sockaddr_in* peeraddr,
                         SLPMessage message,
                         SLPBuffer* sendbuf,
                         int errorcode)
/*-------------------------------------------------------------------------*/
{
    int                     i, typelen;
    int                     size         = 0;
    int                     count        = 0;
    int                     found        = 0;
    SLPDDatabaseSrvType*    srvtypearray = 0;
    SLPBuffer               result       = *sendbuf;


    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if(SLPIntersectStringList(message->body.srvtyperqst.prlistlen,
                              message->body.srvtyperqst.prlist,
                              G_SlpdProperty.interfacesLen,
                              G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------------------------------------*/
    if(SLPIntersectStringList(message->body.srvtyperqst.scopelistlen,
                              message->body.srvtyperqst.scopelist,
                              G_SlpdProperty.useScopesLen,
                              G_SlpdProperty.useScopes) != 0)
    {
        /*------------------------------------*/
        /* Find service types in the database */
        /*------------------------------------*/
        while(found == count)
        {
            count += G_SlpdProperty.maxResults;

            if(srvtypearray) free(srvtypearray);
            srvtypearray = (SLPDDatabaseSrvType*)malloc(sizeof(SLPDDatabaseSrvType) * count);
            if(srvtypearray == 0)
            {
                found       = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }

            found = SLPDDatabaseFindType(&(message->body.srvtyperqst), srvtypearray, count);
            if(found < 0)
            {
                found = 0;
                errorcode   = SLP_ERROR_INTERNAL_ERROR;
                break;
            }
        }

        /* remember the amount found if is really big for next time */
        if(found > G_SlpdProperty.maxResults)
        {
            G_SlpdProperty.maxResults = found;
        }
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if(message->header.flags & SLP_FLAG_MCAST)
    {
        if(found == 0 || errorcode != 0)
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }


    /*-----------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvtyperply */
    /*-----------------------------------------------------------------*/
    size = 16; /* 12 bytes for header, 2 bytes for error code, 2 bytes
          for srvtype count  */
    if(errorcode == 0)
    {
        for(i=0;i<found;i++)
        {
            typelen = INT_MAX;
            errorcode = SLPv1ToEncoding(0, &typelen,
                                        message->header.encoding,  
                                        srvtypearray[i].type,
                                        srvtypearray[i].typelen);
            if(errorcode)
                break;
            size += typelen + 2;  /*  2 byte for length */
        }
    }
    result = SLPBufferRealloc(result,size);
    if(result == 0)
    {
        found = 0;
        errorcode = SLP_ERROR_INTERNAL_ERROR;
    }


    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 1;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVTYPERPLY;
    /*length*/
    ToUINT16(result->start + 2, size);
    /*flags - TODO set the flags correctly */
    *(result->start + 4) = message->header.flags |
                           (size > SLP_MAX_DATAGRAM_SIZE ? SLPv1_FLAG_OVERFLOW : 0);  
    /*dialect*/
    *(result->start + 5) = 0;
    /*language code*/
    memcpy(result->start + 6, message->header.langtag, 2);
    ToUINT16(result->start + 8, message->header.encoding);
    /*xid*/
    ToUINT16(result->start + 10, message->header.xid);

    /*-----------------------------*/
    /* Add rest of the SrvTypeRply */
    /*-----------------------------*/
    result->curpos = result->start + 12;

    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos += 2;

    /* service type count */
    ToUINT16(result->curpos, found);
    result->curpos += 2;

    /* TODO - make sure we don't return generic types */
    for(i=0;i<found;i++)
    {
        typelen = size;
        SLPv1ToEncoding(result->curpos + 2, &typelen,
                        message->header.encoding,  
                        srvtypearray[i].type,
                        srvtypearray[i].typelen);
        ToUINT16(result->curpos, srvtypearray[i].typelen);
        result->curpos += 2 + typelen;
    }

    FINISHED:   
    if(srvtypearray) free(srvtypearray);
    *sendbuf = result;
    return errorcode;
}
Beispiel #25
0
/** Process a SrvTypeRequest message.
 *
 * @param[in] message - The message to process.
 * @param[out] sendbuf - The response buffer to fill.
 * @param[in] errorcode - The error code from the client request.
 *
 * @return Zero on success, or a non-zero SLP error on failure.
 *
 * @internal
 */
static int ProcessSrvTypeRqst(SLPMessage * message, SLPBuffer * sendbuf,
      int errorcode)
{
   size_t size = 0;
   SLPDDatabaseSrvTypeRqstResult * db = 0;
   SLPBuffer result = *sendbuf;

   /* If errorcode is set, we can not be sure that message is good
      Go directly to send response code                            
    */
   if (errorcode)
      goto RESPOND;

   /* check for one of our IP addresses in the prlist */
   if (SLPIntersectStringList(message->body.srvtyperqst.prlistlen, 
         message->body.srvtyperqst.prlist, G_SlpdProperty.interfacesLen,
         G_SlpdProperty.interfaces))
   {
      /* Silently ignore */
      result->end = result->start;
      goto FINISHED;  
   }

   /* make sure that we handle the scope */
   if (SLPIntersectStringList(message->body.srvtyperqst.scopelistlen,
         message->body.srvtyperqst.scopelist, G_SlpdProperty.useScopesLen,
         G_SlpdProperty.useScopes) != 0)
      errorcode = SLPDDatabaseSrvTypeRqstStart(message, &db);
   else
      errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;

RESPOND:

   /* do not send error codes or empty replies to multicast requests */
   if (errorcode != 0 || db->srvtypelistlen == 0)
      if (message->header.flags & SLP_FLAG_MCAST 
            || SLPNetIsMCast(&(message->peer)))
      {
         result->end = result->start;
         goto FINISHED;  
      }

   /* ensure the buffer is big enough to handle the whole srvtyperply */
   size = message->header.langtaglen + 18;   /* 14 bytes for header     */
                                             /*  2 bytes for error code */
                                             /*  2 bytes for srvtype len */
   if (errorcode == 0)
      size += db->srvtypelistlen;

   /* Reallocate the result buffer */
   result = SLPBufferRealloc(result, size);
   if (result == 0)
   {
      errorcode = SLP_ERROR_INTERNAL_ERROR;
      goto FINISHED;
   }

   /* Add the header */

   /* version */
   *result->curpos++ = 2;

   /* function id */
   *result->curpos++ = SLP_FUNCT_SRVTYPERPLY;

   /* length */
   PutUINT24(&result->curpos, size);

   /* flags */
   PutUINT16(&result->curpos, (size > (size_t)G_SlpdProperty.MTU?
         SLP_FLAG_OVERFLOW: 0));

   /* ext offset */
   PutUINT24(&result->curpos, 0);

   /* xid */
   PutUINT16(&result->curpos, message->header.xid);

   /* lang tag len */
   PutUINT16(&result->curpos, message->header.langtaglen);

   /* lang tag */
   memcpy(result->curpos, message->header.langtag,
         message->header.langtaglen);
   result->curpos += message->header.langtaglen;

   /* Add rest of the SrvTypeRply */

   /* error code*/
   PutUINT16(&result->curpos, errorcode);
   if (errorcode == 0)
   {
      /* length of srvtype-list */
      PutUINT16(&result->curpos, db->srvtypelistlen);
      memcpy(result->curpos, db->srvtypelist, db->srvtypelistlen);
      result->curpos += db->srvtypelistlen;
   }

FINISHED:   

   if (db) 
      SLPDDatabaseSrvTypeRqstEnd(db);

   *sendbuf = result;

   return errorcode;
}
Beispiel #26
0
/*-------------------------------------------------------------------------*/
int v1ProcessSrvRqst(struct sockaddr_in* peeraddr,
                     SLPMessage message,
                     SLPBuffer* sendbuf,
                     int errorcode)
/*-------------------------------------------------------------------------*/
{
    int                         i;
    int                         urllen;
    int                         size        = 0;
    SLPDDatabaseSrvRqstResult*  db          = 0;
    SLPBuffer                   result      = *sendbuf;

    /*--------------------------------------------------------------*/
    /* If errorcode is set, we can not be sure that message is good */
    /* Go directly to send response code                            */
    /*--------------------------------------------------------------*/
    if (errorcode)
    {
        goto RESPOND;
    }

    /*-------------------------------------------------*/
    /* Check for one of our IP addresses in the prlist */
    /*-------------------------------------------------*/
    if (SLPIntersectStringList(message->body.srvrqst.prlistlen,
                               message->body.srvrqst.prlist,
                               G_SlpdProperty.interfacesLen,
                               G_SlpdProperty.interfaces))
    {
        result->end = result->start;
        goto FINISHED;
    }

    /*------------------------------------------------*/
    /* Check to to see if a this is a special SrvRqst */
    /*------------------------------------------------*/
    if (SLPCompareString(message->body.srvrqst.srvtypelen,
                         message->body.srvrqst.srvtype,
                         15,
                         "directory-agent") == 0)
    {
        errorcode = v1ProcessDASrvRqst(peeraddr, message, sendbuf, errorcode);
        return errorcode;
    }

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if (SLPIntersectStringList(message->body.srvrqst.scopelistlen,
                               message->body.srvrqst.scopelist,
                               G_SlpdProperty.useScopesLen,
                               G_SlpdProperty.useScopes) != 0)
    {
        /*-------------------------------*/
        /* Find services in the database */
        /*-------------------------------*/
        errorcode = SLPDDatabaseSrvRqstStart(message, &db);
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }


    RESPOND:
    /*----------------------------------------------------------------*/
    /* Do not send error codes or empty replies to multicast requests */
    /*----------------------------------------------------------------*/
    if (message->header.flags & SLP_FLAG_MCAST)
    {
        if (errorcode != 0 || db->urlcount == 0)
        {
            result->end = result->start;
            goto FINISHED;  
        }
    }

    /*-------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvrply */
    /*-------------------------------------------------------------*/
    size = 16; /* 12 bytes for header, 2 bytes for error code, 2 bytes
          for url count */
    if (errorcode == 0)
    {
        for (i = 0; i < db->urlcount; i++)
        {
            urllen = INT_MAX;
            errorcode = SLPv1ToEncoding(0, 
                                        &urllen,
                                        message->header.encoding,  
                                        db->urlarray[i]->url,
                                        db->urlarray[i]->urllen);
            if (errorcode)
                break;
            size += urllen + 4; /* 2 bytes for lifetime, 2 bytes for urllen */
        } 
        result = SLPBufferRealloc(result,size);
        if (result == 0)
        {
            errorcode = SLP_ERROR_INTERNAL_ERROR;
        }
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 1;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVRPLY;
    /*length*/
    ToUINT16(result->start + 2, size);
    /*flags - TODO set the flags correctly */
    *(result->start + 4) = message->header.flags |
                           (size > SLP_MAX_DATAGRAM_SIZE ? SLPv1_FLAG_OVERFLOW : 0);  
    /*dialect*/
    *(result->start + 5) = 0;
    /*language code*/
    memcpy(result->start + 6, message->header.langtag, 2);
    ToUINT16(result->start + 8, message->header.encoding);
    /*xid*/
    ToUINT16(result->start + 10, message->header.xid);

    /*-------------------------*/
    /* Add rest of the SrvRply */
    /*-------------------------*/
    result->curpos = result->start + 12;
    /* error code*/
    ToUINT16(result->curpos, errorcode);
    result->curpos = result->curpos + 2;
    if (errorcode == 0)
    {
        /* urlentry count */
        ToUINT16(result->curpos, db->urlcount);
        result->curpos = result->curpos + 2;
        for (i = 0; i < db->urlcount; i++)
        {
            /* url-entry lifetime */
            ToUINT16(result->curpos, db->urlarray[i]->lifetime);
            result->curpos = result->curpos + 2;
            /* url-entry url and urllen */
            urllen = size;      
            errorcode = SLPv1ToEncoding(result->curpos + 2, 
                                        &urllen,
                                        message->header.encoding,  
                                        db->urlarray[i]->url,
                                        db->urlarray[i]->urllen);
            ToUINT16(result->curpos, urllen);
            result->curpos = result->curpos + 2 + urllen;
        }
    }
    else
    {
        /* urlentry count */
        ToUINT16(result->curpos, 0);
        result->curpos = result->curpos + 2;
    }

    FINISHED:   

    SLPDDatabaseSrvRqstEnd(db);

    *sendbuf = result;

    return errorcode;
}
Beispiel #27
0
/** Process a general service request message.
 *
 * @param[in] message - The message to process.
 * @param[out] sendbuf - The response buffer to fill.
 * @param[in] errorcode - The error code from the client request.
 *
 * @return Zero on success, or a non-zero SLP error on failure.
 *
 * @internal
 */
static int ProcessSrvRqst(SLPMessage * message, SLPBuffer * sendbuf, 
      int errorcode)
{
   int i;
   SLPUrlEntry * urlentry;
   SLPDDatabaseSrvRqstResult * db = 0;
   size_t size = 0;
   SLPBuffer result = *sendbuf;

#ifdef ENABLE_SLPv2_SECURITY
   SLPAuthBlock * authblock = 0;
   int j;
#endif

   /* If errorcode is set, we can not be sure that message is good
      Go directly to send response code 
    */
   if (errorcode)
      goto RESPOND;

   /* Check for one of our IP addresses in the prlist */
   if (SLPIntersectStringList(message->body.srvrqst.prlistlen, 
         message->body.srvrqst.prlist, G_SlpdProperty.interfacesLen,
         G_SlpdProperty.interfaces))
   {
      /* silently ignore */
      result->end = result->start;
      goto FINISHED;
   }

   /* Make sure that we handle at least verify registrations made with
      the requested SPI.  If we can't then have to return an error
      because there is no way we can return URL entries that are
      signed in a way the requester can understand
    */
#ifdef ENABLE_SLPv2_SECURITY
   if (G_SlpdProperty.securityEnabled)
   {
      if (SLPSpiCanVerify(G_SlpdSpiHandle, message->body.srvrqst.spistrlen,
            message->body.srvrqst.spistr) == 0)
      {
         errorcode = SLP_ERROR_AUTHENTICATION_UNKNOWN;
         goto RESPOND;
      }
   }
   else if (message->body.srvrqst.spistrlen)
   {
      errorcode = SLP_ERROR_AUTHENTICATION_UNKNOWN;
      goto RESPOND;
   }
#else
   if (message->body.srvrqst.spistrlen)
   {
      errorcode = SLP_ERROR_AUTHENTICATION_UNKNOWN;
      goto RESPOND;
   }
#endif

   /* check to to see if a this is a special SrvRqst */
   if (SLPCompareString(message->body.srvrqst.srvtypelen, 
         message->body.srvrqst.srvtype, 23, SLP_DA_SERVICE_TYPE) == 0)
   {
      errorcode = ProcessDASrvRqst(message, sendbuf, errorcode);
      if (errorcode == 0)
      {
         /* Since we have an errorcode of 0, we were successful,
            and have already formed a response packet; return now.
          */
         return errorcode;
      }
      goto RESPOND;
   }
   if (SLPCompareString(message->body.srvrqst.srvtypelen, 
         message->body.srvrqst.srvtype, 21, SLP_SA_SERVICE_TYPE) == 0)
   {
      errorcode = ProcessSASrvRqst(message, sendbuf, errorcode);
      if (errorcode == 0)
      {
         /* Since we have an errorcode of 0, we were successful,
            and have already formed a response packet; return now.
          */
         return errorcode;
      }
      goto RESPOND;
   }

   /* make sure that we handle the scope */
   if (SLPIntersectStringList(message->body.srvrqst.scopelistlen, 
         message->body.srvrqst.scopelist, G_SlpdProperty.useScopesLen,
         G_SlpdProperty.useScopes) != 0)
      errorcode = SLPDDatabaseSrvRqstStart(message, &db);
   else
      errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;

RESPOND:

   /* do not send error codes or empty replies to multicast requests */
   if (errorcode != 0 || db->urlcount == 0)
   {
      if (message->header.flags & SLP_FLAG_MCAST 
            || SLPNetIsMCast(&(message->peer)))
      {
         result->end = result->start;
         goto FINISHED;  
      }
   }

   /* ensure the buffer is big enough to handle the whole srvrply */
   size = message->header.langtaglen + 18;/* 14 bytes for header     */
                                          /*  2 bytes for error code */
                                          /*  2 bytes for url count  */
   if (errorcode == 0)
   {
      for (i = 0; i < db->urlcount; i++)
      {
         /* urlentry is the url from the db result */
         urlentry = db->urlarray[i];

         size += urlentry->urllen + 6; /*  1 byte for reserved  */
                                       /*  2 bytes for lifetime */
                                       /*  2 bytes for urllen   */
                                       /*  1 byte for authcount */
#ifdef ENABLE_SLPv2_SECURITY
         /* make room to include the authblock that was asked for */
         if (G_SlpdProperty.securityEnabled 
               && message->body.srvrqst.spistrlen)
         {
            for (j = 0; j < urlentry->authcount; j++)
            {
               if (SLPCompareString(urlentry->autharray[j].spistrlen,
                     urlentry->autharray[j].spistr,
                     message->body.srvrqst.spistrlen,
                     message->body.srvrqst.spistr) == 0)
               {
                  authblock = &(urlentry->autharray[j]);
                  size += authblock->length;
                  break;
               }
            }
         }
#endif 
      }
   }

   /* reallocate the result buffer */
   result = SLPBufferRealloc(result, size);
   if (result == 0)
   {
      errorcode = SLP_ERROR_INTERNAL_ERROR;
      goto FINISHED;
   }

   /* add the header */

   /* version */
   *result->curpos++ = 2;

   /* function id */
   *result->curpos++ = SLP_FUNCT_SRVRPLY;

   /* length */
   PutUINT24(&result->curpos, size);

   /* flags */
   PutUINT16(&result->curpos, (size > (size_t)G_SlpdProperty.MTU? 
         SLP_FLAG_OVERFLOW: 0));

   /* ext offset */
   PutUINT24(&result->curpos, 0);

   /* xid */
   PutUINT16(&result->curpos, message->header.xid);

   /* lang tag len */
   PutUINT16(&result->curpos, message->header.langtaglen);

   /* lang tag */
   memcpy(result->curpos, message->header.langtag,
         message->header.langtaglen);
   result->curpos += message->header.langtaglen;

   /* add rest of the SrvRply */

   /* error code*/
   PutUINT16(&result->curpos, errorcode);
   if (errorcode == 0)
   {
      /* urlentry count */
      PutUINT16(&result->curpos, db->urlcount);
      for (i = 0; i < db->urlcount; i++)
      {
         /* urlentry is the url from the db result */
         urlentry = db->urlarray[i]; 

#ifdef ENABLE_SLPv1
         if (urlentry->opaque == 0)
         {
            /* url-entry reserved */
            *result->curpos++ = 0;        

            /* url-entry lifetime */
            PutUINT16(&result->curpos, urlentry->lifetime);

            /* url-entry urllen */
            PutUINT16(&result->curpos, urlentry->urllen);

            /* url-entry url */
            memcpy(result->curpos, urlentry->url, urlentry->urllen);
            result->curpos += urlentry->urllen;

            /* url-entry auths */
            *result->curpos++ = 0;
         }
         else
#endif
         {
            /* Use an opaque copy if available (and authentication is 
             * not being used).
             */

            /* TRICKY: Fix up the lifetime. */
            TO_UINT16(urlentry->opaque + 1, urlentry->lifetime);
            memcpy(result->curpos, urlentry->opaque, urlentry->opaquelen);
            result->curpos += urlentry->opaquelen;
         }
      }
   }
   else
      PutUINT16(&result->curpos, 0); /* set urlentry count to 0*/

FINISHED:   

   if (db) 
      SLPDDatabaseSrvRqstEnd(db);

   *sendbuf = result;

   return errorcode;
}
Beispiel #28
0
/*-------------------------------------------------------------------------*/
int v1ProcessSrvReg(struct sockaddr_in* peeraddr,
                    SLPMessage message,
                    SLPBuffer recvbuf,
                    SLPBuffer* sendbuf,
                    int errorcode)
/*                                                                         */
/* Returns: non-zero if message should be silently dropped                 */
/*-------------------------------------------------------------------------*/
{
    SLPBuffer       result = *sendbuf;

    /*--------------------------------------------------------------*/
    /* If errorcode is set, we can not be sure that message is good */
    /* Go directly to send response code  also do not process mcast */
    /* srvreg or srvdereg messages                                  */
    /*--------------------------------------------------------------*/
    if (errorcode || message->header.flags & SLP_FLAG_MCAST)
    {
        goto RESPOND;
    }

    /*------------------------------------*/
    /* Make sure that we handle the scope */
    /*------ -----------------------------*/
    if (SLPIntersectStringList(message->body.srvreg.scopelistlen,
                               message->body.srvreg.scopelist,
                               G_SlpdProperty.useScopesLen,
                               G_SlpdProperty.useScopes))
    {
        /*---------------------------------*/
        /* put the service in the database */
        /*---------------------------------*/
        if (ISLOCAL(message->peer.sin_addr))
        {
            message->body.srvreg.source= SLP_REG_SOURCE_LOCAL;
        }
        else
        {
            message->body.srvreg.source = SLP_REG_SOURCE_REMOTE;
        }

        errorcode = SLPDDatabaseReg(message,recvbuf);
    }
    else
    {
        errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;
    }

    RESPOND:    
    /*--------------------------------------------------------------------*/
    /* don't send back reply anything multicast SrvReg (set result empty) */
    /*--------------------------------------------------------------------*/
    if (message->header.flags & SLP_FLAG_MCAST)
    {
        result->end = result->start;
        goto FINISHED;
    }


    /*------------------------------------------------------------*/
    /* ensure the buffer is big enough to handle the whole srvack */
    /*------------------------------------------------------------*/
    result = SLPBufferRealloc(result, 14);
    if (result == 0)
    {
        errorcode = SLP_ERROR_INTERNAL_ERROR;
        goto FINISHED;
    }

    /*----------------*/
    /* Add the header */
    /*----------------*/
    /*version*/
    *(result->start)       = 1;
    /*function id*/
    *(result->start + 1)   = SLP_FUNCT_SRVACK;
    /*length*/
    ToUINT16(result->start + 2, 14);
    /*flags - TODO set the flags correctly */
    *(result->start + 4) = 0;
    /*dialect*/
    *(result->start + 5) = 0;
    /*language code*/
    memcpy(result->start + 6, message->header.langtag, 2);
    ToUINT16(result->start + 8, message->header.encoding);
    /*xid*/
    ToUINT16(result->start + 10, message->header.xid);

    /*-------------------*/
    /* Add the errorcode */
    /*-------------------*/
    ToUINT16(result->start + 12, errorcode);

    FINISHED:
    *sendbuf = result;
    return errorcode;
}
Beispiel #29
0
/** Process an SA SrvRequest message.
 *
 * @param[in] message - The message to process.
 * @param[out] sendbuf - The response buffer to fill.
 * @param[in] errorcode - The error code from the client request.
 *
 * @return Zero on success, or a non-zero SLP error on failure.
 *
 * @internal
 */
static int ProcessSASrvRqst(SLPMessage * message, SLPBuffer * sendbuf,
      int errorcode)
{
   char localaddr_str[INET6_ADDRSTRLEN + 2];
   size_t size = 0;
   SLPBuffer result = *sendbuf;

   if (message->body.srvrqst.scopelistlen == 0 
         || SLPIntersectStringList(message->body.srvrqst.scopelistlen,
               message->body.srvrqst.scopelist, G_SlpdProperty.useScopesLen,
               G_SlpdProperty.useScopes) != 0)
   {
      /* send back a SAAdvert */

      /* ensure the buffer is big enough to handle the whole SAAdvert */
      size = message->header.langtaglen + 21;/* 14 bytes for header     */
                                             /*  2 bytes for url count  */
                                             /*  2 bytes for scope list len */
                                             /*  2 bytes for attr list len */
                                             /*  1 byte for authblock count */
      size += G_SlpdProperty.urlPrefixLen;
      localaddr_str[0] = 0;
      if (message->localaddr.ss_family == AF_INET) 
         inet_ntop(message->localaddr.ss_family, &((struct sockaddr_in *)
               &message->localaddr)->sin_addr, localaddr_str, 
               sizeof(localaddr_str));
      else if (message->localaddr.ss_family == AF_INET6) 
      {
         strcpy(localaddr_str, "[");
         inet_ntop(message->localaddr.ss_family, &((struct sockaddr_in6 *) 
               &message->localaddr)->sin6_addr, &localaddr_str[1], 
               sizeof(localaddr_str) - 1);
         strcat(localaddr_str, "]");
      }
      size += strlen(localaddr_str);
      size += G_SlpdProperty.useScopesLen;

      /* TODO: size += G_SlpdProperty.SAAttributes */

      result = SLPBufferRealloc(result,size);
      if (result == 0)
      {
         /* TODO: out of memory, what should we do here! */
         errorcode = SLP_ERROR_INTERNAL_ERROR;
         goto FINISHED;
      }

      /* Add the header */

      /* version */
      *result->curpos++ = 2;

      /* function id */
      *result->curpos++ = SLP_FUNCT_SAADVERT;

      /* length */
      PutUINT24(&result->curpos, size);

      /* flags */
      PutUINT16(&result->curpos, (size > (size_t)G_SlpdProperty.MTU? 
            SLP_FLAG_OVERFLOW: 0));

      /* ext offset */
      PutUINT24(&result->curpos, 0);

      /* xid */
      PutUINT16(&result->curpos, message->header.xid);

      /* lang tag len */
      PutUINT16(&result->curpos, message->header.langtaglen);

      /* lang tag */
      memcpy(result->curpos, message->header.langtag,
            message->header.langtaglen);
      result->curpos += message->header.langtaglen;

      /* Add rest of the SAAdvert */

      /* url len */
      PutUINT16(&result->curpos, G_SlpdProperty.urlPrefixLen 
            + strlen(localaddr_str));

      /* url */
      memcpy(result->curpos, G_SlpdProperty.urlPrefix,
            G_SlpdProperty.urlPrefixLen);
      result->curpos += G_SlpdProperty.urlPrefixLen;
      memcpy(result->curpos, localaddr_str, strlen(localaddr_str));
      result->curpos += strlen(localaddr_str);

      /* scope list len */
      PutUINT16(&result->curpos, G_SlpdProperty.useScopesLen);

      /* scope list */
      memcpy(result->curpos, G_SlpdProperty.useScopes,
            G_SlpdProperty.useScopesLen);
      result->curpos += G_SlpdProperty.useScopesLen;

      /* attr list len */
      /* PutUINT16(&result->curpos, G_SlpdProperty.SAAttributesLen) */
      PutUINT16(&result->curpos, 0);

      /* attr list */
      /* memcpy(result->curpos, G_SlpdProperty.SAAttributes,
            G_SlpdProperty.SAAttributesLen) */

      /* authblock count */
      *result->curpos++ = 0;
   }
   else
      errorcode = SLP_ERROR_SCOPE_NOT_SUPPORTED;

FINISHED:

   *sendbuf = result;

   return errorcode;
}
Beispiel #30
0
/*=========================================================================*/
int SLPDDatabaseReg(SLPMessage msg, SLPBuffer buf)
/* Add a service registration to the database                              */
/*                                                                         */
/* msg          (IN) SLPMessage of a SrvReg message as returned by         */
/*                   SLPMessageParse()                                     */
/*                                                                         */
/* buf          (IN) Otherwise unreferenced buffer interpreted by the msg  */
/*                   structure                                             */
/*                                                                         */
/* Returns  -   Zero on success.  Nonzero on error                         */
/*                                                                         */
/* NOTE:        All registrations are treated as fresh                     */
/*=========================================================================*/
{
    SLPDatabaseHandle   dh;
    SLPDatabaseEntry*   entry;
    SLPSrvReg*          entryreg;
    SLPSrvReg*          reg;
    int                 result;

    /* reg is the SrvReg message being registered */
    reg = &(msg->body.srvreg);

    /* check service-url syntax */
    if ( SLPCheckServiceUrlSyntax(reg->urlentry.url, reg->urlentry.urllen) )
    {
        return SLP_ERROR_INVALID_REGISTRATION;
    }

    /* check attr-list syntax */
    if ( reg->attrlistlen &&
         SLPCheckAttributeListSyntax(reg->attrlist,reg->attrlistlen) )
    {
        return SLP_ERROR_INVALID_REGISTRATION;
    }

    dh = SLPDatabaseOpen(&G_SlpdDatabase.database);
    if ( dh )
    {
        /*-----------------------------------------------------*/
        /* Check to see if there is already an identical entry */
        /*-----------------------------------------------------*/
        while ( 1 )
        {
            entry = SLPDatabaseEnum(dh);
            if ( entry == NULL ) break;

            /* entry reg is the SrvReg message from the database */
            entryreg = &(entry->msg->body.srvreg);

            if ( SLPCompareString(entryreg->urlentry.urllen,
                                  entryreg->urlentry.url,
                                  reg->urlentry.urllen,
                                  reg->urlentry.url) == 0 )
            {
                if ( SLPIntersectStringList(entryreg->scopelistlen,
                                            entryreg->scopelist,
                                            reg->scopelistlen,
                                            reg->scopelist) > 0 )
                {

                    /* Check to ensure the source addr is the same */
                    /* as the original */
                    if ( G_SlpdProperty.checkSourceAddr &&
                         memcmp(&(entry->msg->peer.sin_addr),
                                &(msg->peer.sin_addr),
                                sizeof(struct in_addr)) )
                    {
                        SLPDatabaseClose(dh);
                        return SLP_ERROR_AUTHENTICATION_FAILED;
                    }

#ifdef ENABLE_SLPv2_SECURITY
                    if ( entryreg->urlentry.authcount &&
                         entryreg->urlentry.authcount != reg->urlentry.authcount )
                    {
                        SLPDatabaseClose(dh);
                        return SLP_ERROR_AUTHENTICATION_FAILED;
                    }
#endif  
                    /* Remove the identical entry */
                    SLPDatabaseRemove(dh,entry);
                    break;
                }
            }
        }

        /*------------------------------------*/
        /* Add the new srvreg to the database */
        /*------------------------------------*/
        entry = SLPDatabaseEntryCreate(msg,buf);
        if ( entry )
        {
            /* set the source (allows for quicker aging ) */
            if ( msg->body.srvreg.source == SLP_REG_SOURCE_UNKNOWN )
            {
                if ( ISLOCAL(msg->peer.sin_addr) )
                {
                    msg->body.srvreg.source = SLP_REG_SOURCE_LOCAL; 
                }
                else
                {
                    msg->body.srvreg.source = SLP_REG_SOURCE_REMOTE;     
                }
            }

            /* add to database */
            SLPDatabaseAdd(dh, entry);
            SLPDLogRegistration("Registration",entry);

            /* SUCCESS! */
            result = 0;
        }
        else
        {
            result = SLP_ERROR_INTERNAL_ERROR;
        }

        SLPDatabaseClose(dh);
    }
    else
    {
        result = SLP_ERROR_INTERNAL_ERROR;
    }

    return result;
}