public static IEnumerable <Pair <NetworkFileSystemEntry, string> > ReadEntries(Func <string> readNextLine)
        {
            string               currentFile     = null;
            NodeType             currentNodeType = null;
            AttributesEnumerable attributesEnumerable;
            ValueBox <string>    currentLine = new ValueBox <string>();

            Predicate <string> isAttributeLine = delegate(string s)
            {
                return(s[0] == ' ');
            };

            currentLine.Value = readNextLine();

            try
            {
                for (; ;)
                {
                    currentFile     = null;
                    currentNodeType = null;

                    if (currentLine.Value.StartsWith(ResponseCodes.RESPONSE_MARKER, StringComparison.CurrentCultureIgnoreCase))
                    {
                        if (currentLine.Value.EqualsIgnoreCase(ResponseCodes.READY))
                        {
                            break;
                        }
                        else if (currentLine.Value.StartsWith(ResponseCodes.ERROR, StringComparison.CurrentCultureIgnoreCase))
                        {
                            yield return(new Pair <NetworkFileSystemEntry, string>
                                         (
                                             new NetworkFileSystemEntry(),
                                             currentLine.Value
                                         ));

                            yield break;
                        }
                        else if (currentLine.Value.StartsWith(ResponseCodes.ENCODING))
                        {
                            string value = null, encoding = "url";

                            currentLine.Value = currentLine.Value.Substring(ResponseCodes.ENCODING.Length);

                            foreach (KeyValuePair <string, string> keyValuePair in CommandResponse.ParseTupleString(currentLine.Value))
                            {
                                if (keyValuePair.Key == "value")
                                {
                                    value = keyValuePair.Value;
                                }
                                else if (keyValuePair.Key == "encoding")
                                {
                                    encoding = keyValuePair.Key;
                                }
                                else if (keyValuePair.Key == "type")
                                {
                                    currentNodeType = GetNodeType(keyValuePair.Value);
                                }
                            }

                            if (value == null || currentNodeType == null)
                            {
                                AttributesEnumerable.ConsumeAttributes(readNextLine, currentLine, isAttributeLine);

                                continue;
                            }

                            try
                            {
                                currentFile = ProtocolTypes.DecodeString(value, encoding);
                            }
                            catch (NotSupportedException)
                            {
                                AttributesEnumerable.ConsumeAttributes(readNextLine, currentLine, isAttributeLine);

                                continue;
                            }
                        }
                        else
                        {
                            // Major error

                            throw new TextNetworkProtocolException();
                        }
                    }

                    if (currentLine.Value.Length == 0)
                    {
                        continue;
                    }

                    if (currentFile == null)
                    {
                        Pair <string, string> result;

                        result          = currentLine.Value.SplitAroundFirstCharFromLeft(':');
                        currentFile     = TextConversion.FromEscapedHexString(result.Right);
                        currentNodeType = GetNodeType(result.Left);
                    }

                    if (currentNodeType == null)
                    {
                        AttributesEnumerable.ConsumeAttributes(readNextLine, currentLine, isAttributeLine);

                        continue;
                    }

                    attributesEnumerable = new AttributesEnumerable
                                           (
                        readNextLine,
                        isAttributeLine,
                        currentLine
                                           );

                    try
                    {
                        yield return(new Pair <NetworkFileSystemEntry, string>
                                     (
                                         new NetworkFileSystemEntry(currentFile, currentNodeType, attributesEnumerable),
                                         null
                                     ));
                    }
                    finally
                    {
                        attributesEnumerable.Finish();
                    }
                }
            }
            finally
            {
                while (!currentLine.Value.StartsWith(ResponseCodes.READY))
                {
                    currentLine.Value = readNextLine();
                }
            }
        }