示例#1
0
        /**
         * <summary>Loads the font data.</summary>
         */
        private void Load(
            )
        {
            try
            {
                ParseHeader();
                Index nameIndex    = Index.Parse(fontData);
                Index topDictIndex = Index.Parse(fontData);
                stringIndex = Index.Parse(fontData);
        #pragma warning disable 0219
                Index globalSubrIndex = Index.Parse(fontData);

                string fontName = ToString(nameIndex[0]);
        #pragma warning restore 0219
                Dict topDict = Dict.Parse(topDictIndex[0]);

                //      int encodingOffset = topDict.get(Dict.OperatorEnum.Encoding, 0, 0).intValue();
                //TODO: encoding

                int charsetOffset           = (int)topDict.Get(Dict.OperatorEnum.Charset, 0, 0);
                StandardCharsetEnum?charset = GetStandardCharset(charsetOffset);
                if (charset.HasValue)
                {
                    glyphIndexes = new Dictionary <int, int>(StandardCharsets[charset.Value]);
                }
                else
                {
                    glyphIndexes = new Dictionary <int, int>();

                    int   charStringsOffset = (int)topDict.Get(Dict.OperatorEnum.CharStrings, 0);
                    Index charStringsIndex  = Index.Parse(fontData, charStringsOffset);

                    fontData.Seek(charsetOffset);
                    int charsetFormat = fontData.ReadByte();
                    for (int index = 1, count = charStringsIndex.Count; index <= count;)
                    {
                        switch (charsetFormat)
                        {
                        case 0:
                            glyphIndexes[index++] = ToUnicode(fontData.ReadUnsignedShort());
                            break;

                        case 1:
                        case 2:
                        {
                            int first = fontData.ReadUnsignedShort();
                            int nLeft = (charsetFormat == 1 ? fontData.ReadByte() : fontData.ReadUnsignedShort());
                            for (int rangeItemIndex = first, rangeItemEndIndex = first + nLeft; rangeItemIndex <= rangeItemEndIndex; rangeItemIndex++)
                            {
                                glyphIndexes[index++] = ToUnicode(rangeItemIndex);
                            }
                        }
                        break;
                        }
                    }
                }
            }
            catch (Exception e)
            { throw e; }
        }
示例#2
0
 private void WriteFromTo(IInputStream from, IOutputStream to)
 {
     while (!from.IsEof)
     {
         to.WriteByte(( byte )from.ReadByte());
     }
 }
        public int ReadByte()
        {
            if (_byteslength != 0)
            {
                _byteslength--;
                return(_currentValue);
            }

            if (IsEof)
            {
                return(-1);
            }

            _currentValue = ( byte )_inputStream.ReadByte();
            if (_currentValue != RleMarker)
            {
                return(_currentValue);
            }

            if (IsEof)
            {
                throw new ApplicationException($"After rleMarker={RleMarker} can be one or more bytes");
            }

            _currentValue = ( byte )_inputStream.ReadByte();
            if (_currentValue == RleMarker)
            {
                return(RleMarker);
            }

            _byteslength = _currentValue + 4;
            if (IsEof)
            {
                throw new ApplicationException($"After length={RleMarker} marker can be one or more bytes");
            }

            _currentValue = ( byte )_inputStream.ReadByte();
            _byteslength--;

            return(_currentValue);
        }
示例#4
0
 public static Index Parse(IInputStream stream)
 {
     byte[][] data = new byte[stream.ReadUnsignedShort()][];
     {
         int[] offsets = new int[data.Length + 1];
         int   offSize = stream.ReadByte();
         for (int index = 0, count = offsets.Length; index < count; index++)
         {
             offsets[index] = stream.ReadInt(offSize);
         }
         for (int index = 0, count = data.Length; index < count; index++)
         {
             stream.Read(data[index] = new byte[offsets[index + 1] - offsets[index]]);
         }
     }
     return(new Index(data));
 }
        /**
         * <summary>Moves the pointer to the next token.</summary>
         * <remarks>To properly parse the current token, the pointer MUST be just before its starting
         * (leading whitespaces are ignored). When this method terminates, the pointer IS
         * at the last byte of the current token.</remarks>
         * <returns>Whether a new token was found.</returns>
         */
        public virtual bool MoveNext(
            )
        {
            StringBuilder buffer = null;

            token = null;
            int c = 0;

            // Skip leading white-space characters.
            do
            {
                c = stream.ReadByte();
                if (c == -1)
                {
                    return(false);
                }
            } while(IsWhitespace(c)); // Keep goin' till there's a white-space character...

            // Which character is it?
            switch (c)
            {
            case Symbol.Slash: // Name.
            {
                tokenType = TokenTypeEnum.Name;

                /*
                 * NOTE: As name objects are simple symbols uniquely defined by sequences of characters,
                 * the bytes making up the name are never treated as text, so here they are just
                 * passed through without unescaping.
                 */
                buffer = new StringBuilder();
                while (true)
                {
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        break; // NOOP.
                    }
                    if (IsDelimiter(c) || IsWhitespace(c))
                    {
                        break;
                    }

                    buffer.Append((char)c);
                }
                if (c > -1)
                {
                    stream.Skip(-1);
                }            // Restores the first byte after the current token.
            } break;

            case '0':
            case '1':
            case '2':
            case '3':
            case '4':
            case '5':
            case '6':
            case '7':
            case '8':
            case '9':
            case '.':
            case '-':
            case '+': // Number.
            {
                if (c == '.')
                {
                    tokenType = TokenTypeEnum.Real;
                }
                else // Digit or signum.
                {
                    tokenType = TokenTypeEnum.Integer;
                }                              // By default (it may be real).

                // Building the number...
                buffer = new StringBuilder();
                while (true)
                {
                    buffer.Append((char)c);
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        break; // NOOP.
                    }
                    else if (c == '.')
                    {
                        tokenType = TokenTypeEnum.Real;
                    }
                    else if (c < '0' || c > '9')
                    {
                        break;
                    }
                }
                if (c > -1)
                {
                    stream.Skip(-1);
                }            // Restores the first byte after the current token.
            } break;

            case Symbol.OpenSquareBracket: // Array (begin).
                tokenType = TokenTypeEnum.ArrayBegin;
                break;

            case Symbol.CloseSquareBracket: // Array (end).
                tokenType = TokenTypeEnum.ArrayEnd;
                break;

            case Symbol.OpenAngleBracket: // Dictionary (begin) | Hexadecimal string.
            {
                c = stream.ReadByte();
                if (c == -1)
                {
                    throw new ParseException("Unexpected EOF (isolated opening angle-bracket character).");
                }
                // Is it a dictionary (2nd angle bracket)?
                if (c == Symbol.OpenAngleBracket)
                {
                    tokenType = TokenTypeEnum.DictionaryBegin;
                    break;
                }

                // Hexadecimal string (single angle bracket).
                tokenType = TokenTypeEnum.Hex;

                buffer = new StringBuilder();
                while (c != Symbol.CloseAngleBracket) // NOT string end.
                {
                    if (!IsWhitespace(c))
                    {
                        buffer.Append((char)c);
                    }

                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        throw new ParseException("Unexpected EOF (malformed hex string).");
                    }
                }
            } break;

            case Symbol.CloseAngleBracket: // Dictionary (end).
            {
                c = stream.ReadByte();
                if (c != Symbol.CloseAngleBracket)
                {
                    throw new ParseException("Malformed dictionary.", stream.Position);
                }

                tokenType = TokenTypeEnum.DictionaryEnd;
            } break;

            case Symbol.OpenRoundBracket: // Literal string.
            {
                tokenType = TokenTypeEnum.Literal;

                buffer = new StringBuilder();
                int level = 0;
                while (true)
                {
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        break;
                    }
                    else if (c == Symbol.OpenRoundBracket)
                    {
                        level++;
                    }
                    else if (c == Symbol.CloseRoundBracket)
                    {
                        level--;
                    }
                    else if (c == '\\')
                    {
                        bool lineBreak = false;
                        c = stream.ReadByte();
                        switch (c)
                        {
                        case 'n':
                            c = Symbol.LineFeed;
                            break;

                        case 'r':
                            c = Symbol.CarriageReturn;
                            break;

                        case 't':
                            c = '\t';
                            break;

                        case 'b':
                            c = '\b';
                            break;

                        case 'f':
                            c = '\f';
                            break;

                        case Symbol.OpenRoundBracket:
                        case Symbol.CloseRoundBracket:
                        case '\\':
                            break;

                        case Symbol.CarriageReturn:
                            lineBreak = true;
                            c         = stream.ReadByte();
                            if (c != Symbol.LineFeed)
                            {
                                stream.Skip(-1);
                            }
                            break;

                        case Symbol.LineFeed:
                            lineBreak = true;
                            break;

                        default:
                        {
                            // Is it outside the octal encoding?
                            if (c < '0' || c > '7')
                            {
                                break;
                            }

                            // Octal.
                            int octal = c - '0';
                            c = stream.ReadByte();
                            // Octal end?
                            if (c < '0' || c > '7')
                            {
                                c = octal; stream.Skip(-1); break;
                            }
                            octal = (octal << 3) + c - '0';
                            c     = stream.ReadByte();
                            // Octal end?
                            if (c < '0' || c > '7')
                            {
                                c = octal; stream.Skip(-1); break;
                            }
                            octal = (octal << 3) + c - '0';
                            c     = octal & 0xff;
                            break;
                        }
                        }
                        if (lineBreak)
                        {
                            continue;
                        }
                        if (c == -1)
                        {
                            break;
                        }
                    }
                    else if (c == Symbol.CarriageReturn)
                    {
                        c = stream.ReadByte();
                        if (c == -1)
                        {
                            break;
                        }
                        else if (c != Symbol.LineFeed)
                        {
                            c = Symbol.LineFeed; stream.Skip(-1);
                        }
                    }
                    if (level == -1)
                    {
                        break;
                    }

                    buffer.Append((char)c);
                }
                if (c == -1)
                {
                    throw new ParseException("Malformed literal string.");
                }
            } break;

            case Symbol.Percent: // Comment.
            {
                tokenType = TokenTypeEnum.Comment;

                buffer = new StringBuilder();
                while (true)
                {
                    c = stream.ReadByte();
                    if (c == -1 ||
                        IsEOL(c))
                    {
                        break;
                    }

                    buffer.Append((char)c);
                }
            } break;

            default: // Keyword.
            {
                tokenType = TokenTypeEnum.Keyword;

                buffer = new StringBuilder();
                do
                {
                    buffer.Append((char)c);
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        break;
                    }
                } while(!IsDelimiter(c) && !IsWhitespace(c));
                if (c > -1)
                {
                    stream.Skip(-1);
                }            // Restores the first byte after the current token.
            } break;
            }

            if (buffer != null)
            {
                switch (tokenType)
                {
                case TokenTypeEnum.Keyword:
                {
                    token = buffer.ToString();
                    switch ((string)token)
                    {
                    case Keyword.False:
                    case Keyword.True: // Boolean.
                        tokenType = TokenTypeEnum.Boolean;
                        token     = bool.Parse((string)token);
                        break;

                    case Keyword.Null: // Null.
                        tokenType = TokenTypeEnum.Null;
                        token     = null;
                        break;
                    }
                } break;

                case TokenTypeEnum.Name:
                case TokenTypeEnum.Literal:
                case TokenTypeEnum.Hex:
                case TokenTypeEnum.Comment:
                    token = buffer.ToString();
                    break;

                case TokenTypeEnum.Integer:
                    token = Int32.Parse(
                        buffer.ToString(),
                        NumberStyles.Integer,
                        StandardNumberFormatInfo
                        );
                    break;

                case TokenTypeEnum.Real:
                    token = Double.Parse(
                        buffer.ToString(),
                        NumberStyles.Float,
                        StandardNumberFormatInfo
                        );
                    break;
                }
            }
            return(true);
        }
示例#6
0
            public static Dict Parse(
                IInputStream stream
                )
            {
                IDictionary <int, IList <object> > entries = new Dictionary <int, IList <object> >();
                IList <object> operands = null;

                while (true)
                {
                    int b0 = stream.ReadByte();
                    if (b0 == -1)
                    {
                        break;
                    }

                    if (b0 >= 0 && b0 <= 21) // Operator.
                    {
                        int @operator = b0;
                        if (b0 == 12) // 2-byte operator.
                        {
                            @operator = @operator << 8 + stream.ReadByte();
                        }

                        /*
                         * NOTE: In order to resiliently support unknown operators on parsing, parsed operators
                         * are not directly mapped to OperatorEnum.
                         */
                        entries[@operator] = operands;
                        operands           = null;
                    }
                    else // Operand.
                    {
                        if (operands == null)
                        {
                            operands = new List <object>();
                        }

                        if (b0 == 28) // 3-byte integer.
                        {
                            operands.Add(stream.ReadByte() << 8 + stream.ReadByte());
                        }
                        else if (b0 == 29) // 5-byte integer.
                        {
                            operands.Add(stream.ReadByte() << 24 + stream.ReadByte() << 16 + stream.ReadByte() << 8 + stream.ReadByte());
                        }
                        else if (b0 == 30) // Variable-length real.
                        {
                            StringBuilder operandBuilder = new StringBuilder();
                            bool          ended          = false;
                            do
                            {
                                int   b       = stream.ReadByte();
                                int[] nibbles = { (b >> 4) & 0xf, b & 0xf };
                                foreach (int nibble in nibbles)
                                {
                                    switch (nibble)
                                    {
                                    case 0x0:
                                    case 0x1:
                                    case 0x2:
                                    case 0x3:
                                    case 0x4:
                                    case 0x5:
                                    case 0x6:
                                    case 0x7:
                                    case 0x8:
                                    case 0x9:
                                        operandBuilder.Append(nibble);
                                        break;

                                    case 0xa: // Decimal point.
                                        operandBuilder.Append(".");
                                        break;

                                    case 0xb: // Positive exponent.
                                        operandBuilder.Append("E");
                                        break;

                                    case 0xc: // Negative exponent.
                                        operandBuilder.Append("E-");
                                        break;

                                    case 0xd: // Reserved.
                                        break;

                                    case 0xe: // Minus.
                                        operandBuilder.Append("-");
                                        break;

                                    case 0xf: // End of number.
                                        ended = true;
                                        break;
                                    }
                                }
                            } while(!ended);
                            operands.Add(ConvertUtils.ParseDoubleInvariant(operandBuilder.ToString()));
                        }
                        else if (b0 >= 32 && b0 <= 246) // 1-byte integer.
                        {
                            operands.Add(b0 - 139);
                        }
                        else if (b0 >= 247 && b0 <= 250) // 2-byte positive integer.
                        {
                            operands.Add((b0 - 247) << 8 + stream.ReadByte() + 108);
                        }
                        else if (b0 >= 251 && b0 <= 254) // 2-byte negative integer.
                        {
                            operands.Add(-(b0 - 251) << 8 - stream.ReadByte() - 108);
                        }
                        else // Reserved.
                        { /* NOOP */
                        }
                    }
                }
                return(new Dict(entries));
            }
示例#7
0
            public object UnpackNull()
            {
                byte markerByte = _in.ReadByte();

                if (markerByte != NULL)
                {
                    throw new ArgumentOutOfRangeException(nameof(markerByte), markerByte,
                                                          $"Expected a null, but got: 0x{(markerByte & 0xFF).ToString("X2")}");
                }
                return(null);
            }
示例#8
0
        public int ReadByte()
        {
            int value = _inputStream.ReadByte();

            return(value != -1 ? _decodingShuffledBytes[value] : -1);
        }
示例#9
0
        /**
         * <summary>Parses the next token [PDF:1.6:3.1].</summary>
         * <remarks>To properly parse the current token, the pointer MUST be just before its starting
         * (leading whitespaces are ignored). When this method terminates, the pointer IS
         * at the last byte of the current token.</remarks>
         * <returns>Whether a new token was found.</returns>
         */
        public bool MoveNext(
            )
        {
            /*
             * NOTE: It'd be interesting to evaluate an alternative regular-expression-based
             * implementation...
             */
            StringBuilder buffer = null;

            token = null;
            int c = 0;

            // Skip white-space characters [PDF:1.6:3.1.1].
            do
            {
                c = stream.ReadByte();
                if (c == -1)
                {
                    return(false);
                }
            } while(IsWhitespace(c)); // Keep goin' till there's a white-space character...

            // Which character is it?
            switch (c)
            {
            case Symbol.Slash: // Name.
                tokenType = TokenTypeEnum.Name;

                buffer = new StringBuilder();
                while (true)
                {
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        throw new FileFormatException("Unexpected EOF (malformed name object).", stream.Position);
                    }
                    if (IsDelimiter(c) || IsWhitespace(c))
                    {
                        break;
                    }

                    buffer.Append((char)c);
                }
                stream.Skip(-1); // Recover the first byte after the current token.
                break;

            case '0':
            case '1':
            case '2':
            case '3':
            case '4':
            case '5':
            case '6':
            case '7':
            case '8':
            case '9':
            case '.':
            case '-':
            case '+': // Number [PDF:1.6:3.2.2] | Indirect reference.
                switch (c)
                {
                case '.': // Decimal point.
                    tokenType = TokenTypeEnum.Real;
                    break;

                case '-':
                case '+':                              // Signum.
                    tokenType = TokenTypeEnum.Integer; // By default (it may be real).
                    break;

                default:                                   // Digit.
                    if (multipleTokenParsing)              // Plain number (multiple token parsing -- see indirect reference search).
                    {
                        tokenType = TokenTypeEnum.Integer; // By default (it may be real).
                    }
                    else // Maybe an indirect reference (postfix notation [PDF:1.6:3.2.9]).
                    {
                        /*
                         * NOTE: We need to identify this pattern:
                         * ref :=  { int int 'R' }
                         */
                        // Enable multiple token parsing!
                        // NOTE: This state MUST be disabled before returning.
                        multipleTokenParsing = true;

                        // 1. Object number.
                        // Try the possible object number!
                        stream.Skip(-1); MoveNext();
                        // Isn't it a valid object number?
                        if (tokenType != TokenTypeEnum.Integer)
                        {
                            // Disable multiple token parsing!
                            multipleTokenParsing = false;
                            return(true);
                        }
                        // Assign object number!
                        int objectNumber = (int)token;
                        // Backup the recovery position!
                        long oldOffset = stream.Position;

                        // 2. Generation number.
                        // Try the possible generation number!
                        MoveNext();
                        // Isn't it a valid generation number?
                        if (tokenType != TokenTypeEnum.Integer)
                        {
                            // Rollback!
                            stream.Seek(oldOffset);
                            token = objectNumber; tokenType = TokenTypeEnum.Integer;
                            // Disable multiple token parsing!
                            multipleTokenParsing = false;
                            return(true);
                        }
                        // Assign generation number!
                        int generationNumber = (int)token;

                        // 3. Reference keyword.
                        // Try the possible reference keyword!
                        MoveNext();
                        // Isn't it a valid reference keyword?
                        if (tokenType != TokenTypeEnum.Reference)
                        {
                            // Rollback!
                            stream.Seek(oldOffset);
                            token = objectNumber; tokenType = TokenTypeEnum.Integer;
                            // Disable multiple token parsing!
                            multipleTokenParsing = false;
                            return(true);
                        }
                        token = new Reference(objectNumber, generationNumber);
                        // Disable multiple token parsing!
                        multipleTokenParsing = false;
                        return(true);
                    }
                    break;
                }

                // Building the number...
                buffer = new StringBuilder();
                do
                {
                    buffer.Append((char)c);
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        throw new FileFormatException("Unexpected EOF (malformed number object).", stream.Position);
                    }
                    if (c == '.')
                    {
                        tokenType = TokenTypeEnum.Real;
                    }
                    else if (c < '0' || c > '9')
                    {
                        break;
                    }
                } while(true);

                stream.Skip(-1); // Recover the first byte after the current token.
                break;

            case Symbol.OpenSquareBracket: // Array (begin).
                tokenType = TokenTypeEnum.ArrayBegin;
                break;

            case Symbol.CloseSquareBracket: // Array (end).
                tokenType = TokenTypeEnum.ArrayEnd;
                break;

            case Symbol.OpenAngleBracket: // Dictionary (begin) | Hexadecimal string.
                c = stream.ReadByte();
                if (c == -1)
                {
                    throw new FileFormatException("Unexpected EOF (isolated opening angle-bracket character).", stream.Position);
                }
                // Is it a dictionary (2nd angle bracket [PDF:1.6:3.2.6])?
                if (c == Symbol.OpenAngleBracket)
                {
                    tokenType = TokenTypeEnum.DictionaryBegin;
                    break;
                }

                // Hexadecimal string (single angle bracket [PDF:1.6:3.2.3]).
                tokenType = TokenTypeEnum.Hex;

                // [FIX:0.0.4:4] It skipped after the first hexadecimal character, missing it.
                buffer = new StringBuilder();
                while (c != Symbol.CloseAngleBracket) // NOT string end.
                {
                    buffer.Append((char)c);

                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        throw new FileFormatException("Unexpected EOF (malformed hex string).", stream.Position);
                    }
                }
                break;

            case Symbol.CloseAngleBracket: // Dictionary (end).
                c = stream.ReadByte();
                if (c != Symbol.CloseAngleBracket)
                {
                    throw new FileFormatException("Malformed dictionary.", stream.Position);
                }

                tokenType = TokenTypeEnum.DictionaryEnd;
                break;

            case Symbol.OpenRoundBracket: // Literal string.
                tokenType = TokenTypeEnum.Literal;

                buffer = new StringBuilder();
                int level = 0;
                while (true)
                {
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        break;
                    }
                    if (c == Symbol.OpenRoundBracket)
                    {
                        level++;
                    }
                    else if (c == Symbol.CloseRoundBracket)
                    {
                        level--;
                    }
                    else if (c == '\\')
                    {
                        bool lineBreak = false;
                        c = stream.ReadByte();
                        switch (c)
                        {
                        case 'n':
                            c = Symbol.LineFeed;
                            break;

                        case 'r':
                            c = Symbol.CarriageReturn;
                            break;

                        case 't':
                            c = '\t';
                            break;

                        case 'b':
                            c = '\b';
                            break;

                        case 'f':
                            c = '\f';
                            break;

                        case Symbol.OpenRoundBracket:
                        case Symbol.CloseRoundBracket:
                        case '\\':
                            break;

                        case Symbol.CarriageReturn:
                            lineBreak = true;
                            c         = stream.ReadByte();
                            if (c != Symbol.LineFeed)
                            {
                                stream.Skip(-1);
                            }
                            break;

                        case Symbol.LineFeed:
                            lineBreak = true;
                            break;

                        default:
                        {
                            // Is it outside the octal encoding?
                            if (c < '0' || c > '7')
                            {
                                break;
                            }

                            // Octal [PDF:1.6:3.2.3].
                            int octal = c - '0';
                            c = stream.ReadByte();
                            // Octal end?
                            if (c < '0' || c > '7')
                            {
                                c = octal; stream.Skip(-1); break;
                            }
                            octal = (octal << 3) + c - '0';
                            c     = stream.ReadByte();
                            // Octal end?
                            if (c < '0' || c > '7')
                            {
                                c = octal; stream.Skip(-1); break;
                            }
                            octal = (octal << 3) + c - '0';
                            c     = octal & 0xff;
                            break;
                        }
                        }
                        if (lineBreak)
                        {
                            continue;
                        }
                        if (c == -1)
                        {
                            break;
                        }
                    }
                    else if (c == Symbol.CarriageReturn)
                    {
                        c = stream.ReadByte();
                        if (c == -1)
                        {
                            break;
                        }
                        if (c != Symbol.LineFeed)
                        {
                            c = Symbol.LineFeed; stream.Skip(-1);
                        }
                    }
                    if (level == -1)
                    {
                        break;
                    }

                    buffer.Append((char)c);
                }
                if (c == -1)
                {
                    throw new FileFormatException("Malformed literal string.", stream.Position);
                }

                break;

            case Symbol.CapitalR: // Indirect reference.
                tokenType = TokenTypeEnum.Reference;
                break;

            case Symbol.Percent: // Comment [PDF:1.6:3.1.2].
                tokenType = TokenTypeEnum.Comment;

                buffer = new StringBuilder();
                while (true)
                {
                    c = stream.ReadByte();
                    if (c == -1 ||
                        IsEOL(c))
                    {
                        break;
                    }

                    buffer.Append((char)c);
                }
                break;

            default: // Keyword object.
                tokenType = TokenTypeEnum.Keyword;

                buffer = new StringBuilder();
                do
                {
                    buffer.Append((char)c);
                    c = stream.ReadByte();
                    if (c == -1)
                    {
                        break;
                    }
                } while(!IsDelimiter(c) && !IsWhitespace(c));
                stream.Skip(-1); // Recover the first byte after the current token.
                break;
            }

            if (buffer != null)
            {
                /*
                 * Current token initialization.
                 */
                // Wich token type?
                switch (tokenType)
                {
                case TokenTypeEnum.Keyword:
                    token = buffer.ToString();
                    // Late recognition.
                    switch ((string)token)
                    {
                    case Keyword.False:
                    case Keyword.True: // Boolean.
                        tokenType = TokenTypeEnum.Boolean;
                        token     = bool.Parse((string)token);
                        break;

                    case Keyword.Null: // Null.
                        tokenType = TokenTypeEnum.Null;
                        token     = null;
                        break;
                    }
                    break;

                case TokenTypeEnum.Comment:
                case TokenTypeEnum.Hex:
                case TokenTypeEnum.Name:
                    token = buffer.ToString();
                    break;

                case TokenTypeEnum.Literal:
                    token = buffer.ToString();
                    // Late recognition.
                    if (((string)token).StartsWith(Keyword.DatePrefix)) // Date.
                    {
                        tokenType = TokenTypeEnum.Date;
                        token     = PdfDate.ToDate((string)token);
                    }
                    break;

                case TokenTypeEnum.Integer:
                    token = Int32.Parse(
                        buffer.ToString(),
                        NumberStyles.Integer,
                        StandardNumberFormatInfo
                        );
                    break;

                case TokenTypeEnum.Real:
                    // [FIX:1668410] Parsing of float numbers was buggy (localized default number format).
                    token = Single.Parse(
                        buffer.ToString(),
                        NumberStyles.Float,
                        StandardNumberFormatInfo
                        );
                    break;
                }
            }
            return(true);
        }
示例#10
0
            public object UnpackNull()
            {
                byte markerByte = _in.ReadByte();

                if (markerByte != NULL)
                {
                    throw new ProtocolException(
                              $"Expected a null, but got: 0x{(markerByte & 0xFF).ToString("X2")}");
                }
                return(null);
            }