Report a bug
If you spot a problem with this page, click here to create a Bugzilla issue.
Improve this page
Quickly fork, edit online, and submit a pull request for this page. Requires a signed-in GitHub account. This works well for small changes. If you'd like to make larger changes you may want to consider using a local clone.

Change Log: 2.099.0

previous version: 2.098.1 – next version: 2.099.1

Download D 2.099.0
released Mar 06, 2022

2.099.0 comes with 20 major changes and 221 fixed Bugzilla issues. A huge thanks goes to the 100 contributors who made 2.099.0 possible.

List of all bug fixes and enhancements in D 2.099.0.

Compiler changes

  1. When ref scope return attributes are used on a parameter, and return scope appears, the return applies to the scope, not the ref.

    Formerly, the return sometimes applied to the ref instead, which can be confusing. If return scope does not appear adjacent and in that order, the return will apply to the ref.

  2. __traits(parameters) has been added to the compiler.

    If used inside a function, this trait yields a tuple of the parameters to that function for example:

    int echoPlusOne(int x)
        __traits(parameters)[0] += 1;
        return x;

    This can be used to simply forward a functions parameters (becoming arguments of another), in effect unifying functions with variadic parameters and normal functions i.e. the following pattern is now possible without use of variadics:

    int add(int x, int y)
        return x + y;
    auto forwardToAdd(Pack...)(Pack xy)
        return add(xy);

    would become

    int add(int x, int y)
        return x + y;
    auto forwardToAdd(int x, int y)
        return add(__traits(parameters));

    When used inside a nested function or lambda, the trait gets the arguments of that and only that nested function or lambda, not what they are contained in.

    For example, these assertions hold:

    int testNested(int x)
        static assert(typeof(__traits(parameters)).length == 1);
        int add(int x, int y)
            static assert(typeof(__traits(parameters)).length == 2);
            return x + y;
        return add(x + 2, x + 3);

    When used inside a foreach using an overloaded opApply, the trait yields the parameters to the delegate and not the function the foreach appears within.

    class Tree {
        int opApply(int delegate(size_t, Tree) dg) {
            if (dg(0, this)) return 1;
            return 0;
    void useOpApply(Tree top, int x)
        foreach(idx; 0..5)
            static assert(is(typeof(__traits(parameters)) == AliasSeq!(Tree, int)));
        foreach(idx, elem; top)
            static assert(is(typeof(__traits(parameters)) == AliasSeq!(size_t, Tree)));
  3. Add ability to import modules to ImportC

    ImportC can now import modules with the __import keyword, with the C code:

    __import core.stdc.stdarg; // import a D source file
    __import test2;            // import an ImportC file

    int foo() { va_list x; return 1 + A; }

    test2.c is:

    enum E { A = 3 };

    The syntax for __import after the keyword is the same as for D's import declaration.

  4. Casting between compatible sequences

    Prior to this release, casting between built-in sequences of the same type was not allowed.

    Starting with this release, casting between sequences of the same length is accepted provided that the underlying types of the casted sequence are implicitly convertible to the target sequence types.

    alias Seq(T...) = T;
    void foo()
        Seq!(int, int) seq;
        auto foo = cast(long) seq;
        pragma(msg, typeof(foo)); // (int, int)
        auto bar = cast(Seq!(long, int)) seq; // allowed
        pragma(msg, typeof(bar)); // (long, int)
  5. New command line switch -vasm which outputs assembler code per function

    The new -vasm compiler switch will print to the console the generated assembler code for each function. As opossed to a typical dissasembler, it will omit all the boilerplate and output just the assembly code for each function. For example, compiling the following code:

    // test.d
    int demo(int x)
        return x * x;

    by using the command dmd test.d -c -vasm will yield:

    0000:   89 F8                   mov     EAX,EDI
    0002:   0F AF C0                imul    EAX,EAX
    0005:   C3                      ret
  6. The '-preview=intpromote' switch is now set by default.

    Integer promotions now follow C integral promotions rules consistently It affects the unary - and ~ operators with operands of type byte, ubyte, short, ushort, char, or wchar. The operands are promoted to int before the operator is applied, and the resulting type will now be int.

    To revert to the old behavor, either use the '-revert=intpromote' switch, or explicitly cast the result of the unary operator back to the smaller integral type:

    void main()
        // Note: byte.max = 127, byte.min = -128
        byte b = -128;
        int x = -b; // new behavior: x = 128
        int y = cast(byte)(-b); // old behavior: y = -128
        byte b2 = cast(byte) -b; // cast now required
  7. -m32 now produces MS Coff objects when targeting windows

    The -m32mscoff switch is deprecated and -m32 should be used in its place. A new switch -m32omf has been added to produce code for OMF. Use of this switch is discouraged because OMF will soon be unsupported.

  8. Ignore unittests in non-root modules

    This mainly means that unittests inside templates are now only instantiated if the module lexically declaring the template is one of the root modules.

    E.g., compiling some project with -unittest does NOT compile and later run any unittests in instantiations of templates declared in other libraries anymore.

    Declaring unittests inside templates is considered an anti-pattern. In almost all cases, the unittests don't depend on the template parameters, but instantiate the template with fixed arguments (e.g., Nullable!T unittests instantiating Nullable!int), so compiling and running identical tests for each template instantiation is hardly desirable. But adding a unittest right below some function being tested is arguably good for locality, so unittests end up inside templates.

    To make sure a template's unittests are run, it should be instantiated in the same module, e.g., some module-level unittest.

    This change paved the way for a more straight-forward template emission algorithm without -unittest special cases, showing significant compile-time improvements for some projects. -allinst now emits all templates instantiated in root modules.

  9. main can now return type noreturn and supports return inference

    If main never returns (due to an infinite loop or always throwing an exception), it can now be declared as returning noreturn. See

    If main is declared with auto, the inferred return type must be one of void, int and noreturn.

  10. Falling through switch cases is now an error

    This was deprectated in 2.072.2 because it is a common mistake to forget a break statement at the end of a switch case. The deprecation warning has now been turned into an error.

    If you intend to let control flow continue from one case to the next, use the goto case; statement.

    void parseNumFmt(char c, out int base, out bool uppercase)
        switch (c)
            case 'B': // fallthrough allowed, case has no code
            case 'b':
                base = 2;
                // error, accidental fallthrough to case 'X'
            case 'X':
                uppercase = true;
                goto case; // allowed, explicit fallthrough
            case 'x':
                base = 16;
  11. Throw expression as proposed by DIP 1034 have been implemented

    Prior to this release, throw was considered as a statement and hence was not allowed to appear inside of other expressions. This was cumbersome e.g. when wanting to throw an expression from a lambda:

    SumType!(int, string) result;
        (int num)       => writeln("Found ", num),
        // (string err) => throw new Exception(err)    // expression expected
        (string err)     { throw new Exception(err); } // ok, introduces an explicit body

    throw is now treated as an expression as specified by DIP 1034 [1], causing it to become more flexible and easier to use.

    SumType!(int, string) result;
        (int num)    => writeln("Found ", num),
        (string err) => throw new Exception(err)   // works


  12. Added __traits(initSymbol) to obtain aggregate initializers

    Using __traits(initSymbol, A) where A is either a class or a struct will yield a const(void)[] that holds the initial state of an instance of A. The slice either points to the initializer symbol of A or null if A is zero-initialised - matching the behaviour of TypeInfo.initializer().

    This traits can e.g. be used to initialize malloc'ed class instances without relying on TypeInfo:

    class C
        int i = 4;
    void main()
        const void[] initSym = __traits(initSymbol, C);
        void* ptr = malloc(initSym.length);
        scope (exit) free(ptr);
        ptr[0..initSym.length] = initSym[];
        C c = cast(C) ptr;
        assert(c.i == 4);

Runtime changes

  1. Add support for OpenBSD ioctls

    Support OpenBSD ioctls as found in OpenBSD's /usr/include/sys/filio.h, /usr/include/sys/ioccom.h, /usr/include/sys/ioctl.h, and /usr/include/sys/ttycom.h.

  2. Add support for @safe class opEquals

    object.opEquals is now @safe if the static types being compared provide an opEquals method that is also @safe.

Library changes

  1. Move checkedint out of experimental.

    std.experimental.checkedint is now std.checkedint. The old name is still available and publicly imports the new one, and is also deprecated.

  2. chunkBy @safe with forward ranges and splitWhen fully @safe

    std.algorithm.iteration.splitWhen now infers safety from the underlying range, as most Phobos ranges do. std.algorithm.iteration.chunkBy also does that when instantiated with a forward range. Inference for chunkBy with a non-forward input range is not yet implemented, though.

    @safe void fun()
        import std.algorithm;
        // Grouping by particular attribute of each element:
        auto data = [
            [1, 1],
            [1, 2],
            [2, 2],
            [2, 3]
        auto r1 = data.chunkBy!((a,b) => a[0] == b[0]);
            [[1, 1], [1, 2]],
            [[2, 2], [2, 3]]
        auto r2 = [1, 2, 3, 4, 5, 6, 7, 8, 9].splitWhen!((x, y) => ((x*y) % 3) > 0);
            [2, 3, 4],
            [5, 6, 7],
            [8, 9]
  3. std.csv can now optionally handle csv files with variable number of columns.

    By default std.csv will throw if the number of columns on a line is not equal to the number of columns of the first line. To allow, or disallow, a variable amount of columns a bool can be passed to all overloads of the csvReader function as shown below.

    string text = "76,26,22\n1,2\n3,4,5,6";
    auto records = text.csvReader!int(',', '"', true);
        [76, 26, 22],
        [1, 2],
        [3, 4, 5, 6]
  4. Change default log level for std.experimental.logger to LogLevel.warning

    std.experimental.logger.core.sharedLog now returns by default a logger with its log level set to LogLevel.warning.

  5. accepts std.typecons tuples

    The previous version of to did not support conversions to std.typecons tuples. Starting with this release, tuples are now supported as highlighted in the following example:

    void main()
        import std.conv : to;
        import std.typecons : Tuple;
        auto data = ["10", "20", "30"];
        auto a3 =!(int[3]);                // accepted in previous and current versions
        auto t3 =!(Tuple!(int, int, int)); // rejected in past versions, accepted now

Dub changes

  1. Windows: Copy PDB files to targetPath, alongside executable/DLL

    If the default PDB file is generated when linking an executable or DLL (e.g., no /PDB:my\path.pdb lflag), it is now copied to the target directory too.

List of all bug fixes and enhancements in D 2.099.0:

DMD Compiler regression fixes

  1. Bugzilla 17635: [REG 2.066.0] cannot convert unique immutable(int)** to immutable
  2. Bugzilla 21367: Nameless union propagates copy constructors and destructors over all members
  3. Bugzilla 21538: Overriding with more attributes on delegate parameter is allowed
  4. Bugzilla 21674: [REG v2.086] alias this triggers wrong deprecation message on function call
  5. Bugzilla 21719: [REG 2.072] "auto" methods of classes do not infer attributes correctly.
  6. Bugzilla 22130: [REG2.080.1][DIP1000] pure factory functions stopped working
  7. Bugzilla 22163: [REG 2.094.0] wrong code with static float array and delegate accessing it
  8. Bugzilla 22226: [REG 2.095.1] __ctfe + function call in conditional expression used to initialize struct member in constructor causes ICE
  9. Bugzilla 22254: Template instantiated twice results in different immutable qualifier
  10. Bugzilla 22512: importC: incomplete array type must have initializer
  11. Bugzilla 22659: [REG master] Error: declaration '(S[2] arr = __error__;)' is not yet implemented in CTFE
  12. Bugzilla 22676: fullyQualifiedName fails to compile with 2.098.1 relese -- there is some issue with call to __traits(isScalar ..
  13. Bugzilla 22705: importC: forward reference to struct typedef gives struct already exists
  14. Bugzilla 22714: ICE: Assertion failure in ClassDeclaration::isBaseOf
  15. Bugzilla 22730: master: "dmd -i" doesn't include unit tests from imported modules
  16. Bugzilla 22738: std.file.tempDir adds an addition / even when it already has one
  17. Bugzilla 22761: [REG 2.099] importC: Error: redeclaration with different type
  18. Bugzilla 22780: [REG 2.090] variable reference to scope class must be scope
  19. Bugzilla 22804: [REG 2.099] compiling multiple files without linking produces broken object files
  20. Bugzilla 22816: [REG 2.099] Parser reads files with other extensions
  21. Bugzilla 22817: [REG 2.099] Missing file gives misleading error message
  22. Bugzilla 22826: [REG 2.098] #line accepts importC linemarker flags

DMD Compiler bug fixes

  1. Bugzilla 2: Hook up new dmd command line arguments
  2. Bugzilla 3: Finish or remove MatchExp::toElem
  3. Bugzilla 3818: Generic error message for wrong foreach
  4. Bugzilla 8346: Literals 00 - 07 results in odd errors when used with UFCS
  5. Bugzilla 10584: Unhelpful error default constructing nested class
  6. Bugzilla 15711: Incorrect type inferring of [char]/string when passed via recursive template, extracting it from a structure field
  7. Bugzilla 15804: missing UDAs on nested struct template
  8. Bugzilla 17870: Can't alias a mix of parent and child class members
  9. Bugzilla 17977: [DIP1000] destructor allows escaping reference to a temporary struct instance
  10. Bugzilla 18960: Function parameter requires name with default value
  11. Bugzilla 19320: -cov and -O yield variable used before set
  12. Bugzilla 19482: attributes incorrectly applied to static foreach local variables
  13. Bugzilla 19873: function should be by default @system even with -preview=dip1000
  14. Bugzilla 20023: Separate compilation breaks dip1000 / dip1008 @safety
  15. Bugzilla 20691: Converting scope static array to scope dynamic array should be error
  16. Bugzilla 20777: User defined type as enum base type fails to compile.
  17. Bugzilla 20904: dip1000 implicit conversion delegates error
  18. Bugzilla 21431: Incorrect maximum and actual number of cases in a switch case range is reported
  19. Bugzilla 21844: makedeps option adds spurious/incorrect dependency
  20. Bugzilla 21969: importC: Error: bit fields are not supported
  21. Bugzilla 22124: Corrupted closure when compiling with -preview=dip1000
  22. Bugzilla 22127: compiler assertion failure parser on UDA and function literal
  23. Bugzilla 22137: -preview=dip1000 enables visibility checks for tupleof
  24. Bugzilla 22139: Compiler special cases object.dup when compiling with -preview=dip1000
  25. Bugzilla 22233: importC: (identifier)() incorrectly parsed as a cast-expression
  26. Bugzilla 22236: sizeof an empty C struct should be 0, not 1
  27. Bugzilla 22245: importC: Error: found . when expecting )
  28. Bugzilla 22267: ImportC: typedef-ed variable initialization with RHS in parenthesis doesn't parse
  29. Bugzilla 22277: removing strongly pure function calls is an incorrect optimization
  30. Bugzilla 22283: -preview=in -inline leads to strange error inside object.d
  31. Bugzilla 22285: markdown tables are not parsed correctly
  32. Bugzilla 22287: ambiguous virtual function for extern(C++) under Windows
  33. Bugzilla 22298: [DIP1000] Nested function's scope parameters can be assigned to variables in enclosing function
  34. Bugzilla 22305: ImportC: #pragma STDC FENV_ACCESS is not supported
  35. Bugzilla 22311: dmd slice length is wrong on DWARF
  36. Bugzilla 22323: Link error for virtual destructor of C++ class in DLL
  37. Bugzilla 22339: importC: error message with character literal reports as integer instead of character literal.
  38. Bugzilla 22342: importC: Error: function 'func()' is not callable using argument types '(int)'
  39. Bugzilla 22344: ImportC: overloading of functions is not allowed
  40. Bugzilla 22356: Can't mixin the return type of a function
  41. Bugzilla 22361: Failed import gives misleading error message
  42. Bugzilla 22365: Compiler crash: tcs.body_ null in StatementSemanticVisitor.visit(TryCatchStatement) in semantic3 pass (dmd/statementsem.d:3956)
  43. Bugzilla 22366: [dip1000] scope variable can be assigned to associative array
  44. Bugzilla 22372: Loop index incorrectly optimised out for -release -O
  45. Bugzilla 22387: Noreturn init loses type qualifiers
  46. Bugzilla 22401: importC: Error: cannot implicitly convert expression of type 'const(int[1])' to 'const(int*)'
  47. Bugzilla 22415: importC: Deprecation: switch case fallthrough - use 'goto case;' if intended
  48. Bugzilla 22421: static foreach introduces semantic difference between indexing and iteration variable
  49. Bugzilla 22467: DWARF: wchar_t reports wrong DECL attributes
  50. Bugzilla 22510: Structs with copy constructor can not be heap allocated with default constructor
  51. Bugzilla 22515: Aggregate definition with qualifiers has inconsistencies between structs and classes
  52. Bugzilla 22517: [REG 2.093][ICE] Bus error at dmd/lexer.d:398
  53. Bugzilla 22527: Casting out-of-range floating point value to signed integer overflows
  54. Bugzilla 22533: OpenBSD: Use correct size_t compat for 32-bit
  55. Bugzilla 22535: ImportC: gcc/clang math intrinsics are rejected.
  56. Bugzilla 22553: ImportC: undefined identifier __uint128_t
  57. Bugzilla 22566: Error: unknown architecture feature 4+avx for -target
  58. Bugzilla 22573: DMD compiler errors on Illumos/Solaris
  59. Bugzilla 22590: importC: static functions have no debug information generated for them
  60. Bugzilla 22598: importC: Add support for __extension__ keyword
  61. Bugzilla 22607: ImportC misses some float values ending with f
  62. Bugzilla 22619: Missing inout substitution for __copytmp temporaries caused by copy ctors
  63. Bugzilla 22623: ImportC: typedef'd struct definition tag not put in symbol table
  64. Bugzilla 22624: ImportC: struct members in static initializer misaligned following bit field
  65. Bugzilla 22625: ImportC: original name of typedefed struct not visible in D when compiling separately
  66. Bugzilla 22632: Crash happens when CTFE compares an associative array to null using ==
  67. Bugzilla 22634: assert for too many symbols should be error
  68. Bugzilla 22655: Disassembler assertion on rdtsc
  69. Bugzilla 22656: SSE2 instructions have inconsistent layouts in the disassembler output
  70. Bugzilla 22665: ImportC: qualified enum values should be of enum type on the D side, not int
  71. Bugzilla 22666: ImportC: Error: attributes should be specified before the function definition
  72. Bugzilla 22668: Deprecation when a deprecated method overrides another deprecated method
  73. Bugzilla 22685: Template function instantiated with lambda and overload is nested incorrectly
  74. Bugzilla 22686: ICE: dmd segfaults on invalid member reference in static function
  75. Bugzilla 22698: ImportC: nested struct tag stored in wrong scope
  76. Bugzilla 22699: importC: assignment cannot be used as a condition
  77. Bugzilla 22703: importC: C++11 unscoped enums with underlying type rejects some C types.
  78. Bugzilla 22708: switch statement with an undefined symbol results in many errors
  79. Bugzilla 22709: [dip1000] slice of static array can be escaped in @safe using ref arguments
  80. Bugzilla 22710: CTFE on bitfields does not account for field width
  81. Bugzilla 22713: ImportC: op= not correctly implemented for bit fields
  82. Bugzilla 22717: object.TypeInfo_Struct.equals swaps lhs and rhs parameters
  83. Bugzilla 22725: ImportC: segfault when compiling with -H
  84. Bugzilla 22726: ImportC: typedefs of tagged enums fail to compile
  85. Bugzilla 22727: ImportC: support for __stdcall and __fastcall is necessary for 32-bit Windows builds
  86. Bugzilla 22734: importC: typedef anonymous enum members not available when used from D
  87. Bugzilla 22749: importC: C11 does not allow taking the address of a bit-field
  88. Bugzilla 22756: ImportC: no __builtin_offsetof
  89. Bugzilla 22757: importC: typedef causes forward reference error
  90. Bugzilla 22758: ImportC: parenthesized expression confused with cast-expression

DMD Compiler enhancements

  1. Bugzilla 5096: More readable unpaired brace error
  2. Bugzilla 7925: extern(C++) delegates?
  3. Bugzilla 11008: Allow -main switch even if user-defined main function exists
  4. Bugzilla 20340: [betterC] -main inserts D main function even with betterC
  5. Bugzilla 20616: Error: undefined identifier __dollar
  6. Bugzilla 21160: DWARF: DW_AT_main_subprogram should be emitted for _Dmain
  7. Bugzilla 22113: Allow noreturn as a type for main function
  8. Bugzilla 22198: Compile time bounds checking for static arrays
  9. Bugzilla 22278: [Conditional Compilation] there should be in and out flags
  10. Bugzilla 22291: __traits(arguments) to return a tuple of the function arguments
  11. Bugzilla 22353: Header generation is producing trailing whitespace on attribute declarations
  12. Bugzilla 22354: Header generation is producing trailing whitespace on enum declarations
  13. Bugzilla 22355: LLD fallback for mscoff is broken in the presence of some old VS versions
  14. Bugzilla 22377: Show location for Windows extern(C++) mangling ICE
  15. Bugzilla 22379: OpenBSD: link -lexecinfo to get backtrace symbols
  16. Bugzilla 22419: Allow return type inference for main
  17. Bugzilla 22423: DWARF DW_TAG_subprogram should generate DW_AT_decl_column
  18. Bugzilla 22426: DWARF DW_AT_noreturn should be present when function is noreturn
  19. Bugzilla 22459: DWARF: delegate type names should be distinguishable
  20. Bugzilla 22468: DWARF: dchar type is missing encoding
  21. Bugzilla 22469: DWARF: some debug info types are named wrongly
  22. Bugzilla 22471: DWARF: generated main is not marked as DW_AT_artificial
  23. Bugzilla 22494: Search paths for dmd.conf missing from dmd man page
  24. Bugzilla 22508: DWARF: associative arrays should report qualified name instead of _AArray__
  25. Bugzilla 22519: [dip1000] cannot take address of ref return
  26. Bugzilla 22541: DIP1000: Resolve ambiguity of ref-return-scope parameters
  27. Bugzilla 22631: ImportC: support C++11 unscoped enums with underlying type
  28. Bugzilla 22672: Allow casting a ValueSeq to a compatible TypeTuple
  29. Bugzilla 22733: hdrgen generates inconsistent order of STC attributes for ~this()
  30. Bugzilla 22746: Functions that throws marked as nothrow produces bad error
  31. Bugzilla 22753: Deprecation message for import module shouldn't produce hifen when no message
  32. Bugzilla 22754: Header generator shouldn't generate trailing whitespace on visibility declaration

Phobos bug fixes

  1. Bugzilla 17037: std.concurrency has random segfaults
  2. Bugzilla 19544: Can't call inputRangeObject on ranges not supported by moveFront
  3. Bugzilla 20554: std.algorithm.searching.all 's static assert produces a garbled error message
  4. Bugzilla 21022: std.range.only does not work with const
  5. Bugzilla 21457: std.functional.partial ignores function overloads
  6. Bugzilla 22105: std.container.array.Array.length setter creates values of init-less types
  7. Bugzilla 22185: std.array.array() doesn't handle throwing element copying
  8. Bugzilla 22249: std.experimental.checkedint: Warn.onLowerBound does not compile
  9. Bugzilla 22255: JSONValue.opBinaryRight!"in" is const
  10. Bugzilla 22297: Behavior of minElement and maxElement with empty range is undocumented
  11. Bugzilla 22301: Only use 'from' if a packet was actually received
  12. Bugzilla 22325: ReplaceType fails on templated type instantiated with void-returning function
  13. Bugzilla 22359: joiner over an empty forward range object liable to segfault
  14. Bugzilla 22364: Unreachable warning for collectException[Msg] with noreturn value
  15. Bugzilla 22368: has[Unshared]Aliasing fails to instantiate for noreturn
  16. Bugzilla 22369: Unreachable statements in std.concurrency with noreturn values / callbacks
  17. Bugzilla 22383: Array of bottom types not recognized as a range
  18. Bugzilla 22384: castSwitch confused by noreturn handlers
  19. Bugzilla 22386: Unreachable warning for assertThrown with noreturn value
  20. Bugzilla 22394: std.getopt cannot handle "-"
  21. Bugzilla 22408: Multiple issues in AllImplicitConversionTargets
  22. Bugzilla 22414: clamp(a, b, c) should always return typeof(a)
  23. Bugzilla 22561: only().joiner fails with immutable element type
  24. Bugzilla 22572: Cannot define SumType over immutable struct with Nullable
  25. Bugzilla 22608: RandomAccessInfinite is not a valid random-access range
  26. Bugzilla 22647: [std.variant.Variant] Cannot compare types compliant with null comparison with 'null'
  27. Bugzilla 22648: [std.variant.Variant] Incorrectly written unittests
  28. Bugzilla 22673: .array of a range with length preallocates without checking if the length was lying or not.
  29. Bugzilla 22683: core.math.rndtonl can't be linked
  30. Bugzilla 22695: std.traits.isBuiltinType is false for typeof(null)
  31. Bugzilla 22704: Linker error when running the public unittests
  32. Bugzilla 22838: std.bitmanip.BitArray.count() reads beyond data when data size is integer size_t multiple

Phobos enhancements

  1. Bugzilla 13551: for std.typecons tuples too
  2. Bugzilla 17488: Platform-inconsistent behavior from getTempDir()
  3. Bugzilla 18051: missing enum support in formattedRead/unformatValue
  4. Bugzilla 21507: SysTime.toISOExtString is unusable for logging or consistent filename creation
  5. Bugzilla 22117: Can't store scope pointer in a SumType
  6. Bugzilla 22340: totalCPUs may not return accurate number of CPUs
  7. Bugzilla 22370: std.concurrency.spawn* should accept noreturn callables
  8. Bugzilla 22511: Nullable is not copyable when templated type has elaborate copy ctor
  9. Bugzilla 22532: std.experimental.logger Change default log level to LogLevel.warning, or
  10. Bugzilla 22701: std.typecons.apply needlessly checks if the predicate is callable

Druntime regression fixes

  1. Bugzilla 22136: [REG 2.097.1] hashOf failed to compile because of different inheritance order

Druntime bug fixes

  1. Bugzilla 22328: Specific D types are used instead of Windows type aliases
  2. Bugzilla 22336: core.lifetime.move doesn't work with betterC on elaborate non zero structs
  3. Bugzilla 22523: DRuntime options passed after -- affect current process
  4. Bugzilla 22552: moveEmplace wipes context pointer of nested struct contained in non-nested struct
  5. Bugzilla 22630: It is possible for VS to be installed and providing VC directory without VC libraries being installed
  6. Bugzilla 22702: druntime not compliant with D spec re getLinkage
  7. Bugzilla 22721: importC: some gnu builtins are rejected
  8. Bugzilla 22735: __builtins.di does not implement __builtin_bswap64 correctly
  9. Bugzilla 22741: importC: Error: bswap isn’t a template
  10. Bugzilla 22744: ImportC: builtins defined in __builtins.di cause undefined symbol linker errors.
  11. Bugzilla 22777: stat struct in assumes CRuntime_DigitalMars
  12. Bugzilla 22779: druntime: Calling __delete with null pointer-to-struct segfaults

Druntime enhancements

  1. Bugzilla 14892: -profile=gc doesn't account for GC API allocations
  2. Bugzilla 20936: core.sync.rwmutex should have shared overloads (and make it usable in @safe code)
  3. Bugzilla 21005: Speed up hashOf for associative arrays
  4. Bugzilla 21014: aa.byKeyValue, byKey, byValue very under-documented
  5. Bugzilla 22378: OpenBSD: execinfo.d and unistd.d aren't being installed
  6. Bugzilla 22669: OpenBSD: Sync socket.d
  7. Bugzilla 22670: Support *BSD kqueue-backed API-compatible inotify shim library bug fixes

  1. Bugzilla 19136: is expressions don't work as documented
  2. Bugzilla 21717: [Oh No! Page Not Found]
  3. Bugzilla 22064: Missing documentation page for phobos core.builtins
  4. Bugzilla 22281: unreadable quotes in the upcoming 2.099 changelog
  5. Bugzilla 22363: Wrong link in for "Garbage Collection"
  6. Bugzilla 22417: Slice assignment operator overloading example is incorrect
  7. Bugzilla 22504: spec/type.html: 6.1 Basic Data Types: Backslash missing in default value for {,d,w}char
  8. Bugzilla 22518: [dip1000] return without scope/ref not specified
  9. Bugzilla 22544: [spec] C++ and Objective-C are not single tokens
  10. Bugzilla 22692: Underground Rekordz link is dead
  11. Bugzilla 22711: Effect of template UDAs on instance members is undocumented enhancements

  1. Bugzilla 22425: Documentation on implicit conversion of arrays is incomplete
  2. Bugzilla 22431: Add OpenBSD to Third-party downloads list

Installer enhancements

  1. Bugzilla 18362: Build dmd with LTO and PGO
  2. Bugzilla 22078: Recognize ARM64 as architecture

Contributors to this release (100)

A huge thanks goes to all the awesome people who made this release possible.

previous version: 2.098.1 – next version: 2.099.1