/// <summary>
        /// Parses the given command line and returns the arguments form is.
        /// The command line is expected to be without the command name.
        /// </summary>
        public static SimpleList <Pair <string, string> > GetArgumentsFromCommandLine(string commandLineWithoutCommand)
        {
            commandLineWithoutCommand = commandLineWithoutCommand.Trim();

            var result = SList.Create <Pair <string, string> >(3);

            var builder = new StringBuilder(commandLineWithoutCommand.Length);

            var argName  = string.Empty;
            var argValue = string.Empty;

            const int lookForArgState   = 0;
            const int readArgNameState  = 1;
            const int readArgValueState = 2;

            int currentState = lookForArgState;

            // If it don't start with the argument prefix, it means that the parameter has no name, just value
            if (!commandLineWithoutCommand.StartsWith(ArgumentPrefix.ToString()))
            {
                currentState = readArgValueState;
            }

            var onQuote           = false;
            var ignoreNextSpecial = false;

            for (int i = 0; i < commandLineWithoutCommand.Length; i++)
            {
                var letter = commandLineWithoutCommand[i];

                // Specials
                var isEmpty     = letter == ' ' && !ignoreNextSpecial;
                var isQuote     = letter == '"' && !ignoreNextSpecial;
                var isBackSlash = letter == '\\' && !ignoreNextSpecial;
                var isArgPrefix = letter == ArgumentPrefix && !ignoreNextSpecial;

                ignoreNextSpecial = false;

                if (isQuote)
                {
                    onQuote = !onQuote;
                    continue;
                }
                else if (isBackSlash)
                {
                    ignoreNextSpecial = true;
                    continue;
                }

                if (onQuote)
                {
                    ignoreNextSpecial = true;
                }

                switch (currentState)
                {
                case lookForArgState:
                    if (isArgPrefix)
                    {
                        currentState = readArgNameState;
                    }
                    break;

                case readArgNameState:
                    // if there's a space after the start of a arg, ignore the space
                    if (isEmpty && builder.Length == 0)
                    {
                        continue;
                    }

                    if (isEmpty)
                    {
                        argName = builder.ToString();
                        TextUtil.ClearBuilder(builder);
                        currentState = readArgValueState;

                        argValue = string.Empty;
                    }
                    else
                    {
                        builder.Append(letter);
                    }
                    break;

                case readArgValueState:
                    if (isArgPrefix)
                    {
                        argValue = builder.ToString();
                        TextUtil.ClearBuilder(builder);

                        var pair = CreateArgPair(argName, argValue);
                        SList.Add(result, pair);

                        argName  = string.Empty;
                        argValue = string.Empty;

                        currentState = readArgNameState;
                    }
                    else
                    {
                        builder.Append(letter);
                    }
                    break;
                }
            }

            // Process what might have been left on the command line
            switch (currentState)
            {
            case lookForArgState:
                argName  = string.Empty;
                argValue = string.Empty;
                break;

            case readArgNameState:
                argName = builder.ToString();
                break;

            case readArgValueState:
                argValue = builder.ToString();
                break;
            }

            // We can arguments with empty names but values or with empty values but names
            if (!(string.IsNullOrEmpty(argName) && string.IsNullOrEmpty(argValue)))
            {
                var finalPair = CreateArgPair(argName, argValue);
                SList.Add(result, finalPair);
            }

            return(result);
        }
Beispiel #2
0
        /// <summary>
        /// Returns the directory at the given path. Returns null if did not found a dir.
        /// </summary>
        public static HashDir FindDirByPath(string path)
        {
            if (PathUtil.GetPathType(path) != PathType.Folder)
            {
                return(null);
            }

            var     data = DataHolder.DeviceData.CurrentDevice.FileSystem;
            HashDir currentDir;

            // If a path starts with the separator, it means it starts on the root folder
            if (path.StartsWith(PathUtil.PathSeparator))
            {
                currentDir = data.RootDir;

                // remove the path separator because we are already on the root folder
                path = path.Remove(0, 1);
            }
            else
            {
                currentDir = data.CurrentDir;
            }

            var builder = new StringBuilder(path.Length);

            for (int i = 0; i < path.Length; i++)
            {
                var current = path[i];
                if (current == PathUtil.PathSeparator[0])
                {
                    currentDir = ProcessPathPart(currentDir, builder.ToString());
                    TextUtil.ClearBuilder(builder);
                    // if currentDir is null, it's a invalid path
                    if (currentDir == null)
                    {
                        return(null);
                    }
                }
                else
                {
                    builder.Append(current);
                }
            }

            // If there's still something to process
            // this can happen if the path did NOT ended in a path separator
            if (builder.Length > 0)
            {
                currentDir = ProcessPathPart(currentDir, builder.ToString());
                TextUtil.ClearBuilder(builder);
            }

            if (currentDir != null)
            {
                if (!IsDirAvaibale(currentDir))
                {
                    return(null);
                }
            }

            return(currentDir);
        }