Change Log: 2.075.0
Download D 2.075.0
released Jul 19, 2017
Compiler changes
Runtime changes
Library changes
List of all bug fixes and enhancements in D 2.075.0.
Compiler changes
- add __traits(getParameterStorageClasses, f, i)
ref int foo(return ref const int* p, scope int* a, out int b, lazy int c); pragma(msg, __traits(getParameterStorageClasses, foo, 0)); static assert(__traits(getParameterStorageClasses, foo, 0)[0] == "return"); static assert(__traits(getParameterStorageClasses, foo, 0)[1] == "ref"); pragma(msg, __traits(getParameterStorageClasses, foo, 1)); static assert(__traits(getParameterStorageClasses, foo, 1)[0] == "scope"); static assert(__traits(getParameterStorageClasses, foo, 2)[0] == "out"); static assert(__traits(getParameterStorageClasses, typeof(&foo), 3)[0] == "lazy");
- Comparison of values belonging to different enums is deprecated.
This change does not affect anonymous enumerations.
enum Status { good, bad } enum OtherStatus { ok no, } // Deprecated - Even though both good and ok evaluate to 0 they belong to // different enumeration types static assert(Status.good == OtherStatus.ok);
- The deprecated built-in array properties .sort and .reverse were removed.
Usage of those built-in array properties was deprecated since 2.072.0 and they have now been removed. Use std.algorithm.sorting.sort and std.algorithm.mutation.reverse instead.
- Deprecate empty statements made by semicolon
Creating empty statements using semicolons, for which was previously issued a warning is now causing a deprecation hint.
- add __traits(getFunctionVariadicStyle, f)
import core.stdc.stdarg; void novar() {} extern(C) void cstyle(int, ...) {} extern(C++) void cppstyle(int, ...) {} void dstyle(...) {} void typesafe(int[]...) {} static assert(__traits(getFunctionVariadicStyle, novar) == "none"); static assert(__traits(getFunctionVariadicStyle, cstyle) == "stdarg"); static assert(__traits(getFunctionVariadicStyle, cppstyle) == "stdarg"); static assert(__traits(getFunctionVariadicStyle, dstyle) == "argptr"); static assert(__traits(getFunctionVariadicStyle, typesafe) == "typesafe"); static assert(__traits(getFunctionVariadicStyle, (int[] a...) {}) == "typesafe"); static assert(__traits(getFunctionVariadicStyle, typeof(cstyle)) == "stdarg");
Runtime changes
- Windows: the DATA and TLS segment can now be configured to be scanned precisely.
A new runtime option "scanDataSeg" has been added to enable precise scanning of the DATA and the TLS segments. This uses information generated by the compiler to identify possible pointers inside these segments. Possible option values are "conservative" (default) and "precise".
As usual, this option can be set by the environment, the command line or by embedding the option into the executable similar to the GC options.
For example add this code to your main module to enable precise scanning:
extern(C) __gshared string[] rt_options = [ "scanDataSeg=precise" ];
- Make fiber stack protection-page size configurable
It is now possible to change the guard page size by using the new Fiber's constructor argument - guard_page_size. It defaults to PAGE_SIZE (the same it used to be on Windows), and specifying 0 will turn this feature off.
- Add Fiber's stack-protection page for Posix.
The feature already existing for Windows' fiber implementation is now added to the systems using mmap to allocate fibers' stacks: After (or before) the last page used for the Fiber's stack, the page is allocate which is protected for any kind of access. This will cause system to trap immediately on the fiber's stack overflow.
- TypeInfo.init now refers to type property.
TypeInfo.init used to refer to the method that is now called TypeInfo.initializer. The name change was necessary because the name "init" would clash with the type property of the same name (init). TypeInfo.init now refers to the type property.
Library changes
- hasLength now enforces that length has type size_t
Historically hasLength!R yielded true for types whereby R.length returns other types convertible to ulong, such as int, ushort, const(size_t), user-defined types using alias this, or notably ulong on 32-bit systems. This behavior has been deprecated. After December 2017, std.range.primitives.hasLength will yield true only if R.length yields the exact type size_t.
- std.datetime has been split into a package.
std.datetime is now a package containing the following modules:
- std.datetime.date
- std.datetime.interval
- std.datetime.stopwatch
- std.datetime.systime
- std.datetime.timezone
The std.datetime package publicly imports all of those modules. So, it should be the case that no existing code will break, as everything in std.datetime will still be imported by importing std.datetime. New code can choose to import the modules individually or to import the entire package.
std.datetime.date contains Date, TimeOfDay, DateTime, and the related free functions. It also contains DateTimeException.
std.datetime.interval contains the *Interval and *IntervalRange types as well as the related free functions.
std.datetime.systime contains SysTime and the related free functions.
std.datetime.timezone contains the time zone types.
The std.datetime package contains StopWatch and the benchmarking functions (so, they can only be imported via std.datetime and not via a submodule). As those functions use core.time.TickDuration (which is being replaced by core.time.MonoTime, they are slated for deprecation).
std.datetime.stopwatch has been added. It contains versions of StopWatch and benchmark which have almost the same API as the existing symbols, but they use core.time.MonoTime and core.time.Duration instead of core.time.TickDuration. In the next major release, the old functions in std.datetime.package will be deprecated, so code which uses the old benchmarking functions should be updated to use std.datetime.stopwatch.
However, note that in order to avoid irreconcilable symbol conflicts between the new and old versions, std.datetime.stopwatch will not be publicly imported by std.datetime.package until the old symbols have been removed. So, for the time being, code using std.datetime.stopwatch.StopWatch or std.datetime.stopwatch.benchmark will need to import std.datetime.stopwatch directly. Code which imports both std.datetime and std.datetime.stopwatch will need to either use selective imports or fully qualified symbols to reconcile the symbol conflicts, but no code will be affected by the changes until it's updated to import std.datetime.stopwatch, and when the old symbols are finally removed, the selective imports and fully qualified paths to the new symbols will continue to work and won't break (though at that point, simply importing std.datetime will work, since std.datetime.package will have been updated to publicly import std.datetime.stopwatch). Code that simply imporst std.datetime.stopwatch without importing std.datetime will not have to worry about symbol conflicts.
- Several functions in std.string have been deprecated
The functions std.string.inPattern, std.string.countchars, std.string.removechars, std.string.squeeze, and std.string.munch, have all been deprecated. These functions are obsolete, as their functionality is better covered by the functions in std.regex and std.algorithm. They will be removed from std.string on May 2018.
If you still need to use these, please see undeaD.
The following are examples of the deprecated functions, and their modern replacements.
Use std.algorithm.searching.find to replace std.string.munch:
import std.algorithm; import std.ascii; import std.string; import std.utf; string s = "\tabc"; // old s.munch(whitespace); // new s = s.find!(a => !isWhite(a));
Use std.regex.matchFirst to replace std.string.inPattern:
import std.string; import std.regex; // old if (inPattern('x', "a-z")) { ... } // new if ("x".matchFirst(regex("[a-z]"))) { ... }
Use std.regex.replaceAll to replace std.string.removechars:
import std.string; import std.regex; // old "abc".removechars("a-z"); // new "abc".replaceAll(regex("[a-z]"), "");
Use std.algorithm.iteration.uniq to replace std.string.squeeze:
import std.algorithm; import std.string; // old "hello".squeeze; // new "hello".uniq;
- Added a constant time comparison function for cryptographic hashes
Added a new function to std.digest.digest.secureEqual that compares two ranges that represent hashes in a secure manner. The comparison is done in constant time regardless of the equality of the two ranges in order to protect against timing attacks. For more information on the attack, please refer to the docs on std.digest.digest.secureEqual.
import std.digest.digest : secureEqual, toHexString; import std.digest.hmac : hmac; import std.digest.sha : SHA1; import std.string : representation; void main() { // a typical HMAC data integrity verification auto secret = "A7GZIP6TAQA6OHM7KZ42KB9303CEY0MOV5DD6NTV".representation; auto data = "data".representation; string hex1 = data.hmac!SHA1(secret).toHexString; string hex2 = data.hmac!SHA1(secret).toHexString; string hex3 = "data1".representation.hmac!SHA1(secret).toHexString; assert( secureEqual(hex1, hex2)); assert(!secureEqual(hex1, hex3)); }
- Added support for 64 bit CRC
Support for both ISO and ECMA 64 bit CRC was added to std.digest.crc.
import std.digest.crc; void main() { ubyte[8] hash64ecma = crc64ECMAOf("abc"); assert(crcHexString(hash64ecma) == "2CD8094A1A277627"); ubyte[8] hash64iso = crc64ISOOf("abc"); assert(crcHexString(hash64iso) == "3776C42000000000"); }
List of all bug fixes and enhancements in D 2.075.0:
DMD Compiler regressions
- Bugzilla 16408: [REG2.065] left-to-right order of evaluation of function arguments not consistently followed
- Bugzilla 17275: [REG 2.072.0] AssertError@declaration.d(2121): Assertion failure
- Bugzilla 17293: "Using C++ Classes From D" example no longer works
- Bugzilla 17338: [Reg 2.075] link failure unsupported symbol section 0xff01
- Bugzilla 17352: [REG 2.075a] Internal error: ddmd/backend/elfobj.c 1739 on duplicate definition
- Bugzilla 17356: [Reg 2.075] __simd_sto no longer executed
- Bugzilla 17399: [REG2.071] core.checkedint.addu cannot inline function
- Bugzilla 17451: ICE in ddmd/declaration.d(2179)
- Bugzilla 17481: [REG 2.069.0] synchronized: Access Violation with dmd -O on win32
- Bugzilla 17492: [REG 2.066] [ICE] AssertError@ddmd/dclass.d(1007): Assertion failure
- Bugzilla 17502: [REG2.064] Out contract in class method causes dmd segfault.
- Bugzilla 17505: [REG2.075] @safe constructor requires the deconstructor to be safe as well
- Bugzilla 17506: [REG2.075] @disable constructor requires members to be initialized
- Bugzilla 17545: [REG2.072] __traits(getAttributes, name) evaluates name to value prematurely
- Bugzilla 17548: [REG2.072.0] Forward reference error with scope function parameters
- Bugzilla 17614: [REG2.075.0-b2] __VERSION__ has the wrong value
DMD Compiler bugs
- Bugzilla 7016: local import does not create -deps dependency
- Bugzilla 13331: naked asm functions are broken when compiling with -profile
- Bugzilla 15896: private ignored when import bindings are used
- Bugzilla 15945: sizeof on an invalid type seems to compile.
- Bugzilla 16244: compiler ICE on complex typeof() for method arg type
- Bugzilla 16566: hasLength should enforce that length has type size_t
- Bugzilla 17289: With Xcode 8.3 linker, warnings of "pointer not aligned"
- Bugzilla 17317: 2.074.0 release candidate does not have updated backend license
- Bugzilla 17335: Function calls in conjunctions do not short circuit when evaluated during compilation
- Bugzilla 17337: SIGILL for AVX vector initialization
- Bugzilla 17339: ambiguous mangling with const alias argument
- Bugzilla 17344: ICE with assignment of post inc-/decremented integral vector
- Bugzilla 17349: Covariant overrides should be allowed
- Bugzilla 17367: CodeView/MSCOFF: bad debug information for enumerators
- Bugzilla 17391: SECURITY: XSSÂ through DDOC comments
- Bugzilla 17422: [scope] class reference not initialized as scope variable
- Bugzilla 17432: [DIP1000] scope delegates change type, but not mangling
- Bugzilla 17450: escaping delegate context pointer not detected for member functions
- Bugzilla 17468: Internal assertion fails during CTFE
- Bugzilla 17491: Compiles on invalid: *&s.init.var is not an lvalue
- Bugzilla 17495: __traits(getParameterStorageClasses) doesn't work with tuples as parameters
DMD Compiler enhancements
- Bugzilla 6227: Comparison of different enums
- Bugzilla 16197: Constructors/postblits and destructors don't match up for array initialisation
- Bugzilla 16540: Attributes do not propagate correctly in lazy params
- Bugzilla 16600: Wrong error message for ambiguous mutable/immutable constructor
- Bugzilla 17396: Add colorized syntax highlighting to error messages emitted by dmd
- Bugzilla 17419: add __traits(getLinkage, s) to the the linkage of symbol s
- Bugzilla 17425: add __traits(getParameterStorageClasses, f, i)
- Bugzilla 17429: [scope] each scope class references adds another delete call
- Bugzilla 17457: Named Return Value Optimization (NRVO) not done with return of constructor call
- Bugzilla 17494: Do not execute scope(...) if an Error exception has been thrown
Phobos regressions
- Bugzilla 17452: Undefined references in std.container.array
- Bugzilla 17472: [Reg 2.075] typeof(stdin) is no longer a File
- Bugzilla 17482: [REG 2.074] comile error: Comparing Nullable!Variant with basic type
- Bugzilla 17511: [REG 2.075a] std.xml puts grand-children into items
- Bugzilla 17555: [REG2.070.0] Control characters in JSON data are invalid and should cause an exception
- Bugzilla 17650: [REG v2.075.0 b1-b4] std.getopt range violation
Phobos bugs
- Bugzilla 5904: std.json parseString doesn't handle chars outside the BMP
- Bugzilla 15517: std.experimental.logger: using 'sharedLog' to change to file logging for default logger does not work
- Bugzilla 15534: [std.experimental.logger.core] Documentation mismatch
- Bugzilla 15720: iota(long.max, long.min, step) does not work properly
- Bugzilla 15763: std.math.approxEqual is not symmetric
- Bugzilla 16246: cannot call iota with 3 [u]bytes or 3 [u]shorts
- Bugzilla 16256: std.experimental.logger cant log a dstring properly
- Bugzilla 16326: filter is not lazy enough & has weird save behavior
- Bugzilla 17251: Appender.put errors out with const input range elements
- Bugzilla 17270: std.experimental.Final fails on pointers
- Bugzilla 17283: std.experimental.typecons uses private module members
- Bugzilla 17288: formattedWrite error when width/precision provided and no value to format
- Bugzilla 17314: BinaryHeap crashes upon insertion if heapified with an array of length 1
- Bugzilla 17328: std.experimental.logger: wrong hex formatting for zeros
- Bugzilla 17519: RedBlackTree doesn't like const/immutable elements
- Bugzilla 17553: std.json should not do UTF decoding when encoding JSON
- Bugzilla 17556: std.json encodes non-BMP characters incorrectly with JSONOptions.escapeNonAsciiChars
- Bugzilla 17564: std.experimental.allocator.theAllocator is null within shared static this
Phobos enhancements
- Bugzilla 6621: Superimposition amount for std.range.chunks
- Bugzilla 7102: std.numeric.gcd with BigInts too
- Bugzilla 10001: string formatting with underscores
- Bugzilla 16108: to!string fails on struct with disabled postblit
- Bugzilla 16615: std.process is missing functionality for child processes
- Bugzilla 17286: A function for comparing two digests securely
- Bugzilla 17327: std.getopt: repeated options unrecognised
- Bugzilla 17394: std.file.mkdirRecurse isn't @safe
- Bugzilla 17557: std.json should not do UTF decoding when parsing
Druntime bugs
- Bugzilla 9275: [GC] removeRoot hits assert(0) instead of being a no-op (as documented)
- Bugzilla 12233: Attempting to use TypeInfo.init results in a compiler error due to lack of 'this'.
- Bugzilla 13186: core/sys/posix/sys/uio.d is not linked into the standard lib
- Bugzilla 16856: D does not work on FreeBSD current (what will eventually be 12) due to libunwind
dlang.org bugs
- Bugzilla 8107: Float literals are not specified as they are implemented
- Bugzilla 17303: type error in the href url under the link Systems Programming
- Bugzilla 17469: View source code
- Bugzilla 17501: Runnable unittest problem with AST rewrite