Пример #1
0
        public void StartServer()
        {
            Task.Run(async() =>
            {
                while (true)
                {
                    _cts.Token.ThrowIfCancellationRequested();

                    ObexPacket packet = await ObexPacket.ReadFromStream(_reader, new ObexConnectPacket());
                    if (packet.Opcode == Opcode.Connect)
                    {
                        if (packet.Headers.ContainsKey(HeaderId.Target))
                        {
                            BytesHeader targetHeader = (BytesHeader)packet.Headers[HeaderId.Target];
                            if (targetHeader.Value != null)
                            {
                                if (Enumerable.SequenceEqual(targetHeader.Value, _serviceUuid.Value))
                                {
                                    packet.Opcode = Opcode.Success;
                                    _writer.WriteBuffer(packet.ToBuffer());
                                    await _writer.StoreAsync();
                                    break;
                                }
                            }
                        }
                    }

                    Console.WriteLine("Not support operation code: " + packet.Opcode);
                    Console.WriteLine("MSE should send Connect request first");
                    packet = new ObexPacket(Opcode.OBEX_UNAVAILABLE);
                    _writer.WriteBuffer(packet.ToBuffer());
                }

                while (true)
                {
                    _cts.Token.ThrowIfCancellationRequested();

                    ObexPacket packet = await ObexPacket.ReadFromStream(_reader);

                    ObexPacket?response = OnClientRequest(packet);
                    if (response != null)
                    {
                        _writer.WriteBuffer(response.ToBuffer());
                        await _writer.StoreAsync();
                    }
                    else
                    {
                        _writer.WriteByte(0xC6); // Not Acceptable
                        _writer.WriteUInt16(3);
                        await _writer.StoreAsync();
                    }
                }
            }, _cts.Token);
        }
Пример #2
0
        /// <summary>
        /// Send OBEX Connect packet to the server.
        /// </summary>
        /// <param name="targetUuid">A 16-length byte array indicates the UUID of the target service.</param>
        /// <exception cref="InvalidOperationException">The Connect method can call only once and it is already called before.</exception>
        /// <exception cref="ObexRequestException">The request failed due to an underlying issue such as connection issue, or the server reply with a invalid response</exception>
        public async Task Connect(ObexServiceUuid targetService)
        {
            if (Conntected)
            {
                throw new InvalidOperationException("ObexClient is already connected to a ObexServer");
            }

            ObexConnectPacket packet = new ObexConnectPacket(targetService);
            var buf = packet.ToBuffer();

            Console.WriteLine("Sending OBEX Connection request to server:");
            Console.WriteLine(BitConverter.ToString(buf.ToArray()));
            Console.WriteLine("Opcode: " + packet.Opcode);

            _writer.WriteBuffer(buf);
            await _writer.StoreAsync();

            Console.WriteLine("Waiting reply packet...");
            ObexPacket response = await ObexPacket.ReadFromStream(_reader, packet);

            var bytes = response.ToBuffer().ToArray();

            Console.WriteLine("Reply packet:");
            Console.WriteLine(BitConverter.ToString(bytes));
            Console.WriteLine($"ResponseCode: {response.Opcode}");
            response.PrintHeaders();

            if (response.Opcode != Opcode.Success && response.Opcode != Opcode.SuccessAlt)
            {
                throw new ObexRequestException($"Unable to connect to the target OBEX service.", response.Opcode);
            }

            if (response.Headers.ContainsKey(HeaderId.ConnectionId))
            {
                _connectionIdHeader = (Int32ValueHeader)response.Headers[HeaderId.ConnectionId];
            }
            Conntected = true;
        }
Пример #3
0
        /// <summary>
        /// Send OBEX request to MSE
        /// </summary>
        /// <param name="req">The request packet</param>
        /// <returns>Response packet. The resposne packet is null if the MSE did not send back any response, or the response is corrupted</returns>
        /// <exception cref="ObexRequestException"> due to an underlying issue such as connection loss, invalid server response</exception>
        public async Task <ObexPacket> RunObexRequest(ObexPacket req)
        {
            if (!Conntected)
            {
                throw new InvalidOperationException("ObexClient is not connected to any ObexServer");
            }

            Opcode     requestOpcode = req.Opcode;
            ObexPacket?response      = null;
            int        c             = 0;

            do
            {
                Console.WriteLine($"Sending request packet: {++c}");
                if (_connectionIdHeader != null)
                {
                    req.Headers[HeaderId.ConnectionId] = _connectionIdHeader;
                }
                var buf = req.ToBuffer();
                Console.WriteLine(BitConverter.ToString(buf.ToArray()));
                Console.WriteLine("Opcode: " + req.Opcode);
                _writer.WriteBuffer(buf);
                await _writer.StoreAsync();

                ObexPacket subResponse;
                subResponse = await ObexPacket.ReadFromStream(_reader);

                var bytes = subResponse.ToBuffer().ToArray();
                Console.WriteLine("Reply packet:");
                Console.WriteLine(BitConverter.ToString(bytes));
                Console.WriteLine($"ResponseCode: {subResponse.Opcode}");

                subResponse.PrintHeaders();
                if (response == null)
                {
                    response = subResponse;
                }

                switch (subResponse.Opcode)
                {
                case Opcode.Success:
                case Opcode.SuccessAlt:
                    if (subResponse.Headers.ContainsKey(HeaderId.EndOfBody))
                    {
                        if (response.Headers.ContainsKey(HeaderId.Body))
                        {
                            ((BodyHeader)response.Headers[HeaderId.Body]).Value += ((BodyHeader)subResponse.Headers[HeaderId.EndOfBody]).Value;
                        }
                        else
                        {
                            response.Headers[HeaderId.Body] = response.Headers[HeaderId.EndOfBody];
                        }
                    }
                    return(response);

                case Opcode.Continue:
                case Opcode.ContinueAlt:
                    if (response != subResponse)
                    {
                        if (response.Headers.ContainsKey(HeaderId.Body))
                        {
                            ((BodyHeader)response.Headers[HeaderId.Body]).Value += ((BodyHeader)subResponse.Headers[HeaderId.Body]).Value;
                        }
                        else
                        {
                            if (subResponse.Headers.ContainsKey(HeaderId.Body))
                            {
                                response.Headers[HeaderId.Body] = subResponse.Headers[HeaderId.Body];
                            }
                        }
                    }
                    break;

                default:
                    throw new ObexRequestException($"The {requestOpcode} request failed with opcode {subResponse.Opcode}");
                }

                req = new ObexPacket(requestOpcode, _connectionIdHeader !);
            } while (true);

            Console.WriteLine("Maultiple GET over 10 times, abort!");
            return(response);
        }