@Gankra Good post.
Regarding capacity: Searching the standard library, I find:
-
foo.capacity() - foo.len()
onVec<u8>
in two places (libstd/sys/windows/pipe.rs
,libstd/sys_common/io.rs
), both as part of unsafe code that passes the uninitialized portion of theVec
to OS read functions; -
foo.capacity() == foo.len()
onVec<u8>
in the samelibstd/sys/windows/pipe.rs
, and onVec<T>
inlibcollections/vec.rs
. (In the latter case, capacity ≠ len is taken to mean that an element can be appended without reallocating.)
If capacity()
returns 0, the first will overflow, and the second will allow out-of-bounds writes – both really bad. Of course, the stdlib itself can be changed, but external code may include similar logic. So I think capacity()
returning 0 is unviable at least for Vec
, and probably for String
as well.
(But then, I agree that supporting statics in Vec
is a bad idea anyway because of the cost on deref_mut
; I didn’t think of doing it only for String
.)
Also, nit: I don’t think any of pop
, truncate
, or clear
would need to special-case static strings, unless you’re really concerned about capacity()
staying the same; the static pointer is still valid with a reduced length.