Пример #1
0
static void
recv_alive_msg (unsigned length)
{
    CARD8   SessionRunning;
    CARD32  AliveSessionID;

    if (state != XDM_AWAIT_ALIVE_RESPONSE)
	return;
    if (length != 5)
	return;
    if (XdmcpReadCARD8 (&buffer, &SessionRunning) &&
	XdmcpReadCARD32 (&buffer, &AliveSessionID))
    {
    	if (SessionRunning && AliveSessionID == SessionID)
    	{
	    /* backoff dormancy period */
	    state = XDM_RUN_SESSION;
	    if ((GetTimeInMillis() - lastDeviceEventTime.milliseconds) >
		keepaliveDormancy * 1000)
	    {
		keepaliveDormancy <<= 1;
		if (keepaliveDormancy > XDM_MAX_DORMANCY)
		    keepaliveDormancy = XDM_MAX_DORMANCY;
	    }
	    timeOutTime = GetTimeInMillis() + keepaliveDormancy * 1000;
    	}
	else
    	{
	    XdmcpDeadSession ("Alive respose indicates session dead");
    	}
    }
}
Пример #2
0
static void send_alive(struct sockaddr *from, int fromlen, int length, int fd)
{
    CARD32 sessionID;
    CARD16 displayNumber;
    struct display *d;
    XdmcpHeader header;
    CARD8 sendRunning;
    CARD32 sendSessionID;

    Debug("send <alive>\n");
    if(XdmcpReadCARD16(&buffer, &displayNumber) && XdmcpReadCARD32(&buffer, &sessionID))
    {
        if(length == 6)
        {
            if(!(d = FindDisplayBySessionID(sessionID)))
                d = FindDisplayByAddress((XdmcpNetaddr)from, fromlen, displayNumber);
            sendRunning = 0;
            sendSessionID = 0;
            if(d && d->status == running)
            {
                if(d->sessionID == sessionID)
                    sendRunning = 1;
                sendSessionID = d->sessionID;
            }
            header.version = XDM_PROTOCOL_VERSION;
            header.opcode = (CARD16)ALIVE;
            header.length = 5;
            Debug("<alive>: %d %ld\n", sendRunning, (long)sendSessionID);
            XdmcpWriteHeader(&buffer, &header);
            XdmcpWriteCARD8(&buffer, sendRunning);
            XdmcpWriteCARD32(&buffer, sendSessionID);
            XdmcpFlush(fd, &buffer, (XdmcpNetaddr)from, fromlen);
        }
    }
}
Пример #3
0
static void
recv_accept_msg(unsigned length)
{
    CARD32  AcceptSessionID;
    ARRAY8  AcceptAuthenticationName, AcceptAuthenticationData;
    ARRAY8  AcceptAuthorizationName, AcceptAuthorizationData;

    if (state != XDM_AWAIT_REQUEST_RESPONSE)
	return;
    AcceptAuthenticationName.data = 0;
    AcceptAuthenticationData.data = 0;
    AcceptAuthorizationName.data = 0;
    AcceptAuthorizationData.data = 0;
    if (XdmcpReadCARD32 (&buffer, &AcceptSessionID) &&
	XdmcpReadARRAY8 (&buffer, &AcceptAuthenticationName) &&
	XdmcpReadARRAY8 (&buffer, &AcceptAuthenticationData) &&
	XdmcpReadARRAY8 (&buffer, &AcceptAuthorizationName) &&
	XdmcpReadARRAY8 (&buffer, &AcceptAuthorizationData))
    {
    	if (length == 12 + AcceptAuthenticationName.length +
		      	   AcceptAuthenticationData.length +
		      	   AcceptAuthorizationName.length +
 		      	   AcceptAuthorizationData.length)
    	{
	    if (!XdmcpCheckAuthentication (&AcceptAuthenticationName,
				      &AcceptAuthenticationData, ACCEPT))
	    {
		XdmcpFatal ("Authentication Failure", &AcceptAuthenticationName);
	    }
	    /* permit access control manipulations from this host */
	    AugmentSelf (&req_sockaddr, req_socklen);
	    /* if the authorization specified in the packet fails
	     * to be acceptable, enable the local addresses
	     */
	    if (!XdmcpAddAuthorization (&AcceptAuthorizationName,
					&AcceptAuthorizationData))
	    {
		AddLocalHosts ();
	    }
	    SessionID = AcceptSessionID;
    	    state = XDM_MANAGE;
    	    send_packet();
    	}
    }
    XdmcpDisposeARRAY8 (&AcceptAuthenticationName);
    XdmcpDisposeARRAY8 (&AcceptAuthenticationData);
    XdmcpDisposeARRAY8 (&AcceptAuthorizationName);
    XdmcpDisposeARRAY8 (&AcceptAuthorizationData);
}
Пример #4
0
static void
recv_refuse_msg(unsigned length)
{
    CARD32 RefusedSessionID;

    if (state != XDM_AWAIT_MANAGE_RESPONSE)
        return;
    if (length != 4)
        return;
    if (XdmcpReadCARD32(&buffer, &RefusedSessionID)) {
        if (RefusedSessionID == SessionID) {
            state = XDM_START_CONNECTION;
            send_packet();
        }
    }
}
Пример #5
0
static void
recv_failed_msg(unsigned length)
{
    CARD32 FailedSessionID;
    ARRAY8 status;

    if (state != XDM_AWAIT_MANAGE_RESPONSE)
        return;
    status.data = 0;
    if (XdmcpReadCARD32(&buffer, &FailedSessionID) &&
        XdmcpReadARRAY8(&buffer, &status)) {
        if (length == 6 + status.length && SessionID == FailedSessionID) {
            XdmcpFatal("Session failed", &status);
        }
    }
    XdmcpDisposeARRAY8(&status);
}
Пример #6
0
static void
recv_alive_msg(unsigned length)
{
    CARD8 SessionRunning;
    CARD32 AliveSessionID;

    if (state != XDM_AWAIT_ALIVE_RESPONSE)
        return;
    if (length != 5)
        return;
    if (XdmcpReadCARD8(&buffer, &SessionRunning) &&
        XdmcpReadCARD32(&buffer, &AliveSessionID)) {
        if (SessionRunning && AliveSessionID == SessionID) {
            state = XDM_RUN_SESSION;
            timeOutTime = GetTimeInMillis() + XDM_DEF_DORMANCY * 1000;
        }
        else {
            XdmcpDeadSession("Alive response indicates session dead");
        }
    }
}
Пример #7
0
int
XdmcpReadARRAY32 (XdmcpBufferPtr buffer, ARRAY32Ptr array)
{
    int	    i;

    /*
     * When returning FALSE, guarantee that array->data = 0.
     * This allows the user to safely call XdmcpDisposeARRAY32(array)
     * regardless of the return value below.
     * Note that XdmcpDisposeARRAY*(array) will call free(array->data),
     * so we must guarantee that array->data is NULL or a malloced pointer.
     */
    if (!XdmcpReadCARD8 (buffer, &array->length)) {
	array->data = NULL;
	return FALSE;
    }
    if (!array->length)
    {
	array->data = NULL;
	return TRUE;
    }
    array->data = (CARD32 *) malloc(array->length * sizeof (CARD32));
    if (!array->data)
	return FALSE;
    for (i = 0; i < (int)array->length; i++)
    {
	if (!XdmcpReadCARD32 (buffer, &array->data[i]))
	{
	    free(array->data);
	    array->data = NULL;
	    array->length = 0;
	    return FALSE;
	}
    }
    return TRUE;
}
Пример #8
0
static void manage(struct sockaddr *from, int fromlen, int length, int fd)
{
    CARD32 sessionID;
    CARD16 displayNumber;
    ARRAY8 displayClass;
    int expectlen;
    struct protoDisplay *pdpy;
    struct display *d;
    char *name = NULL;
    char *class2 = NULL;
    XdmcpNetaddr from_save;
    ARRAY8 clientAddress, clientPort;
    CARD16 connectionType;

    Debug("<manage> %d\n", length);
    displayClass.data = 0;
    displayClass.length = 0;
    if(XdmcpReadCARD32(&buffer, &sessionID) && XdmcpReadCARD16(&buffer, &displayNumber) && XdmcpReadARRAY8(&buffer, &displayClass))
    {
        expectlen = 4 +                      /* session ID */
                    2 +                      /* displayNumber */
                    2 + displayClass.length; /* displayClass */
        if(expectlen != length)
        {
            Debug("<manage> length error got %d expect %d\n", length, expectlen);
            goto abort;
        }
        pdpy = FindProtoDisplay((XdmcpNetaddr)from, fromlen, displayNumber);
        Debug("<manage> session ID %ld, pdpy %p\n", (long)sessionID, pdpy);
        if(!pdpy || pdpy->sessionID != sessionID)
        {
            /*
             * We may have already started a session for this display
             * but it hasn't seen the response in the form of an
             * XOpenDisplay() yet. So check if it is in the list of active
             * displays, and if so check that the session id's match.
             * If all this is true, then we have a duplicate request that
             * can be ignored.
             */
            if(!pdpy && (d = FindDisplayByAddress((XdmcpNetaddr)from, fromlen, displayNumber)) && d->sessionID == sessionID)
            {
                Debug("manage: got duplicate pkt, ignoring\n");
                goto abort;
            }
            Debug("session ID %ld refused\n", (long)sessionID);
            if(pdpy)
                Debug("existing session ID %ld\n", (long)pdpy->sessionID);
            send_refuse(from, fromlen, sessionID, fd);
        }
        else
        {
            name = NetworkAddressToName(pdpy->connectionType, &pdpy->connectionAddress, from, pdpy->displayNumber);
            if(!name)
            {
                Debug("could not compute display name\n");
                send_failed(from, fromlen, "(no name)", sessionID, "out of memory", fd);
                goto abort;
            }
            Debug("computed display name: %s\n", name);
            if((d = FindDisplayByName(name)))
            {
                Debug("terminating active session for %s\n", d->name);
                StopDisplay(d);
            }
            if(displayClass.length)
            {
                if(!StrNDup(&class2, (char *)displayClass.data, displayClass.length))
                {
                    send_failed(from, fromlen, name, sessionID, "out of memory", fd);
                    goto abort;
                }
            }
            if(!(from_save = (XdmcpNetaddr)Malloc(fromlen)))
            {
                send_failed(from, fromlen, name, sessionID, "out of memory", fd);
                goto abort;
            }
            memmove(from_save, from, fromlen);
            if(!(d = NewDisplay(name)))
            {
                free((char *)from_save);
                send_failed(from, fromlen, name, sessionID, "out of memory", fd);
                goto abort;
            }
            d->class2 = class2;
            class2 = 0;
            d->displayType = dForeign | dTransient | dFromXDMCP;
            d->sessionID = pdpy->sessionID;
            d->from.data = (unsigned char *)from_save;
            d->from.length = fromlen;
            d->displayNumber = pdpy->displayNumber;
            ClientAddress(from, &clientAddress, &clientPort, &connectionType);
            d->useChooser = 0;
            d->xdmcpFd = fd;
            if(IsIndirectClient(&clientAddress, connectionType))
            {
                Debug("IsIndirectClient\n");
                ForgetIndirectClient(&clientAddress, connectionType);
                if(UseChooser(&clientAddress, connectionType))
                {
                    d->useChooser = 1;
                    Debug("use chooser for %s\n", d->name);
                }
            }
            d->clientAddr = clientAddress;
            d->connectionType = connectionType;
            d->remoteHost = NetworkAddressToHostname(pdpy->connectionType, &pdpy->connectionAddress);

            XdmcpDisposeARRAY8(&clientPort);
            if(pdpy->fileAuthorization)
            {
                d->authorizations = (Xauth **)Malloc(sizeof(Xauth *));
                if(!d->authorizations)
                {
                    free((char *)from_save);
                    free((char *)d);
                    send_failed(from, fromlen, name, sessionID, "out of memory", fd);
                    goto abort;
                }
                d->authorizations[0] = pdpy->fileAuthorization;
                d->authNum = 1;
                pdpy->fileAuthorization = 0;
            }
            DisposeProtoDisplay(pdpy);
            Debug("starting display %s,%s\n", d->name, d->class2);
            if(LoadDisplayResources(d) < 0)
            {
                LogError(
                    "Unable to read configuration for display %s; "
                    "stopping it.\n",
                    d->name);
                StopDisplay(d);
            }
            else
                StartDisplay(d);
            CloseGetter();
        }
    }
abort:
    XdmcpDisposeARRAY8(&displayClass);
    if(name)
        free((char *)name);
    if(class2)
        free((char *)class2);
}