While early drops make excellent sense to implement at some point, I don't think this particular use case justifies it.
The default way of handling reads should be to do them in chunks to avoid memory usage blowout, for example with std::io::BufReader. If a file is several MB in size and you need the entire thing to be available at once, you should mmap it instead (that's on Linux, I presume there is an equivalent for Windows) -- in fact if you trigger multi-page allocations you already end up calling mmap to satisfy them, except in code above you avoidably make a copy of the thing.
read_to_string is only legitimate for files which are known to be small (for example your config).
If shadowing caused the old variable to be dropped, then what would be the use of such "shadowing"? It would then be exactly identical to assigning to a mutable place. It simply doesn't make sense to expect that it be exactly the same as something else in the first place.
I'm not questioning the reasoning of the language. I just was under the impression that, since the old value could not be accessed anymore due to shadowing, that the old value would become out of scope, and dropped. That is all. And I do understand that a feature like that would be an overhead to the compiler, and (probably, haven't got there yet) cause unexpected behavior for people trying assembly blocks and unsafe code.
For me this would be common sense. But common sense is known to give us wrong sense some times
That's not what I'm saying. I'm saying that if shadowing worked like that, it would make it identical to mut, so by "common sense", as you mentioned, you should suspect that it is not the case that there are two completely identical mechanisms with different name, syntax, and usage.
That still doesn't add up conceptually. Rust is not dynamically-typed, so if a redeclaration actually overwrites an existing variable, then it wouldn't make sense for it to change the type.
(I understand that it can technically be done, but that's not my point.)