Merge stable (#21048)

* bump VERSION to v2.110.0

* purge changelog

* bump VERSION to v2.111.0-beta.1

* Accept __rvalue attribute on ref functions; which will force the result to be treated as __rvalue. (#20946)

This is essential to implement `move`, `forward`, etc.

* memoryerror.d: Fix AnySupported version condition (#20983)

* Fix #20982 - wrong line number in iasmgcc (#20993)

* Move genCfunc to cxxfrontend (#20992)

* druntime: Fix compilation of rt.cover on Android (#21015)

* Expose SourceLoc to C++ interface (#20980)

* [stable] C++ header fixes for declaration, expression, and typinf (#21016)

Seen either from compilation errors or missing symbols at link time.

* C++ headers: Add 3 Declaration bitfield setters/getters required by LDC

* druntime: Add module declaration to rt.invariant, to prevent conflicts with user-provided invariant.d (#21017)

* Fix #21020 - Indexing a *cast* AA yields no lvalue anymore (#21029)

* Add C++23 to CppStdRevision enum (#21043)

* Improve UFCS/property error message (#21046)

---------

Co-authored-by: Manu Evans <turkeyman@gmail.com>
Co-authored-by: Martin Kinkelin <kinke@users.noreply.github.com>
Co-authored-by: Iain Buclaw <ibuclaw@gdcproject.org>
Co-authored-by: Martin Kinkelin <noone@nowhere.com>
This commit is contained in:
Dennis 2025-03-21 15:48:21 +01:00 committed by GitHub
parent 803a44a347
commit d5db322fce
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
32 changed files with 160 additions and 92 deletions

View file

@ -1 +1 @@
v2.110.0-rc.1
v2.111.0-beta.1

View file

@ -1,15 +0,0 @@
Copying from `const(void)[]` to `void[]` is disallowed with `-preview=fixImmutableConv`
If `const(void)[]` data contains tail `const` pointers, copying to `void[]`
can subsequently violate `const` data:
---
void f(int*[] a, const int*[] b)
{
void[] va = a;
const void[] vb = b;
va[] = vb[]; // fills `a` with pointers to const
*a[0] = 0; // const data mutated
}
---
Copying `vb` data to `va` is no longer allowed with the
`-preview=fixImmutableConv` switch.

View file

@ -0,0 +1,4 @@
The compiler now accepts `-extern-std=c++23`
The compiler now accepts c++23 as a supported standard for `-extern-std=`.
Currently this only changes the value of `__traits(getTargetInfo, "cppStd")`.

View file

@ -1,12 +0,0 @@
Import expressions are now treated as hex strings
While [Import expressions](https://dlang.org/spec/expression.html#import_expressions) are typed as `string`, they are also used to embed binary files.
By treating them the same as [hex strings](https://dlang.org/spec/lex.html#hex_strings), they implicitly convert to arrays of integral types.
---
// Formerly, a cast was required:
immutable ubyte[] iconImg = cast(immutable ubyte[]) import("icon.png");
// Now, it implicitly converts to integral arrays:
immutable ubyte[] iconImg = import("icon.png");
---

View file

@ -1,5 +0,0 @@
New trait `isCOMClass` to detect if a type is a COM class
A Component Object Model (COM) class inherits from a possibly user-defined interface named ``IUnknown``.
To detect this during compilation, use the trait ``__traits(isCOMClass, Type)``.
During runtime, use the ``TypeInfo_Class`` flag.

View file

@ -1,15 +0,0 @@
For type `bool`, values other than 0 or 1 are not `@safe`
The spec [was updated](https://dlang.org/spec/type.html#bool)
(for 2.109) so that only 0 and 1 are
[safe values](https://dlang.org/spec/function.html#safe-values)
for `bool`. This means that reading a `bool` value whose underlying byte representation
has other bits set is implementation-defined and should be avoided.
Consequently the following are deprecated in `@safe` code:
* initialization of `bool` variables with `= void` (since 2.109)
* Reading a `bool` field from a union (since 2.109)
* Runtime casting a dynamic array to a `bool` dynamic array type
* Runtime casting a `bool` dynamic array to a tail mutable dynamic array type
* Casting a pointer to a `bool` pointer type
* Casting a `bool` pointer to a tail mutable pointer type

View file

@ -89,7 +89,7 @@ Symbol* getRtlsym(RTLSYM i) @trusted
case RTLSYM.DARRAYP: symbolz(ps,FL.func,FREGSAVED,"_d_arrayboundsp", SFLexit, t); break;
case RTLSYM.DARRAY_SLICEP: symbolz(ps,FL.func,FREGSAVED,"_d_arraybounds_slicep", SFLexit, t); break;
case RTLSYM.DARRAY_INDEXP: symbolz(ps,FL.func,FREGSAVED,"_d_arraybounds_indexp", SFLexit, t); break;
case RTLSYM.DINVARIANT: symbolz(ps,FL.func,FREGSAVED,"_D9invariant12_d_invariantFC6ObjectZv", 0, tsdlib); break;
case RTLSYM.DINVARIANT: symbolz(ps,FL.func,FREGSAVED,"_D2rt10invariant_12_d_invariantFC6ObjectZv", 0, tsdlib); break;
case RTLSYM.MEMCPY: symbolz(ps,FL.func,FREGSAVED,"memcpy", 0, t); break;
case RTLSYM.MEMSET8: symbolz(ps,FL.func,FREGSAVED,"memset", 0, t); break;
case RTLSYM.MEMSET16: symbolz(ps,FL.func,FREGSAVED,"_memset16", 0, t); break;

View file

@ -359,6 +359,8 @@ dmd -cov -unittest myprog.d
Sets `__traits(getTargetInfo, \"cppStd\")` to `201703`)
$(LI $(I c++20): Use C++20 name mangling,
Sets `__traits(getTargetInfo, \"cppStd\")` to `202002`)
$(LI $(I c++23): Use C++23 name mangling,
Sets `__traits(getTargetInfo, \"cppStd\")` to `202302`)
)",
),
Option("extern-std=[h|help|?]",
@ -1122,6 +1124,7 @@ struct CLIUsage
=c++14 Sets `__traits(getTargetInfo, \"cppStd\")` to `201402`
=c++17 Sets `__traits(getTargetInfo, \"cppStd\")` to `201703`
=c++20 Sets `__traits(getTargetInfo, \"cppStd\")` to `202002`
=c++23 Sets `__traits(getTargetInfo, \"cppStd\")` to `202302`
";
/// Options supported by -HC

View file

@ -16,6 +16,7 @@ import dmd.astenums;
import dmd.attrib;
import dmd.common.outbuffer : OutBuffer;
import dmd.dclass : ClassDeclaration;
import dmd.declaration : TypeInfoDeclaration;
import dmd.denum : EnumDeclaration;
import dmd.dmodule /*: Module*/;
import dmd.dscope : Scope;
@ -276,6 +277,19 @@ bool fill(StructDeclaration sd, Loc loc,
return dmd.expressionsem.fill(sd, loc, elements, ctorinit);
}
/***********************************************************
* func.d
*/
FuncDeclaration genCfunc(Parameters* fparams, Type treturn, const(char)* name, StorageClass stc = STC.none)
{
return FuncDeclaration.genCfunc(fparams, treturn, name, cast(STC) stc);
}
FuncDeclaration genCfunc(Parameters* fparams, Type treturn, Identifier id, StorageClass stc = STC.none)
{
return FuncDeclaration.genCfunc(fparams, treturn, id, cast(STC) stc);
}
/***********************************************************
* funcsem.d
*/
@ -715,6 +729,18 @@ bool builtinTypeInfo(Type t)
return dmd.typinf.builtinTypeInfo(t);
}
Type makeNakedAssociativeArray(TypeAArray t)
{
import dmd.typinf;
return dmd.typinf.makeNakedAssociativeArray(t);
}
TypeInfoDeclaration getTypeInfoAssocArrayDeclaration(TypeAArray t, Scope* sc)
{
import dmd.typinf;
return dmd.typinf.getTypeInfoAssocArrayDeclaration(t, sc);
}
version (IN_LLVM)
{
/***********************************************************

View file

@ -37,6 +37,8 @@ namespace dmd
bool checkClosure(FuncDeclaration* fd);
MATCH leastAsSpecialized(FuncDeclaration *f, FuncDeclaration *g, Identifiers *names);
PURE isPure(FuncDeclaration *f);
FuncDeclaration *genCfunc(Parameters *args, Type *treturn, const char *name, StorageClass stc=0);
FuncDeclaration *genCfunc(Parameters *args, Type *treturn, Identifier *id, StorageClass stc=0);
}
//enum STC : ulong from astenums.d:
@ -126,6 +128,10 @@ public:
short inuse; // used to detect cycles
uint8_t bitFields;
LINK _linkage() const;
LINK _linkage(LINK v);
bool noUnderscore() const;
const char *kind() const override;
uinteger_t size(Loc loc) override final;
@ -726,9 +732,6 @@ public:
bool hasNestedFrameRefs();
ParameterList getParameterList();
static FuncDeclaration *genCfunc(Parameters *args, Type *treturn, const char *name, StorageClass stc=0);
static FuncDeclaration *genCfunc(Parameters *args, Type *treturn, Identifier *id, StorageClass stc=0);
virtual FuncDeclaration *toAliasFunc() { return this; }
void accept(Visitor *v) override { v->visit(this); }
};

View file

@ -3632,6 +3632,7 @@ extern (C++) final class CastExp : UnaExp
if (rvalue || !e1.isLvalue())
return false;
return (to.ty == Tsarray && (e1.type.ty == Tvector || e1.type.ty == Tsarray)) ||
(to.ty == Taarray && e1.type.ty == Taarray) ||
e1.type.mutableOf.unSharedOf().equals(to.mutableOf().unSharedOf());
}

View file

@ -40,6 +40,7 @@ class OverloadSet;
class StringExp;
class InterpExp;
class LoweredAssignExp;
class StaticForeach;
#ifdef IN_GCC
typedef union tree_node Symbol;
#else

View file

@ -377,6 +377,22 @@ enum class MessageStyle : uint8_t
sarif = 2u,
};
struct SourceLoc final
{
_d_dynamicArray< const char > filename;
uint32_t line;
uint32_t column;
uint32_t fileOffset;
const char* toChars(bool showColumns = Loc::showColumns, MessageStyle messageStyle = Loc::messageStyle) const;
SourceLoc() :
filename(),
line(),
column(),
fileOffset()
{
}
};
struct Loc final
{
private:
@ -390,7 +406,8 @@ public:
uint32_t linnum() const;
const char* filename() const;
const char* toChars(bool showColumns = Loc::showColumns, MessageStyle messageStyle = Loc::messageStyle) const;
bool equals(const Loc& loc) const;
SourceLoc toSourceLoc() const;
bool equals(Loc loc) const;
Loc() :
index(0u)
{
@ -4052,8 +4069,6 @@ public:
bool needsClosure();
bool hasNestedFrameRefs();
ParameterList getParameterList();
static FuncDeclaration* genCfunc(Array<Parameter* >* fparams, Type* treturn, const char* name, STC stc = (STC)0LLU);
static FuncDeclaration* genCfunc(Array<Parameter* >* fparams, Type* treturn, Identifier* id, STC stc = (STC)0LLU);
virtual FuncDeclaration* toAliasFunc();
void accept(Visitor* v) override;
};
@ -6219,6 +6234,7 @@ enum class CppStdRevision : uint32_t
cpp14 = 201402u,
cpp17 = 201703u,
cpp20 = 202002u,
cpp23 = 202302u,
};
enum class CHECKENABLE : uint8_t

View file

@ -1004,12 +1004,12 @@ extern (C++) class FuncDeclaration : Declaration
/**********************************
* Generate a FuncDeclaration for a runtime library function.
*/
static FuncDeclaration genCfunc(Parameters* fparams, Type treturn, const(char)* name, STC stc = STC.none)
extern(D) static FuncDeclaration genCfunc(Parameters* fparams, Type treturn, const(char)* name, STC stc = STC.none)
{
return genCfunc(fparams, treturn, Identifier.idPool(name[0 .. strlen(name)]), stc);
}
static FuncDeclaration genCfunc(Parameters* fparams, Type treturn, Identifier id, STC stc = STC.none)
extern(D) static FuncDeclaration genCfunc(Parameters* fparams, Type treturn, Identifier id, STC stc = STC.none)
{
FuncDeclaration fd;
TypeFunction tf;

View file

@ -62,6 +62,7 @@ enum CppStdRevision : uint
cpp14 = 2014_02,
cpp17 = 2017_03,
cpp20 = 2020_02,
cpp23 = 2023_02,
}
/// Trivalent boolean to represent the state of a `revert`able change

View file

@ -73,7 +73,8 @@ enum CppStdRevision
CppStdRevisionCpp11 = 201103,
CppStdRevisionCpp14 = 201402,
CppStdRevisionCpp17 = 201703,
CppStdRevisionCpp20 = 202002
CppStdRevisionCpp20 = 202002,
CppStdRevisionCpp23 = 202302,
};
/// Trivalent boolean to represent the state of a `revert`able change
@ -413,6 +414,14 @@ typedef unsigned long long uinteger_t;
#endif
// file location
struct SourceLoc
{
DString filename;
uint32_t line;
uint32_t column;
uint32_t fileOffset;
};
struct Loc
{
private:
@ -438,6 +447,7 @@ public:
uint32_t charnum() const;
uint32_t linnum() const;
const char *filename() const;
SourceLoc toSourceLoc() const;
const char *toChars(
bool showColumns = Loc::showColumns,

View file

@ -55,7 +55,8 @@ public Statement gccAsmSemantic(GccAsmStatement s, Scope* sc)
*ptoklist = null;
}
p.token = *toklist;
p.scanloc = s.loc;
p.baseLoc.startLine = s.loc.linnum;
p.linnum = s.loc.linnum;
// Parse the gcc asm statement.
const errors = global.errors;

View file

@ -133,6 +133,12 @@ nothrow:
return this.index - locFileTable[i].startIndex;
}
/// Returns: this location as a SourceLoc
extern (C++) SourceLoc toSourceLoc() const @nogc @safe
{
return SourceLoc(this);
}
/**
* Checks for equivalence by comparing the filename contents (not the pointer) and character location.
*
@ -140,7 +146,7 @@ nothrow:
* - Uses case-insensitive comparison on Windows
* - Ignores `charnum` if `Columns` is false.
*/
extern (C++) bool equals(ref const(Loc) loc) const
extern (C++) bool equals(Loc loc) const
{
SourceLoc lhs = SourceLoc(this);
SourceLoc rhs = SourceLoc(loc);

View file

@ -1143,6 +1143,9 @@ bool parseCommandLine(const ref Strings arguments, const size_t argc, ref Param
case "c++20":
params.cplusplus = CppStdRevision.cpp20;
break;
case "c++23":
params.cplusplus = CppStdRevision.cpp23;
break;
default:
error("switch `%s` is invalid", p);
params.help.externStd = true;

View file

@ -3444,8 +3444,16 @@ Expression getProperty(Type t, Scope* scope_, Loc loc, Identifier ident, int fla
auto s2 = scope_.search_correct(ident);
// UFCS
if (s2 && s2.isFuncDeclaration)
errorSupplemental(loc, "did you mean %s `%s`?",
s2.kind(), s2.toChars());
{
if (s2.ident == ident)
{
errorSupplemental(s2.loc, "cannot call %s `%s` with UFCS because it is not declared at module scope",
s2.kind(), s2.toChars());
}
else
errorSupplemental(s2.loc, "did you mean %s `%s`?",
s2.kind(), s2.toChars());
}
else if (src.type.ty == Tpointer)
{
// structPtr.field
@ -3454,7 +3462,7 @@ Expression getProperty(Type t, Scope* scope_, Loc loc, Identifier ident, int fla
{
if (auto s3 = as.search_correct(ident))
{
errorSupplemental(loc, "did you mean %s `%s`?",
errorSupplemental(s3.loc, "did you mean %s `%s`?",
s3.kind(), s3.toChars());
}
}

View file

@ -14,6 +14,8 @@
class Expression;
class Type;
class TypeAArray;
class TypeInfoDeclaration;
struct Scope;
namespace dmd
@ -21,5 +23,7 @@ namespace dmd
bool genTypeInfo(Expression *e, Loc loc, Type *torig, Scope *sc);
bool isSpeculativeType(Type *t);
bool builtinTypeInfo(Type *t);
Type *makeNakedAssociativeArray(TypeAArray *t);
TypeInfoDeclaration *getTypeInfoAssocArrayDeclaration(TypeAArray *t, Scope *sc);
}
Type *getTypeInfoType(Loc loc, Type *t, Scope *sc);

View file

@ -394,6 +394,12 @@ void test_location()
Loc loc = Loc::singleFilename("app.d");
assert(strcmp(loc.toChars(true, MessageStyle::digitalmars), "app.d") == 0);
assert(strcmp(loc.toChars(true, MessageStyle::gnu), "app.d") == 0);
Loc loc2 = Loc::singleFilename("app2.d");
assert(!loc2.equals(loc));
SourceLoc sloc = loc.toSourceLoc();
assert(strcmp(sloc.filename.ptr, loc.filename()) == 0);
}
/**********************************/
@ -1730,12 +1736,14 @@ void argtypes_h(Type *t)
//dmd::isHFVA(t);
}
void declaration_h(FuncDeclaration *fd, Loc loc, Expressions* args)
void declaration_h(FuncDeclaration *fd, Loc loc, Expressions* args, Parameters* params)
{
dmd::functionSemantic(fd);
dmd::functionSemantic3(fd);
::eval_builtin(loc, fd, args);
::isBuiltin(fd);
dmd::genCfunc(params, fd->type, "test");
dmd::genCfunc(params, fd->type, Identifier::idPool("test"));
}
void doc_h(Module *m, const char *ptr, d_size_t length, const char *date,
@ -1868,4 +1876,6 @@ void typinf_h(Expression *e, Loc loc, Type *t, Scope *sc)
::getTypeInfoType(loc, t, sc);
dmd::isSpeculativeType(t);
dmd::builtinTypeInfo(t);
dmd::makeNakedAssociativeArray(t->isTypeAArray());
dmd::getTypeInfoAssocArrayDeclaration(t->isTypeAArray(), sc);
}

View file

@ -5,10 +5,10 @@ TEST_OUTPUT:
fail_compilation/fail347.d(26): Error: undefined identifier `bbr`, did you mean variable `bar`?
fail_compilation/fail347.d(27): Error: no property `ofo` for type `S`, did you mean `fail347.S.foo`?
fail_compilation/fail347.d(29): Error: no property `fool` for `sp` of type `fail347.S*`
fail_compilation/fail347.d(29): did you mean variable `foo`?
fail_compilation/fail347.d(20): did you mean variable `foo`?
fail_compilation/fail347.d(30): Error: undefined identifier `strlenx`, did you mean function `strlen`?
fail_compilation/fail347.d(31): Error: no property `strlenx` for `"hello"` of type `string`
fail_compilation/fail347.d(31): did you mean function `strlen`?
fail_compilation/imports/fail347a.d(3): did you mean function `strlen`?
---
*/

View file

@ -1,23 +1,28 @@
/*
TEST_OUTPUT:
---
fail_compilation/ufcs.d(26): Error: no property `regularF` for `s` of type `S`
fail_compilation/ufcs.d(26): the following error occured while looking for a UFCS match
fail_compilation/ufcs.d(26): Error: function `regularF` is not callable using argument types `(S)`
fail_compilation/ufcs.d(26): expected 0 argument(s), not 1
fail_compilation/ufcs.d(31): `ufcs.regularF()` declared here
fail_compilation/ufcs.d(27): Error: no property `templateF` for `s` of type `S`
fail_compilation/ufcs.d(27): the following error occured while looking for a UFCS match
fail_compilation/ufcs.d(27): Error: template `templateF` is not callable using argument types `!()(S)`
fail_compilation/ufcs.d(32): Candidate is: `templateF()()`
fail_compilation/ufcs.d(28): Error: no property `templateO` for `s` of type `S`
fail_compilation/ufcs.d(28): the following error occured while looking for a UFCS match
fail_compilation/ufcs.d(28): Error: none of the overloads of template `ufcs.templateO` are callable using argument types `!()(S)`
fail_compilation/ufcs.d(34): Candidates are: `templateO()(int x)`
fail_compilation/ufcs.d(35): `templateO()(float y)`
fail_compilation/ufcs.d(31): Error: no property `regularF` for `s` of type `S`
fail_compilation/ufcs.d(31): the following error occured while looking for a UFCS match
fail_compilation/ufcs.d(31): Error: function `regularF` is not callable using argument types `(S)`
fail_compilation/ufcs.d(31): expected 0 argument(s), not 1
fail_compilation/ufcs.d(39): `ufcs.regularF()` declared here
fail_compilation/ufcs.d(32): Error: no property `templateF` for `s` of type `S`
fail_compilation/ufcs.d(32): the following error occured while looking for a UFCS match
fail_compilation/ufcs.d(32): Error: template `templateF` is not callable using argument types `!()(S)`
fail_compilation/ufcs.d(40): Candidate is: `templateF()()`
fail_compilation/ufcs.d(33): Error: no property `templateO` for `s` of type `S`
fail_compilation/ufcs.d(33): the following error occured while looking for a UFCS match
fail_compilation/ufcs.d(33): Error: none of the overloads of template `ufcs.templateO` are callable using argument types `!()(S)`
fail_compilation/ufcs.d(42): Candidates are: `templateO()(int x)`
fail_compilation/ufcs.d(43): `templateO()(float y)`
fail_compilation/ufcs.d(36): Error: no property `local` for `s` of type `ufcs.S`
fail_compilation/ufcs.d(35): cannot call function `local` with UFCS because it is not declared at module scope
fail_compilation/ufcs.d(26): struct `S` defined here
---
*/
struct S { }
void f()
@ -26,6 +31,9 @@ void f()
s.regularF();
s.templateF();
s.templateO();
void local(S) {}
s.local();
}
void regularF();

View file

@ -0,0 +1,11 @@
// https://github.com/dlang/dmd/issues/21020
shared struct Queue {
int[int] map;
}
void main() {
auto queue = Queue();
(cast(int[int]) queue.map)[1] = 2;
assert(queue.map[1] == 2);
}

View file

@ -479,7 +479,7 @@ TESTS_EXTRACTOR=$(ROOT)/tests_extractor$(DOTEXE)
BETTERCTESTS_DIR=$(ROOT)/betterctests
# macro that returns the module name given the src path
moduleName=$(subst rt.invariant,invariant,$(subst object_,object,$(subst /,.,$(1))))
moduleName=$(subst /,.,$(1))
$(ROOT)/unittest/% : $(ROOT)/unittest/test_runner$(DOTEXE)
@mkdir -p $(dir $@)

View file

@ -548,7 +548,7 @@ DOCS=\
$(DOCDIR)\rt_deh_win32.html \
$(DOCDIR)\rt_deh_win64_posix.html \
$(DOCDIR)\rt_ehalloc.html \
$(DOCDIR)\rt_invariant.html \
$(DOCDIR)\rt_invariant_.html \
$(DOCDIR)\rt_llmath.html \
$(DOCDIR)\rt_memory.html \
$(DOCDIR)\rt_memset.html \

View file

@ -573,7 +573,7 @@ SRCS=\
src\rt\dmain2.d \
src\rt\dwarfeh.d \
src\rt\ehalloc.d \
src\rt\invariant.d \
src\rt\invariant_.d \
src\rt\lifetime.d \
src\rt\llmath.d \
src\rt\memory.d \

View file

@ -35,6 +35,7 @@ enum CppStdRevision : uint
cpp14 = 201402,
cpp17 = 201703,
cpp20 = 202002,
cpp23 = 202302,
}
/**

View file

@ -40,7 +40,7 @@ version (linux)
version (MemoryErrorSupported)
version = AnySupported;
else version (MemoryErrorSupported)
else version (MemoryAssertSupported)
version = AnySupported;
version (AnySupported):

View file

@ -27,7 +27,7 @@ else version (Posix)
{
import core.stdc.stdio : fopen;
import core.sys.posix.fcntl : O_CREAT, O_RDWR, open, S_IRGRP, S_IROTH, S_IRUSR, S_IWGRP, S_IWOTH, S_IWUSR;
import core.sys.posix.unistd : F_LOCK, ftruncate, lockf;
import core.sys.posix.unistd : ftruncate;
}
else
static assert(0, "Unsupported platform");
@ -487,7 +487,10 @@ void lockFile(int fd)
flock(fd, LOCK_EX); // exclusive lock
}
else version (Posix)
{
import core.sys.posix.unistd : F_LOCK, lockf;
lockf(fd, F_LOCK, 0); // exclusive lock
}
else version (Windows)
{
OVERLAPPED off;

View file

@ -4,15 +4,10 @@
* Copyright: Copyright Digital Mars 2007 - 2010.
* License: $(HTTP www.boost.org/LICENSE_1_0.txt, Boost License 1.0).
* Authors: Walter Bright
* Source: $(DRUNTIMESRC rt/_invariant.d)
*/
/* Copyright Digital Mars 2007 - 2010.
* Distributed under the Boost Software License, Version 1.0.
* (See accompanying file LICENSE or copy at
* http://www.boost.org/LICENSE_1_0.txt)
* Source: $(DRUNTIMESRC rt/_invariant_.d)
*/
module rt.invariant_;
/**
*