示例#1
0
/*=========================================================================*/
void SLPDLogMessage(int msglogflags,
                    struct sockaddr_in* peerinfo,
                    SLPBuffer buf)
/* Log record of receiving or sending an SLP Message.  Logging will only   */
/* occur if message logging is enabled G_SlpProperty.traceMsg != 0         */
/*                                                                         */
/* msglogflags   (IN) What type of message to log                          */
/*                                                                         */
/* peerinfo (IN) the source or destination peer                            */
/*                                                                         */
/* msg      (IN) the message to log                                        */
/*                                                                         */
/* Returns: none                                                           */
/*=========================================================================*/
{
    SLPMessage msg;

    if (peerinfo == NULL ||
        buf == NULL)
    {
        return;
    }

    if ((G_SlpdProperty.traceMsg && (msglogflags & SLPDLOG_TRACEMSG)) ||
        (G_SlpdProperty.traceDrop && (msglogflags & SLPDLOG_TRACEDROP)) )
    {
        /* Don't log localhost traffic since it is probably IPC */
        /* and don't log empty messages                         */
        if (!ISLOCAL(peerinfo->sin_addr) && buf->end != buf->start)
        {
            msg = SLPMessageAlloc();
            if (msg)
            {
                SLPDLog("\n");
                SLPDLogTime();
                SLPDLog("MESSAGE - ");
                if (msglogflags == SLPDLOG_TRACEMSG_OUT)
                {
                    SLPDLog("Trace message (OUT)\n");
                }
                else if (msglogflags == SLPDLOG_TRACEMSG_IN)
                {
                    SLPDLog("Trace message (IN)\n");
                }
                else if (msglogflags == SLPDLOG_TRACEDROP)
                {
                    SLPDLog("Dropped message (following message silently ignored)\n");
                }
                else
                {
                    SLPDLog("\n");
                }

                if (SLPMessageParseBuffer(peerinfo,buf,msg) == 0)
                {
                    SLPDLogMessageInternals(msg);
                }
                else
                {
                    SLPDLog("Message parsing failed\n");
                    SLPDLog("Peer: \n");
                    SLPDLog("   IP address: %s\n", inet_ntoa(msg->peer.sin_addr));          
                }

                SLPMessageFree(msg);
            }
        }
    }
}
示例#2
0
/*-------------------------------------------------------------------------*/
int ProcessSrvReg(struct sockaddr_in* peeraddr,
                  SLPMessage message,
                  SLPBuffer* sendbuf,
                  int errorcode)
/*                                                                         */
/* Returns: non-zero if message should be silently dropped                 */
/*-------------------------------------------------------------------------*/
{
    unsigned int    regtype;
    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))
    {

        /*-------------------------------*/
        /* TODO: Validate the authblocks */
        /*-------------------------------*/


        /*---------------------------------*/
        /* put the service in the database */
        /*---------------------------------*/
        regtype = 0;
        if(message->header.flags & SLP_FLAG_FRESH)
        {
            regtype |= SLPDDATABASE_REG_FRESH;
        }
        if(ISLOCAL(peeraddr->sin_addr))
        {
            regtype |= SLPDDATABASE_REG_LOCAL;
        }
        errorcode = SLPDDatabaseReg(&(message->body.srvreg),regtype);
        if(errorcode > 0)
        {
            errorcode = SLP_ERROR_INVALID_REGISTRATION;
        }
        else if(errorcode < 0)
        {
            errorcode = SLP_ERROR_INTERNAL_ERROR;
        }
    }
    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 ||
       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;
}
示例#3
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;
}
示例#4
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;
}
示例#5
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;
}