/// <summary> /// Take and return the current value and advance this iterator the next value. /// </summary> /// <returns>The taken current value.</returns> public static T TakeCurrent <T>(this Iterator <T> iterator) { PreCondition.AssertNotNull(iterator, nameof(iterator)); PreCondition.AssertTrue(iterator.HasCurrent(), "iterator.HasCurrent()"); T result = iterator.Current; iterator.Next(); return(result); }
private void ReadDigits() { PreCondition.AssertTrue(this.characters.HasCurrent(), "this.characters.HasCurrent()"); PreCondition.AssertTrue(PkgdefTokenizer.IsDigit(this.characters.GetCurrent()), "PkgdefTokenizer.IsDigit(this.characters.GetCurrent())"); int startIndex = this.characters.GetCurrentIndex(); StringBuilder builder = new StringBuilder().Append(this.characters.TakeCurrent()); while (this.characters.HasCurrent() && PkgdefTokenizer.IsDigit(this.characters.GetCurrent())) { builder.Append(this.characters.TakeCurrent()); } this.tokenQueue.Enqueue(PkgdefToken.Digits(startIndex, builder.ToString())); }
private static PkgdefSegment ParseSegment(PkgdefTokenizer tokenizer, Action <PkgdefIssue> onIssue) { PreCondition.AssertNotNull(tokenizer, nameof(tokenizer)); PreCondition.AssertTrue(tokenizer.HasCurrent(), "tokenizer.HasCurrent()"); PreCondition.AssertNotNull(onIssue, nameof(onIssue)); PkgdefSegment result; switch (tokenizer.GetCurrent().GetTokenType()) { case PkgdefTokenType.Whitespace: result = PkgdefSegment.Whitespace(tokenizer.GetCurrent().GetStartIndex(), tokenizer.GetCurrent().GetText()); tokenizer.Next(); break; case PkgdefTokenType.NewLine: result = PkgdefSegment.NewLine(tokenizer.GetCurrent().GetStartIndex(), tokenizer.GetCurrent().GetText()); tokenizer.Next(); break; case PkgdefTokenType.ForwardSlash: result = PkgdefDocument.ParseLineComment(tokenizer, onIssue); break; case PkgdefTokenType.LeftSquareBracket: result = PkgdefDocument.ParseRegistryKeyPath(tokenizer, onIssue); break; case PkgdefTokenType.AtSign: case PkgdefTokenType.DoubleQuote: result = PkgdefDocument.ParseRegistryKeyDataItem(tokenizer, onIssue); break; default: result = PkgdefSegment.Unrecognized(tokenizer.GetCurrent().GetStartIndex(), tokenizer.GetCurrent().GetText()); tokenizer.Next(); break; } return(result); }
private void ReadWhitespace() { PreCondition.AssertTrue(this.characters.HasCurrent(), "this.characters.HasCurrent()"); PreCondition.AssertTrue(PkgdefTokenizer.IsWhitespaceCharacter(this.characters.GetCurrent()), "PkgdefTokenizer.IsWhitespaceCharacter(this.characters.GetCurrent())"); PkgdefToken newLineToken = null; int startIndex = this.characters.GetCurrentIndex(); StringBuilder builder = new StringBuilder(); while (this.characters.HasCurrent() && PkgdefTokenizer.IsWhitespaceCharacter(this.characters.GetCurrent())) { if (this.characters.GetCurrent() != '\r') { builder.Append(this.characters.TakeCurrent()); } else { int newLineStartIndex = this.characters.GetCurrentIndex(); if (this.characters.Next() && this.characters.GetCurrent() == '\n') { newLineToken = PkgdefToken.NewLine(newLineStartIndex, "\r\n"); this.characters.Next(); break; } else { builder.Append('\r'); } } } if (builder.Length > 0) { this.tokenQueue.Enqueue(PkgdefToken.Whitespace(startIndex, builder.ToString())); } if (newLineToken != null) { this.tokenQueue.Enqueue(newLineToken); } }
internal static PkgdefRegistryKeyPathSegment ParseRegistryKeyPath(PkgdefTokenizer tokenizer, Action <PkgdefIssue> onIssue) { PreCondition.AssertNotNull(tokenizer, nameof(tokenizer)); PreCondition.AssertTrue(tokenizer.HasCurrent(), "tokenizer.HasCurrent()"); PreCondition.AssertEqual(tokenizer.GetCurrent().GetTokenType(), PkgdefTokenType.LeftSquareBracket, "tokenizer.GetCurrent().GetTokenType()"); PreCondition.AssertNotNull(onIssue, nameof(onIssue)); List <PkgdefToken> tokens = new List <PkgdefToken>() { tokenizer.TakeCurrent() }; while (tokenizer.HasCurrent()) { PkgdefTokenType tokenType = tokenizer.GetCurrent().GetTokenType(); if (tokenType == PkgdefTokenType.NewLine) { break; } else { tokens.Add(tokenizer.TakeCurrent()); if (tokenType == PkgdefTokenType.RightSquareBracket) { break; } } } PkgdefRegistryKeyPathSegment result = new PkgdefRegistryKeyPathSegment(tokens); if (result.GetRightSquareBracket() == null) { onIssue(new PkgdefIssue(result.GetStartIndex(), result.GetLength(), "Missing registry key path right square bracket (']').")); } return(result); }
internal static PkgdefSegment ParseLineComment(PkgdefTokenizer tokenizer, Action <PkgdefIssue> onIssue) { PreCondition.AssertNotNull(tokenizer, nameof(tokenizer)); PreCondition.AssertTrue(tokenizer.HasCurrent(), "tokenizer.HasCurrent()"); PreCondition.AssertEqual(tokenizer.GetCurrent().GetTokenType(), PkgdefTokenType.ForwardSlash, "tokenizer.GetCurrent().GetTokenType()"); PreCondition.AssertNotNull(onIssue, nameof(onIssue)); PkgdefSegment result; int startIndex = tokenizer.TakeCurrent().GetStartIndex(); StringBuilder builder = new StringBuilder().Append('/'); if (!tokenizer.HasCurrent()) { onIssue(new PkgdefIssue(startIndex, 1, "Missing line-comment's second forward slash ('/').")); result = PkgdefSegment.Unrecognized(startIndex, builder.ToString()); } else if (tokenizer.GetCurrent().GetTokenType() != PkgdefTokenType.ForwardSlash) { onIssue.Invoke(new PkgdefIssue(startIndex + 1, 1, "Expected line-comment's second forward slash ('/').")); result = PkgdefSegment.Unrecognized(startIndex, builder.ToString()); } else { builder.Append('/'); tokenizer.Next(); while (tokenizer.HasCurrent() && tokenizer.GetCurrent().GetTokenType() != PkgdefTokenType.NewLine) { builder.Append(tokenizer.TakeCurrent().GetText()); } string text = builder.ToString(); result = PkgdefSegment.LineComment(startIndex, text); } return(result); }
internal static PkgdefRegistryKeyDataItemSegment ParseRegistryKeyDataItem(PkgdefTokenizer tokenizer, Action <PkgdefIssue> onIssue) { PreCondition.AssertNotNull(tokenizer, nameof(tokenizer)); PreCondition.AssertTrue(tokenizer.HasCurrent(), "tokenizer.HasCurrent()"); PreCondition.AssertOneOf(tokenizer.GetCurrent().GetTokenType(), new[] { PkgdefTokenType.AtSign, PkgdefTokenType.DoubleQuote }, "tokenizer.GetCurrent().GetTokenType()"); PreCondition.AssertNotNull(onIssue, nameof(onIssue)); PkgdefToken registryKeyDataItemNameFirstToken = tokenizer.TakeCurrent(); List <PkgdefToken> tokens = new List <PkgdefToken>() { registryKeyDataItemNameFirstToken }; bool dataItemDone = false; if (registryKeyDataItemNameFirstToken.GetTokenType() == PkgdefTokenType.DoubleQuote) { if (!tokenizer.HasCurrent()) { onIssue(new PkgdefIssue(registryKeyDataItemNameFirstToken.GetStartIndex(), registryKeyDataItemNameFirstToken.GetLength(), "Missing registry key data item name closing double-quote ('\"').")); dataItemDone = true; } else { while (tokenizer.HasCurrent()) { PkgdefTokenType tokenType = tokenizer.GetCurrent().GetTokenType(); if (tokenType == PkgdefTokenType.NewLine) { onIssue(new PkgdefIssue(PkgdefToken.GetStartIndex(tokens), PkgdefToken.GetLength(tokens), "Missing registry key data item name closing double-quote ('\"').")); dataItemDone = true; break; } else { PkgdefToken token = tokenizer.TakeCurrent(); tokens.Add(token); if (token.GetTokenType() == PkgdefTokenType.DoubleQuote) { break; } } } } } if (!dataItemDone) { if (!tokenizer.HasCurrent()) { onIssue(new PkgdefIssue(PkgdefToken.GetStartIndex(tokens), PkgdefToken.GetLength(tokens), "Missing registry key data item equals sign ('=').")); dataItemDone = true; } else { while (tokenizer.HasCurrent()) { PkgdefTokenType tokenType = tokenizer.GetCurrent().GetTokenType(); if (tokenType == PkgdefTokenType.NewLine) { onIssue(new PkgdefIssue(PkgdefToken.GetStartIndex(tokens), PkgdefToken.GetLength(tokens), "Missing registry key data item equals sign ('=').")); dataItemDone = true; break; } else { PkgdefToken token = tokenizer.TakeCurrent(); tokens.Add(token); if (token.GetTokenType() == PkgdefTokenType.EqualsSign) { break; } else if (token.GetTokenType() != PkgdefTokenType.Whitespace) { onIssue(new PkgdefIssue(token.GetStartIndex(), token.GetLength(), "Expected registry key data item equals sign ('=').")); } } } } } if (!dataItemDone) { if (!tokenizer.HasCurrent()) { onIssue(new PkgdefIssue(PkgdefToken.GetStartIndex(tokens), PkgdefToken.GetLength(tokens), "Missing registry key data item value.")); } else { int dataItemValueTokenCount = 0; while (tokenizer.HasCurrent()) { PkgdefTokenType tokenType = tokenizer.GetCurrent().GetTokenType(); if (tokenType == PkgdefTokenType.NewLine) { if (dataItemValueTokenCount == 0) { onIssue(new PkgdefIssue(PkgdefToken.GetStartIndex(tokens), PkgdefToken.GetLength(tokens), "Missing registry key data item value.")); } break; } else { PkgdefToken token = tokenizer.TakeCurrent(); tokens.Add(token); if (token.GetTokenType() != PkgdefTokenType.Whitespace) { dataItemValueTokenCount++; } } } } } return(new PkgdefRegistryKeyDataItemSegment(tokens)); }