internal override bool DecodeArgument(byte b)
        {
            switch (_receivedStep)
            {
            case Steps.Status:     // receive status
                _lastValue = new SharerReadVariableReturn();
                Values.Add(_lastValue);

                _lastValue.Status = (SharerReadVariableStatus)b;

                // if the we have a value, go to next step to decode, else stay to have next variable
                if (_lastValue.Status == SharerReadVariableStatus.OK)
                {
                    _lastValueType = _types[Values.Count - 1];
                    _lastValueSize = SharerTypeHelper.Sizeof(_lastValueType);
                    _lastValueBytes.Clear();
                    _receivedStep = Steps.Value;
                }
                else if (Values.Count >= _types.Length)
                {
                    _receivedStep = Steps.End;
                }

                break;

            case Steps.Value:
                _lastValueBytes.Add(b);     // add received byte

                // if enought returned byte, decode it
                if (_lastValueBytes.Count >= _lastValueSize)
                {
                    _lastValue.Value = SharerTypeHelper.Decode(_lastValueType, _lastValueBytes.ToArray());

                    if (Values.Count >= _types.Length)
                    {
                        _receivedStep = Steps.End;
                    }
                    else
                    {
                        _receivedStep = Steps.Status;
                    }
                }
                break;
            }

            return(_receivedStep == Steps.End);
        }
Exemple #2
0
        public SharerWriteVariablesCommand(List <SharerWriteValue> values)
        {
            _values = values;

            using (MemoryStream memory = new MemoryStream())
            {
                using (BinaryWriter writer = new BinaryWriter(memory))
                {
                    writer.Write((short)values.Count);

                    foreach (var value in values)
                    {
                        writer.Write((short)value.Index);

                        SharerTypeHelper.Encode(value.Type, writer, value.Value);
                    }
                    _buffer = memory.ToArray();
                }
            }
        }
        internal override bool DecodeArgument(byte b)
        {
            switch (_receivedStep)
            {
            case Steps.Status:     // receive status
                Return.Status = (SharerCallFunctionStatus)b;

                // if the function has a returned value
                if (Return.Status == SharerCallFunctionStatus.OK && _returnType != SharerType.@void)
                {
                    _returnBytes.Clear();
                    _returnSize   = SharerTypeHelper.Sizeof(_returnType);
                    _receivedStep = Steps.ReturnValue;
                }
                else
                {
                    _receivedStep = Steps.End;
                }

                break;

            case Steps.ReturnValue:
                _returnBytes.Add(b);     // add received byte

                // if enought returned byte, decode it and end
                if (_returnBytes.Count >= _returnSize)
                {
                    Return.Value = (ReturnType)SharerTypeHelper.Decode(_returnType, _returnBytes.ToArray());

                    _receivedStep = Steps.End;
                }
                break;
            }

            return(_receivedStep == Steps.End);
        }
        /// <summary>
        /// Remote call a function by its name with arguments and get the returned value
        /// </summary>
        /// <typeparam name="ReturnType">The .NET type expected. Should be the same as the Arduino function return type</typeparam>
        /// <param name="functionName">Name of the function to call</param>
        /// <param name="timeout">Maximum expected duration of the function execution on Arduino</param>
        /// <param name="arguments">Optional list of argument values.</param>
        /// <returns>Status of the function call with its returned value</returns>
        public SharerFunctionReturn <ReturnType> Call <ReturnType>(string functionName, TimeSpan timeout, params object[] arguments)
        {
            AssertConnected();

            if (functionName == null)
            {
                throw new ArgumentNullException("functionName");
            }

            Int16          functionId = -1;
            SharerFunction function   = null;

            for (int i = 0; i < Functions.Count; i++)
            {
                if (Functions[i].Name == functionName)
                {
                    function   = Functions[i];
                    functionId = (Int16)i;
                    break;
                }
            }

            if (function == null || functionId < 0)
            {
                throw new Exception(functionName + " not found in function list. Try to update the function List or check if this function has been shared.");
            }

            if (arguments == null || arguments.Length == 0)
            {
                if (function.Arguments.Count != 0)
                {
                    throw new Exception("Attempt to call the function " + function.Name + " with no arguments, but the function has " + function.Arguments.Count + " arguments");
                }
            }
            else if (function.Arguments.Count != arguments.Length)
            {
                throw new Exception("Attempt to call the function " + function.Name + " with " + arguments.Length + " argument(s), but the function has " + function.Arguments.Count + " argument(s)");
            }

            byte[] buffer;

            using (MemoryStream memory = new MemoryStream())
            {
                using (BinaryWriter writer = new BinaryWriter(memory))
                {
                    writer.Write(functionId);

                    if (arguments != null)
                    {
                        for (int i = 0; i < arguments.Length; i++)
                        {
                            if (arguments[i] == null)
                            {
                                throw new ArgumentNullException("arguments[" + i + "]");
                            }

                            try
                            {
                                SharerTypeHelper.Encode(function.Arguments[i].Type, writer, arguments[i]);
                            }
                            catch (Exception ex)
                            {
                                throw new Exception("Error in argument " + function.Arguments[i].Name + " of function " + function.Name, ex);
                            }
                        }
                    }


                    buffer = memory.ToArray();
                }
            }

            var cmd = new SharerCallFunctionCommand <ReturnType>(buffer, function.ReturnType);

            sendCommand(cmd);

            bool success = cmd.WaitAnswer(timeout);

            if (!success)
            {
                throw new Exception("Error while calling function " + functionName, cmd.Exception);
            }

            return(cmd.Return);
        }