private void Validate(SqProgram program, SqRequirements capabilities, List <string> messages)
        {
            //bool hasTimer = (capabilities & SqRequirements.Timer) == SqRequirements.Timer;
            bool hasCM = (capabilities & SqRequirements.ControlModule) == SqRequirements.ControlModule;

            var repeatPos = program.Commands.FindIndex(x => x.Cmd == "repeat");

            if (repeatPos != -1 && repeatPos != program.Commands.Count - 1)
            {
                Log.WriteFormat(Parser.LOG_CAT, LogLevel.Warning, "Unreachable code found in @{0}: all commands after /repeat will never executed", program.Name);
            }

            if (repeatPos != -1 && !program.Commands.Take(repeatPos).Any(x => Commands.CmdDefs[x.Cmd].IsWait))
            {
                Log.WriteFormat(Parser.LOG_CAT, LogLevel.Warning, "Where is no any wait command before /repeat in @{0}. Script will wait 1 tock to prevent \"Script Too Complex\" exception", program.Name);
            }

            /*
             * SqCommand cmd = null;
             * if (!hasTimer && (cmd = program.Commands.FirstOrDefault(x => (Commands.CmdDefs[x.Cmd].Requirements & SqRequirements.Timer) != 0)) != null)
             * {
             *  Log.WriteFormat(Parser.LOG_CAT, LogLevel.Warning, "@{0} contains /{1} command, but where is no timer to execute it", program.Name, cmd.Cmd);
             * }*/

            SqCommand cmd = null;

            if (!hasCM && (cmd = program.Commands.FirstOrDefault(x => (Commands.CmdDefs[x.Cmd].Requirements & SqRequirements.ControlModule) != 0)) != null)
            {
                Log.WriteFormat(Parser.LOG_CAT, LogLevel.Warning, "@{0} contains /{1} command, but Control Module mod is not loaded", program.Name, cmd.Cmd);
            }

            // if (!hasCM && program.Commands)
        }
Beispiel #2
0
        public static bool TryCreateCommand(string name, List <string> args, out SqCommand command, out string errorMessage) // todo: cleanup
        {
            command      = null;
            errorMessage = null;
            string cmd = name.ToLower();

            if (!Commands.CmdDefs.ContainsKey(cmd) || Commands.CmdDefs[cmd].Hidden)
            {
                errorMessage = string.Format(ErrorMessages.UnknownCommand, name);
                return(false);
            }

            var def = Commands.CmdDefs[cmd];

            if ((args.Count > def.Arguments.Length) && !def.Aggregative)
            {
                errorMessage = string.Format(ErrorMessages.TooManyArgumentsIn, name,
                                             def.OptionalCount == 0 ?
                                             def.Arguments.Length.ToString() :
                                             string.Format("from {0} to {1}", def.Arguments.Length - def.OptionalCount, def.Arguments.Length),
                                             args.Count
                                             );
                return(false);
            }

            if (args.Count < def.Arguments.Length - def.OptionalCount)
            {
                string countText;
                if (def.Aggregative)
                {
                    countText = string.Format("at least {0}", def.Arguments.Length - def.OptionalCount - 1);
                }
                else if (def.OptionalCount == 0)
                {
                    countText = string.Format("{0}", def.Arguments.Length);
                }
                else
                {
                    countText = string.Format("from {0} to {1}", def.Arguments.Length - def.OptionalCount, def.Arguments.Length);
                }

                errorMessage = string.Format(ErrorMessages.TooFewArgumentsIn, name,
                                             countText,
                                             args.Count
                                             );
                return(false);
            }

            command = def.Materialize(new List <object>());

            int allowedOptional = args.Count - def.Arguments.Length + def.OptionalCount + (def.Aggregative ? 1 : 0);

            int argIndex = 0;

            for (int i = 0, imax = def.Arguments.Length; i < imax; i++)
            {
                var argDef = def.Arguments[i];

                if (argDef.Aggregative)
                {
                    if (i != imax - 1)
                    {
                        throw new Exception("invalid method definition");
                    }

                    IList argList = new List <object>();
                    while (argIndex < args.Count)
                    {
                        object value;
                        if (TryParseArgument(args[argIndex], argDef.Type, out value))
                        {
                            argList.Add(value);
                        }
                        else
                        {
                            errorMessage = string.Format(ErrorMessages.InvalidTypeValue, args[argIndex], argDef.Type);
                            return(false);
                        }

                        argIndex++;
                    }

                    command.Args.Add(argList);
                }
                else
                {
                    if (!argDef.Optional || allowedOptional > 0)
                    {
                        object value;
                        if (TryParseArgument(args[argIndex], argDef.Type, out value))
                        {
                            command.Args.Add(value);
                        }
                        else
                        {
                            errorMessage = string.Format(ErrorMessages.InvalidTypeValue, args[argIndex], argDef.Type);
                            return(false);
                        }
                        argIndex++;

                        if (argDef.Optional)
                        {
                            allowedOptional--;
                        }
                    }
                    else
                    {
                        command.Args.Add(argDef.Default);
                    }
                }
            }

            return(true);
        }