alias size_t hash_t;\r
alias int equals_t;\r
\r
-alias char[] string;\r
-alias wchar[] wstring;\r
-alias dchar[] dstring;\r
+alias invariant(char)[] string;\r
+alias invariant(wchar)[] wstring;\r
+alias invariant(dchar)[] dstring;\r
\r
class Object\r
{\r
// 2: // has no possible pointers into GC memory\r
// 4: // has offTi[] member\r
// 8: // has constructors\r
+ // 16: // has xgetMembers member\r
void* deallocator;\r
OffsetTypeInfo[] offTi;\r
void* defaultConstructor;\r
+ const(MemberInfo[]) function(string) xgetMembers;\r
\r
static ClassInfo find(in char[] classname);\r
Object create();\r
+ const(MemberInfo[]) getMembers(in char[] classname);\r
}\r
\r
struct OffsetTypeInfo\r
uint flags();\r
// 1: // has possible pointers into GC memory\r
OffsetTypeInfo[] offTi();\r
+ void destroy(void* p);\r
+ void postblit(void* p);\r
}\r
\r
class TypeInfo_Typedef : TypeInfo\r
\r
class TypeInfo_Enum : TypeInfo_Typedef\r
{\r
+\r
}\r
\r
class TypeInfo_Pointer : TypeInfo\r
\r
uint m_flags;\r
\r
+ const(MemberInfo[]) function(in char[]) xgetMembers;\r
+ void function(void*) xdtor;\r
+ void function(void*) xpostblit;\r
}\r
\r
class TypeInfo_Tuple : TypeInfo\r
TypeInfo[] elements;\r
}\r
\r
+class TypeInfo_Const : TypeInfo\r
+{\r
+ TypeInfo next;\r
+}\r
+\r
+class TypeInfo_Invariant : TypeInfo_Const\r
+{\r
+\r
+}\r
+\r
+abstract class MemberInfo\r
+{\r
+ string name();\r
+}\r
+\r
+class MemberInfo_field : MemberInfo\r
+{\r
+ this(string name, TypeInfo ti, size_t offset);\r
+\r
+ override string name();\r
+ TypeInfo typeInfo();\r
+ size_t offset();\r
+}\r
+\r
+class MemberInfo_function : MemberInfo\r
+{\r
+ enum\r
+ {\r
+ Virtual = 1,\r
+ Member = 2,\r
+ Static = 4,\r
+ }\r
+\r
+ this(string name, TypeInfo ti, void* fp, uint flags);\r
+\r
+ override string name();\r
+ TypeInfo typeInfo();\r
+ void* fp();\r
+ uint flags();\r
+}\r
+\r
class ModuleInfo\r
{\r
string name;\r
{\r
interface TraceInfo\r
{\r
- int opApply( int delegate( inout char[] ) );\r
+ int opApply( int delegate(inout char[]) );\r
string toString();\r
}\r
\r
{
extern FILE[_NFILE]* _imp___iob;
- const FILE* stdin;
- const FILE* stdout;
- const FILE* stderr;
- const FILE* stdaux;
- const FILE* stdprn;
+ auto FILE* stdin;
+ auto FILE* stdout;
+ auto FILE* stderr;
+ auto FILE* stdaux;
+ auto FILE* stdprn;
static this()
{
{
extern FILE[_NFILE] _iob;
- const FILE* stdin = &_iob[0];
- const FILE* stdout = &_iob[1];
- const FILE* stderr = &_iob[2];
- const FILE* stdaux = &_iob[3];
- const FILE* stdprn = &_iob[4];
+ auto FILE* stdin = &_iob[0];
+ auto FILE* stdout = &_iob[1];
+ auto FILE* stderr = &_iob[2];
+ auto FILE* stdaux = &_iob[3];
+ auto FILE* stdprn = &_iob[4];
}
}
else version( linux )
extern FILE* __stdoutp;
extern FILE* __stderrp;
- const FILE* stdin;
- const FILE* stdout;
- const FILE* stderr;
+ auto FILE* stdin;
+ auto FILE* stdout;
+ auto FILE* stderr;
static this()
{
{
extern FILE[3] __sF;
- const FILE* stdin = &__sF[0];
- const FILE* stdout = &__sF[1];
- const FILE* stderr = &__sF[2];
+ auto FILE* stdin = &__sF[0];
+ auto FILE* stdout = &__sF[1];
+ auto FILE* stderr = &__sF[2];
}
else
{
--- /dev/null
+/**
+ * Part of the D programming language runtime library.
+ * http://www.digitalmars.com
+ * Written by Walter Bright
+ * Placed in the Public Domain
+ */
+module rt.arrayassign;
+
+private
+{
+ import util.string;
+ import stdc.string;
+ import stdc.stdlib;
+ debug(PRINTF) import stdc.stdio;
+}
+
+/**
+ * Does array assignment (not construction) from another
+ * array of the same element type.
+ * ti is the element type.
+ * Handles overlapping copies.
+ */
+extern (C) void[] _d_arrayassign(TypeInfo ti, void[] from, void[] to)
+{
+ debug(PRINTF) printf("_d_arrayassign(from = %p,%d, to = %p,%d) size = %d\n", from.ptr, from.length, to.ptr, to.length, ti.tsize());
+
+ if (to.length != from.length)
+ {
+ char[10] tmp = void;
+ string msg = "lengths don't match for array copy,"c;
+ msg ~= tmp.intToString(to.length) ~ " = " ~ tmp.intToString(from.length);
+ throw new Exception(msg);
+ }
+
+ auto element_size = ti.tsize();
+
+ /* Need a temporary buffer tmp[] big enough to hold one element
+ */
+ void[16] buf = void;
+ void[] tmp;
+ if (element_size > buf.sizeof)
+ tmp = alloca(element_size)[0 .. element_size];
+ else
+ tmp = buf;
+
+
+ if (to.ptr <= from.ptr)
+ {
+ foreach (i; 0 .. to.length)
+ {
+ void* pto = to.ptr + i * element_size;
+ void* pfrom = from.ptr + i * element_size;
+ memcpy(tmp.ptr, pto, element_size);
+ memcpy(pto, pfrom, element_size);
+ ti.postblit(pto);
+ ti.destroy(tmp.ptr);
+ }
+ }
+ else
+ {
+ for (int i = to.length; i--; )
+ {
+ void* pto = to.ptr + i * element_size;
+ void* pfrom = from.ptr + i * element_size;
+ memcpy(tmp.ptr, pto, element_size);
+ memcpy(pto, pfrom, element_size);
+ ti.postblit(pto);
+ ti.destroy(tmp.ptr);
+ }
+ }
+ return to;
+}
+
+/**
+ * Does array initialization (not assignment) from another
+ * array of the same element type.
+ * ti is the element type.
+ */
+extern (C) void[] _d_arrayctor(TypeInfo ti, void[] from, void[] to)
+{
+ debug(PRINTF) printf("_d_arrayctor(from = %p,%d, to = %p,%d) size = %d\n", from.ptr, from.length, to.ptr, to.length, ti.tsize());
+
+ if (to.length != from.length)
+ {
+ char[10] tmp = void;
+ string msg = "lengths don't match for array initialization,"c;
+ msg ~= tmp.intToString(to.length) ~ " = " ~ tmp.intToString(from.length);
+ throw new Exception(msg);
+ }
+
+ auto element_size = ti.tsize();
+
+ int i;
+ try
+ {
+ for (i = 0; i < to.length; i++)
+ {
+ // Copy construction is defined as bit copy followed by postblit.
+ memcpy(to.ptr + i * element_size, from.ptr + i * element_size, element_size);
+ ti.postblit(to.ptr + i * element_size);
+ }
+ }
+ catch (Object o)
+ {
+ /* Destroy, in reverse order, what we've constructed so far
+ */
+ while (i--)
+ {
+ ti.destroy(to.ptr + i * element_size);
+ }
+
+ throw o;
+ }
+ return to;
+}
+
+
+/**
+ * Do assignment to an array.
+ * p[0 .. count] = value;
+ */
+extern (C) void* _d_arraysetassign(void* p, void* value, int count, TypeInfo ti)
+{
+ void* pstart = p;
+
+ auto element_size = ti.tsize();
+
+ //Need a temporary buffer tmp[] big enough to hold one element
+ void[16] buf = void;
+ void[] tmp;
+ if (element_size > buf.sizeof)
+ {
+ tmp = alloca(element_size)[0 .. element_size];
+ }
+ else
+ tmp = buf;
+
+ foreach (i; 0 .. count)
+ {
+ memcpy(tmp.ptr, p, element_size);
+ memcpy(p, value, element_size);
+ ti.postblit(p);
+ ti.destroy(tmp.ptr);
+ p += element_size;
+ }
+ return pstart;
+}
+
+/**
+ * Do construction of an array.
+ * ti[count] p = value;
+ */
+extern (C) void* _d_arraysetctor(void* p, void* value, int count, TypeInfo ti)
+{
+ void* pstart = p;
+ auto element_size = ti.tsize();
+
+ try
+ {
+ foreach (i; 0 .. count)
+ {
+ // Copy construction is defined as bit copy followed by postblit.
+ memcpy(p, value, element_size);
+ ti.postblit(p);
+ p += element_size;
+ }
+ }
+ catch (Object o)
+ {
+ // Destroy, in reverse order, what we've constructed so far
+ while (p > pstart)
+ {
+ p -= element_size;
+ ti.destroy(p);
+ }
+
+ throw o;
+ }
+ return pstart;
+}
onSwitchError( file, line );
}
+extern (C) void _d_hidden_func()
+{
+ // TODO: Figure out what to do with this routine
+}
+
bool _d_isHalting = false;
extern (C) bool rt_isHalting()
alias size_t hash_t;
alias int equals_t;
-alias char[] string;
-alias wchar[] wstring;
-alias dchar[] dstring;
+alias invariant(char)[] string;
+alias invariant(wchar)[] wstring;
+alias invariant(dchar)[] dstring;
/**
* All D class objects inherit from Object.
// 2: // has no possible pointers into GC memory
// 4: // has offTi[] member
// 8: // has constructors
+ // 16: // has xgetMembers member
void* deallocator;
OffsetTypeInfo[] offTi;
void function(Object) defaultConstructor; // default Constructor
+ const(MemberInfo[]) function(in char[]) xgetMembers;
/**
* Search all modules for ClassInfo corresponding to classname.
}
return o;
}
+ /**
+ * Search for all members with the name 'name'.
+ * If name[] is null, return all members.
+ */
+ const(MemberInfo[]) getMembers(in char[] name)
+ {
+ if (flags & 16 && xgetMembers)
+ return xgetMembers(name);
+ return null;
+ }
}
/**
/// Get type information on the contents of the type; null if not available
OffsetTypeInfo[] offTi() { return null; }
+ /// Run the destructor on the object and all its sub-objects
+ void destroy(void* p) {}
+ /// Run the postblit on the object and all its sub-objects
+ void postblit(void* p) {}
}
class TypeInfo_Typedef : TypeInfo
override TypeInfo next() { return value; }
override uint flags() { return value.flags(); }
+ override void destroy(void* p)
+ {
+ auto sz = value.tsize();
+ p += sz * len;
+ foreach (i; 0 .. len)
+ {
+ p -= sz;
+ value.destroy(p);
+ }
+ }
+
+ override void postblit(void* p)
+ {
+ auto sz = value.tsize();
+ foreach (i; 0 .. len)
+ {
+ value.postblit(p);
+ p += sz;
+ }
+ }
+
TypeInfo value;
size_t len;
}
// A sorry hash algorithm.
// Should use the one for strings.
// BUG: relies on the GC not moving objects
- auto q = cast(ubyte*)p;
+ auto q = cast(const(ubyte)*)p;
for (size_t i = 0; i < init.length; i++)
{
h = h * 9 + *q;
override uint flags() { return m_flags; }
+ override void destroy(void* p)
+ {
+ if (xdtor)
+ (*xdtor)(p);
+ }
+
+ override void postblit(void* p)
+ {
+ if (xpostblit)
+ (*xpostblit)(p);
+ }
+
string name;
void[] m_init; // initializer; init.ptr == null if 0 initialize
char[] function(in void*) xtoString;
uint m_flags;
+
+ const(MemberInfo[]) function(in char[]) xgetMembers;
+ void function(void*) xdtor;
+ void function(void*) xpostblit;
}
class TypeInfo_Tuple : TypeInfo
{
assert(0);
}
+
+ override void destroy(void* p)
+ {
+ assert(0);
+ }
+
+ override void postblit(void* p)
+ {
+ assert(0);
+ }
+}
+
+class TypeInfo_Const : TypeInfo
+{
+ override string toString()
+ {
+ return cast(string) ("const(" ~ base.toString() ~ ")");
+ }
+
+ override equals_t opEquals(Object o) { return base.opEquals(o); }
+ override hash_t getHash(in void *p) { return base.getHash(p); }
+ override equals_t equals(in void *p1, in void *p2) { return base.equals(p1, p2); }
+ override int compare(in void *p1, in void *p2) { return base.compare(p1, p2); }
+ override size_t tsize() { return base.tsize(); }
+ override void swap(void *p1, void *p2) { return base.swap(p1, p2); }
+
+ override TypeInfo next() { return base.next(); }
+ override uint flags() { return base.flags(); }
+ override void[] init() { return base.init(); }
+
+ TypeInfo base;
+}
+
+class TypeInfo_Invariant : TypeInfo_Const
+{
+ override string toString()
+ {
+ return cast(string) ("invariant(" ~ base.toString() ~ ")");
+ }
+}
+
+abstract class MemberInfo
+{
+ string name();
+}
+
+class MemberInfo_field : MemberInfo
+{
+ this(string name, TypeInfo ti, size_t offset)
+ {
+ m_name = name;
+ m_typeinfo = ti;
+ m_offset = offset;
+ }
+
+ override string name() { return m_name; }
+ TypeInfo typeInfo() { return m_typeinfo; }
+ size_t offset() { return m_offset; }
+
+ string m_name;
+ TypeInfo m_typeinfo;
+ size_t m_offset;
+}
+
+class MemberInfo_function : MemberInfo
+{
+ this(string name, TypeInfo ti, void* fp, uint flags)
+ {
+ m_name = name;
+ m_typeinfo = ti;
+ m_fp = fp;
+ m_flags = flags;
+ }
+
+ override string name() { return m_name; }
+ TypeInfo typeInfo() { return m_typeinfo; }
+ void* fp() { return m_fp; }
+ uint flags() { return m_flags; }
+
+ string m_name;
+ TypeInfo m_typeinfo;
+ void* m_fp;
+ uint m_flags;
}
aApplyR.o \\r
adi.o \\r
alloca.o \\r
+ arrayassign.o \\r
arraybyte.o \\r
arraycast.o \\r
arraycat.o \\r
aApply.obj \\r
aApplyR.obj \\r
adi.obj \\r
+ arrayassign.obj \\r
arraybyte.obj \\r
arraycast.obj \\r
arraycat.obj \\r
}
}
- invariant
+ invariant()
{
if (data)
{
}
- invariant
+ invariant()
{
if (gcx)
{
void Invariant() { }
- invariant
+ invariant()
{
if (inited)
{
void Invariant() { }
- invariant
+ invariant()
{
//mark.Invariant();
//scan.Invariant();