make SliceBuilder safer to use.

This commit is contained in:
Cameron Ross 2018-04-17 00:17:10 -03:00
parent 4cad68f924
commit 568acb832a
No known key found for this signature in database
GPG key ID: 777897D98DC91C54
2 changed files with 17 additions and 17 deletions

View file

@ -531,15 +531,17 @@ public:
/// end of the slice being built, the slice is extended (trivial operation).
///
/// See_Also: begin
void write(char[] str) @trusted pure nothrow @nogc
void write(char[] str) @safe pure nothrow @nogc
{
assert(inProgress, "write called without begin");
assert(end_ <= reader_.bufferOffset_,
"AT START: Slice ends after buffer position");
// Nothing? Already done.
if (str.length == 0) { return; }
// If str starts at the end of the slice (is a string returned by a Reader
// method), just extend the slice to contain str.
if(str.ptr == reader_.buffer_.ptr + end_)
if(&str[0] == &reader_.buffer_[end_])
{
end_ += str.length;
}
@ -547,8 +549,7 @@ public:
// by a Reader method and point to buffer. So we need to memmove.
else
{
core.stdc.string.memmove(reader_.buffer_.ptr + end_, cast(char*)str.ptr,
str.length * char.sizeof);
copy(str, reader_.buffer_[end_..end_ + str.length * char.sizeof]);
end_ += str.length;
}
}
@ -585,7 +586,7 @@ public:
/// position = Position to insert the character at in code units, not code points.
/// Must be less than slice length(); a previously returned length()
/// can be used.
void insert(const dchar c, const size_t position) @system pure nothrow @nogc
void insert(const dchar c, const size_t position) @safe pure nothrow @nogc
{
assert(inProgress, "insert called without begin");
assert(start_ + position <= end_, "Trying to insert after the end of the slice");
@ -600,9 +601,8 @@ public:
if(movedLength > 0)
{
core.stdc.string.memmove(reader_.buffer_.ptr + point + bytes,
reader_.buffer_.ptr + point,
movedLength * char.sizeof);
copy(reader_.buffer_[point..point + movedLength * char.sizeof],
reader_.buffer_[point + bytes..point + bytes + movedLength * char.sizeof]);
}
reader_.buffer_[point .. point + bytes] = encodeBuf[0 .. bytes];
end_ += bytes;
@ -635,9 +635,9 @@ public:
/// ended either by commit()-ing or reverting through the destructor.
///
/// Saves the current state of a slice.
this(ref SliceBuilder builder) @system pure nothrow @nogc
this(SliceBuilder* builder) @safe pure nothrow @nogc
{
builder_ = &builder;
builder_ = builder;
stackLevel_ = builder_.endStackUsed_;
builder_.push();
}

View file

@ -1210,7 +1210,7 @@ final class Scanner
/// Scan a block scalar token with specified style.
///
/// In case of an error, error_ is set. Use throwIfError() to handle this.
Token scanBlockScalar(const ScalarStyle style) @trusted
Token scanBlockScalar(const ScalarStyle style) @safe
{
const startMark = reader_.mark;
@ -1233,7 +1233,7 @@ final class Scanner
alias Transaction = SliceBuilder.Transaction;
// Used to strip the last line breaks written to the slice at the end of the
// scalar, which may be needed based on chomping.
Transaction breaksTransaction = Transaction(reader_.sliceBuilder);
Transaction breaksTransaction = Transaction(&reader_.sliceBuilder);
// Read the first indentation/line breaks before the scalar.
size_t startLen = reader_.sliceBuilder.length;
if(increment == int.min)
@ -1263,7 +1263,7 @@ final class Scanner
// This transaction serves to rollback data read in the
// scanBlockScalarBreaksToSlice() call.
breaksTransaction = Transaction(reader_.sliceBuilder);
breaksTransaction = Transaction(&reader_.sliceBuilder);
startLen = reader_.sliceBuilder.length;
// The line breaks should actually be written _after_ the if() block
// below. We work around that by inserting
@ -1712,7 +1712,7 @@ final class Scanner
/// Scan plain scalar token (no block, no quotes).
///
/// In case of an error, error_ is set. Use throwIfError() to handle this.
Token scanPlain() @trusted
Token scanPlain() @safe
{
// We keep track of the allowSimpleKey_ flag here.
// Indentation rules are loosed for the flow context
@ -1788,7 +1788,7 @@ final class Scanner
endMark = reader_.mark;
spacesTransaction.commit();
spacesTransaction = Transaction(reader_.sliceBuilder);
spacesTransaction = Transaction(&reader_.sliceBuilder);
const startLength = reader_.sliceBuilder.length;
scanPlainSpacesToSlice(startMark);
@ -1809,7 +1809,7 @@ final class Scanner
///
/// Assumes that the caller is building a slice in Reader, and puts the spaces
/// into that slice.
void scanPlainSpacesToSlice(const Mark startMark) @system
void scanPlainSpacesToSlice(const Mark startMark) @safe
{
// The specification is really confusing about tabs in plain scalars.
// We just forbid them completely. Do not use tabs in YAML!
@ -1847,7 +1847,7 @@ final class Scanner
bool extraBreaks = false;
alias Transaction = SliceBuilder.Transaction;
auto transaction = Transaction(reader_.sliceBuilder);
auto transaction = Transaction(&reader_.sliceBuilder);
if(lineBreak != '\n') { reader_.sliceBuilder.write(lineBreak); }
while(search.canFind(reader_.peek()))
{