Commits

Iain Buclaw committed 7c9615d

D2 druntime segfault fixes.

Comments (0)

Files changed (8)

d/druntime/compiler/gdc/adi.d

  *  Modified by Sean Kelly for use with the D Runtime Project
  */
 
+/* NOTE: This file has been patched from the original DMD distribution to
+   work with the GDC compiler.
+
+   Modified by Iain Buclaw, September 2010.
+*/
+
 module rt.adi;
 
 //debug=adi;            // uncomment to turn on debugging printf's
  * reversed.
  */
 
-extern (C) long _adReverseChar(char[] a)
+extern (C) char[] _adReverseChar(char[] a)
 {
     if (a.length > 1)
     {
             hi = hi - 1 + (stridehi - stridelo);
         }
     }
-    return *cast(long*)(&a);
+    return a;
 }
 
 unittest
  * reversed.
  */
 
-extern (C) long _adReverseWchar(wchar[] a)
+extern (C) wchar[] _adReverseWchar(wchar[] a)
 {
     if (a.length > 1)
     {
             hi = hi - 1 + (stridehi - stridelo);
         }
     }
-    return *cast(long*)(&a);
+    return a;
 }
 
 unittest
  * Support for array.reverse property.
  */
 
-extern (C) long _adReverse(Array a, size_t szelem)
+extern (C) Array _adReverse(Array a, size_t szelem)
     out (result)
     {
-        assert(result is *cast(long*)(&a));
+        assert(result is a);
     }
     body
     {
                     //gc_free(tmp);
             }
         }
-        return *cast(long*)(&a);
+        return a;
     }
 
 unittest
  * Sort array of chars.
  */
 
-extern (C) long _adSortChar(char[] a)
+extern (C) char[] _adSortChar(char[] a)
 {
     if (a.length > 1)
     {
         }
         delete da;
     }
-    return *cast(long*)(&a);
+    return a;
 }
 
 /**********************************************
  * Sort array of wchars.
  */
 
-extern (C) long _adSortWchar(wchar[] a)
+extern (C) wchar[] _adSortWchar(wchar[] a)
 {
     if (a.length > 1)
     {
         }
         delete da;
     }
-    return *cast(long*)(&a);
+    return a;
 }
 
 /***************************************

d/druntime/compiler/gdc/alloca.d

-/*_ _alloca.d
- * Copyright (C) 1990-2003 by Digital Mars, www.digitalmars.com
- * All Rights Reserved
- * Written by Walter Bright
- */
-
-module rt.alloca;
-
-/+
-#if DOS386
-extern size_t _x386_break;
-#else
-extern size_t _pastdata;
-#endif
-+/
-
-/*******************************************
- * Allocate data from the caller's stack frame.
- * This is a 'magic' function that needs help from the compiler to
- * work right, do not change its name, do not call it from other compilers.
- * Input:
- *      nbytes  number of bytes to allocate
- *      ECX     address of variable with # of bytes in locals
- *              This is adjusted upon return to reflect the additional
- *              size of the stack frame.
- * Returns:
- *      EAX     allocated data, null if stack overflows
- */
-
-extern (C) void* __alloca(int nbytes)
-{
-    asm
-    {
-        naked                   ;
-        mov     EDX,ECX         ;
-        mov     EAX,4[ESP]      ; // get nbytes
-        push    EBX             ;
-        push    EDI             ;
-        push    ESI             ;
-        add     EAX,3           ;
-        and     EAX,0xFFFFFFFC  ; // round up to dword
-        jnz     Abegin          ;
-        mov     EAX,4           ; // allow zero bytes allocation, 0 rounded to dword is 4..
-    Abegin:
-        mov     ESI,EAX         ; // ESI = nbytes
-        neg     EAX             ;
-        add     EAX,ESP         ; // EAX is now what the new ESP will be.
-        jae     Aoverflow       ;
-    }
-    version (Windows)
-    {
-    asm
-    {
-        // We need to be careful about the guard page
-        // Thus, for every 4k page, touch it to cause the OS to load it in.
-        mov     ECX,EAX         ; // ECX is new location for stack
-        mov     EBX,ESI         ; // EBX is size to "grow" stack
-    L1:
-        test    [ECX+EBX],EBX   ; // bring in page
-        sub     EBX,0x1000      ; // next 4K page down
-        jae     L1              ; // if more pages
-        test    [ECX],EBX       ; // bring in last page
-    }
-    }
-    version (DOS386)
-    {
-    asm
-    {
-        // is ESP off bottom?
-        cmp     EAX,_x386_break ;
-        jbe     Aoverflow       ;
-    }
-    }
-    version (Unix)
-    {
-    asm
-    {
-        cmp     EAX,_pastdata   ;
-        jbe     Aoverflow       ; // Unlikely - ~2 Gbytes under UNIX
-    }
-    }
-    asm
-    {
-        // Copy down to [ESP] the temps on the stack.
-        // The number of temps is (EBP - ESP - locals).
-        mov     ECX,EBP         ;
-        sub     ECX,ESP         ;
-        sub     ECX,[EDX]       ; // ECX = number of temps (bytes) to move.
-        add     [EDX],ESI       ; // adjust locals by nbytes for next call to alloca()
-        mov     ESP,EAX         ; // Set up new stack pointer.
-        add     EAX,ECX         ; // Return value = ESP + temps.
-        mov     EDI,ESP         ; // Destination of copy of temps.
-        add     ESI,ESP         ; // Source of copy.
-        shr     ECX,2           ; // ECX to count of dwords in temps
-                                  // Always at least 4 (nbytes, EIP, ESI,and EDI).
-        rep                     ;
-        movsd                   ;
-        jmp     done            ;
-
-    Aoverflow:
-        // Overflowed the stack.  Return null
-        xor     EAX,EAX         ;
-
-    done:
-        pop     ESI             ;
-        pop     EDI             ;
-        pop     EBX             ;
-        ret                     ;
-    }
-}

d/druntime/compiler/gdc/cover.d

-/**
- * Code coverage analyzer.
- *
- * Bugs:
- *      $(UL
- *          $(LI the execution counters are 32 bits in size, and can overflow)
- *          $(LI inline asm statements are not counted)
- *      )
- *
- * Copyright: Copyright (C) 2005-2006 Digital Mars, www.digitalmars.com.  All rights reserved.
- * License:   BSD style: $(LICENSE)
- * Authors:   Walter Bright, Sean Kelly
- */
-
-module rt.cover;
-
-private
-{
-    version( Windows )
-        import sys.windows.windows;
-    else version( GNU )
-    {
-	import std.c.unix.unix;
-    }
-    else version( Posix )
-    {
-        import stdc.posix.fcntl;
-        import stdc.posix.unistd;
-    }
-    import core.bitmanip;
-    version( GNU ) {}
-    else {
-	import stdc.stdio;
-    }
-    import util.utf;
-
-    struct BitArray
-    {
-        size_t  len;
-        uint*   ptr;
-
-        bool opIndex( size_t i )
-        in
-        {
-            assert( i < len );
-        }
-        body
-        {
-            return cast(bool) bt( ptr, i );
-        }
-    }
-
-    struct Cover
-    {
-        char[]      filename;
-        BitArray    valid;
-        uint[]      data;
-    }
-
-    Cover[] gdata;
-    char[]  srcpath;
-    char[]  dstpath;
-    bool    merge;
-}
-
-
-/**
- * Set path to where source files are located.
- *
- * Params:
- *  pathname = The new path name.
- */
-extern (C) void dmd_coverSourcePath( char[] pathname )
-{
-    srcpath = pathname;
-}
-
-
-/**
- * Set path to where listing files are to be written.
- *
- * Params:
- *  pathname = The new path name.
- */
-extern (C) void dmd_coverDestPath( char[] pathname )
-{
-    dstpath = pathname;
-}
-
-
-/**
- * Set merge mode.
- *
- * Params:
- *      flag = true means new data is summed with existing data in the listing
- *         file; false means a new listing file is always created.
- */
-extern (C) void dmd_coverSetMerge( bool flag )
-{
-    merge = flag;
-}
-
-
-/**
- * The coverage callback.
- *
- * Params:
- *  filename = The name of the coverage file.
- *  valid    = ???
- *  data     = ???
- */
-extern (C) void _d_cover_register( char[] filename, BitArray valid, uint[] data )
-{
-    Cover c;
-
-    c.filename  = filename;
-    c.valid     = valid;
-    c.data      = data;
-    gdata      ~= c;
-}
-
-
-static ~this()
-{
-    const NUMLINES = 16384 - 1;
-    const NUMCHARS = 16384 * 16 - 1;
-
-    char[]      srcbuf      = new char[NUMCHARS];
-    char[][]    srclines    = new char[][NUMLINES];
-    char[]      lstbuf      = new char[NUMCHARS];
-    char[][]    lstlines    = new char[][NUMLINES];
-
-    foreach( Cover c; gdata )
-    {
-        if( !readFile( appendFN( srcpath, c.filename ), srcbuf ) )
-            continue;
-        splitLines( srcbuf, srclines );
-
-        if( merge )
-        {
-            if( !readFile( c.filename ~ ".lst", lstbuf ) )
-                break;
-            splitLines( lstbuf, lstlines );
-
-            for( size_t i = 0; i < lstlines.length; ++i )
-            {
-                if( i >= c.data.length )
-                    break;
-
-                int count = 0;
-
-                foreach( char c2; lstlines[i] )
-                {
-                    switch( c2 )
-                    {
-                    case ' ':
-                        continue;
-                    case '0': case '1': case '2': case '3': case '4':
-                    case '5': case '6': case '7': case '8': case '9':
-                        count = count * 10 + c2 - '0';
-                        continue;
-                    default:
-                        break;
-                    }
-                }
-                c.data[i] += count;
-            }
-        }
-
-        FILE* flst = fopen( (c.filename ~ ".lst").ptr, "wb" );
-
-        if( !flst )
-            continue; //throw new Exception( "Error opening file for write: " ~ lstfn );
-
-        uint nno;
-        uint nyes;
-
-        for( int i = 0; i < c.data.length; i++ )
-        {
-            if( i < srclines.length )
-            {
-                uint    n    = c.data[i];
-                char[]  line = srclines[i];
-
-                line = expandTabs( line );
-
-                if( n == 0 )
-                {
-                    if( c.valid[i] )
-                    {
-                        nno++;
-                        fprintf( flst, "0000000|%.*s\n", line );
-                    }
-                    else
-                    {
-                        fprintf( flst, "       |%.*s\n", line );
-                    }
-                }
-                else
-                {
-                    nyes++;
-                    fprintf( flst, "%7u|%.*s\n", n, line );
-                }
-            }
-        }
-        if( nyes + nno ) // no divide by 0 bugs
-        {
-            fprintf( flst, "%.*s is %d%% covered\n", c.filename, ( nyes * 100 ) / ( nyes + nno ) );
-        }
-        fclose( flst );
-    }
-}
-
-
-char[] appendFN( char[] path, char[] name )
-{
-    version( Windows )
-        const char sep = '\\';
-    else
-        const char sep = '/';
-
-    char[] dest = path;
-
-    if( dest && dest[$ - 1] != sep )
-        dest ~= sep;
-    dest ~= name;
-    return dest;
-}
-
-
-bool readFile( char[] name, inout char[] buf )
-{
-    version( Windows )
-    {
-        auto    wnamez  = toUTF16z( name );
-        HANDLE  file    = CreateFileW( wnamez,
-                                       GENERIC_READ,
-                                       FILE_SHARE_READ,
-                                       null,
-                                       OPEN_EXISTING,
-                                       FILE_ATTRIBUTE_NORMAL | FILE_FLAG_SEQUENTIAL_SCAN,
-                                       cast(HANDLE) null );
-
-        delete wnamez;
-        if( file == INVALID_HANDLE_VALUE )
-            return false;
-        scope( exit ) CloseHandle( file );
-
-        DWORD   num = 0;
-        DWORD   pos = 0;
-
-        buf.length = 4096;
-        while( true )
-        {
-            if( !ReadFile( file, &buf[pos], cast(DWORD)( buf.length - pos ), &num, null ) )
-                return false;
-            if( !num )
-                break;
-            pos += num;
-            buf.length = pos * 2;
-        }
-        buf.length = pos;
-        return true;
-    }
-    else version( linux )
-    {
-        char[]  namez = new char[name.length + 1];
-                        namez[0 .. name.length] = name;
-                        namez[$ - 1] = 0;
-        int     file = open( namez.ptr, O_RDONLY );
-
-        delete namez;
-        if( file == -1 )
-            return false;
-        scope( exit ) close( file );
-
-        int     num = 0;
-        uint    pos = 0;
-
-        buf.length = 4096;
-        while( true )
-        {
-            num = read( file, &buf[pos], cast(uint)( buf.length - pos ) );
-            if( num == -1 )
-                return false;
-            if( !num )
-                break;
-            pos += num;
-            buf.length = pos * 2;
-        }
-        buf.length = pos;
-        return true;
-    }
-}
-
-
-void splitLines( char[] buf, inout char[][] lines )
-{
-    size_t  beg = 0,
-            pos = 0;
-
-    lines.length = 0;
-    for( ; pos < buf.length; ++pos )
-    {
-        char c = buf[pos];
-
-        switch( buf[pos] )
-        {
-        case '\r':
-        case '\n':
-            lines ~= buf[beg .. pos];
-            beg = pos + 1;
-            if( buf[pos] == '\r' && pos < buf.length - 1 && buf[pos + 1] == '\n' )
-                ++pos, ++beg;
-        default:
-            continue;
-        }
-    }
-    if( beg != pos )
-    {
-        lines ~= buf[beg .. pos];
-    }
-}
-
-
-char[] expandTabs( char[] string, int tabsize = 8 )
-{
-    const dchar LS = '\u2028'; // UTF line separator
-    const dchar PS = '\u2029'; // UTF paragraph separator
-
-    bool changes = false;
-    char[] result = string;
-    int column;
-    int nspaces;
-
-    foreach( size_t i, dchar c; string )
-    {
-        switch( c )
-        {
-            case '\t':
-                nspaces = tabsize - (column % tabsize);
-                if( !changes )
-                {
-                    changes = true;
-                    result = null;
-                    result.length = string.length + nspaces - 1;
-                    result.length = i + nspaces;
-                    result[0 .. i] = string[0 .. i];
-                    result[i .. i + nspaces] = ' ';
-                }
-                else
-                {   int j = result.length;
-                    result.length = j + nspaces;
-                    result[j .. j + nspaces] = ' ';
-                }
-                column += nspaces;
-                break;
-
-            case '\r':
-            case '\n':
-            case PS:
-            case LS:
-                column = 0;
-                goto L1;
-
-            default:
-                column++;
-            L1:
-                if (changes)
-                {
-                    if (c <= 0x7F)
-                        result ~= c;
-                    else
-                        encode(result, c);
-                }
-                break;
-        }
-    }
-    return result;
-}

d/druntime/compiler/gdc/memset.d

-/*
- *  Copyright (C) 2004 by Digital Mars, www.digitalmars.com
- *  Written by Walter Bright
- *
- *  This software is provided 'as-is', without any express or implied
- *  warranty. In no event will the authors be held liable for any damages
- *  arising from the use of this software.
- *
- *  Permission is granted to anyone to use this software for any purpose,
- *  including commercial applications, and to alter it and redistribute it
- *  freely, in both source and binary form, subject to the following
- *  restrictions:
- *
- *  o  The origin of this software must not be misrepresented; you must not
- *     claim that you wrote the original software. If you use this software
- *     in a product, an acknowledgment in the product documentation would be
- *     appreciated but is not required.
- *  o  Altered source versions must be plainly marked as such, and must not
- *     be misrepresented as being the original software.
- *  o  This notice may not be removed or altered from any source
- *     distribution.
- */
-module rt.memset;
-
-
-extern (C)
-{
-    // Functions from the C library.
-    void *memcpy(void *, void *, size_t);
-}
-
-extern (C):
-
-short *_memset16(short *p, short value, size_t count)
-{
-    short *pstart = p;
-    short *ptop;
-
-    for (ptop = &p[count]; p < ptop; p++)
-        *p = value;
-    return pstart;
-}
-
-int *_memset32(int *p, int value, size_t count)
-{
-version (X86)
-{
-    asm
-    {
-        mov     EDI,p           ;
-        mov     EAX,value       ;
-        mov     ECX,count       ;
-        mov     EDX,EDI         ;
-        rep                     ;
-        stosd                   ;
-        mov     EAX,EDX         ;
-    }
-}
-else
-{
-    int *pstart = p;
-    int *ptop;
-
-    for (ptop = &p[count]; p < ptop; p++)
-        *p = value;
-    return pstart;
-}
-}
-
-long *_memset64(long *p, long value, size_t count)
-{
-    long *pstart = p;
-    long *ptop;
-
-    for (ptop = &p[count]; p < ptop; p++)
-        *p = value;
-    return pstart;
-}
-
-cdouble *_memset128(cdouble *p, cdouble value, size_t count)
-{
-    cdouble *pstart = p;
-    cdouble *ptop;
-
-    for (ptop = &p[count]; p < ptop; p++)
-        *p = value;
-    return pstart;
-}
-
-real *_memset80(real *p, real value, size_t count)
-{
-    real *pstart = p;
-    real *ptop;
-
-    for (ptop = &p[count]; p < ptop; p++)
-        *p = value;
-    return pstart;
-}
-
-creal *_memset160(creal *p, creal value, size_t count)
-{
-    creal *pstart = p;
-    creal *ptop;
-
-    for (ptop = &p[count]; p < ptop; p++)
-        *p = value;
-    return pstart;
-}
-
-void *_memsetn(void *p, void *value, int count, size_t sizelem)
-{   void *pstart = p;
-    int i;
-
-    for (i = 0; i < count; i++)
-    {
-        memcpy(p, value, sizelem);
-        p = cast(void *)(cast(char *)p + sizelem);
-    }
-    return pstart;
-}

d/druntime/compiler/gdc/qsort.d

         _adSort() is required.
 */
 
+/* NOTE: This file has been patched from the original DMD distribution to
+   work with the GDC compiler.
+
+   Modified by Iain Buclaw, September 2010.
+*/
+
 module rt.qsort;
 
 /*
 structures.  The default value is optimized for a high cost for compares. */
 
 
-extern (C) long _adSort(Array a, TypeInfo ti)
+extern (C) Array _adSort(Array a, TypeInfo ti)
 {
   byte* base;
   byte*[40] stack;              // stack
       limit = sp[1];
     }
     else                                // else stack empty, all done
-      return *cast(long*)(&a);
+      return a;
   }
   assert(0);
 }

d/druntime/compiler/gdc/qsort2.d

-
-/*
- * Placed into Public Domain
- * written by Walter Bright
- * www.digitalmars.com
- *
- * This is a public domain version of qsort.d.
- * All it does is call C's qsort(), but runs a little slower since
- * it needs to synchronize a global variable.
- */
-
-/*
- *  Modified by Sean Kelly for use with the D Runtime Project
- */
-
-module rt.qsort2;
-
-//debug=qsort;
-
-private import stdc.stdlib;
-
-struct Array
-{
-    size_t length;
-    void*  ptr;
-}
-
-private TypeInfo tiglobal;
-
-extern (C) int cmp(void* p1, void* p2)
-{
-    return tiglobal.compare(p1, p2);
-}
-
-extern (C) long _adSort(Array a, TypeInfo ti)
-{
-    synchronized
-    {
-        tiglobal = ti;
-        qsort(a.ptr, a.length, cast(size_t)ti.tsize(), &cmp);
-    }
-    return *cast(long*)(&a);
-}
-
-
-
-unittest
-{
-    debug(qsort) printf("array.sort.unittest()\n");
-
-    int a[] = new int[10];
-
-    a[0] = 23;
-    a[1] = 1;
-    a[2] = 64;
-    a[3] = 5;
-    a[4] = 6;
-    a[5] = 5;
-    a[6] = 17;
-    a[7] = 3;
-    a[8] = 0;
-    a[9] = -1;
-
-    a.sort;
-
-    for (int i = 0; i < a.length - 1; i++)
-    {
-        //printf("i = %d", i);
-        //printf(" %d %d\n", a[i], a[i + 1]);
-        assert(a[i] <= a[i + 1]);
-    }
-}

d/phobos2/Makefile.am

 	  compiler/arraycat.o compiler/arraydouble.o compiler/arrayfloat.o \
 	  compiler/arrayint.o compiler/arrayreal.o compiler/arrayshort.o \
 	  compiler/cast_.o compiler/complex.o \
-	  compiler/cover.o compiler/critical.o compiler/dgccmain2.o \
+	  compiler/critical.o compiler/dgccmain2.o \
 	  compiler/invariant.o compiler/invariant_.o compiler/lifetime.o \
-	  compiler/gccmemory.o compiler/memset.o \
+	  compiler/gccmemory.o \
 	  compiler/monitor.o compiler/obj.o compiler/object_.o \
 	  compiler/qsort.o compiler/switch_.o
 

d/phobos2/Makefile.in

 	  compiler/arraycat.o compiler/arraydouble.o compiler/arrayfloat.o \
 	  compiler/arrayint.o compiler/arrayreal.o compiler/arrayshort.o \
 	  compiler/cast_.o compiler/complex.o \
-	  compiler/cover.o compiler/critical.o compiler/dgccmain2.o \
+	  compiler/critical.o compiler/dgccmain2.o \
 	  compiler/invariant.o compiler/invariant_.o compiler/lifetime.o \
-	  compiler/gccmemory.o compiler/memset.o \
+	  compiler/gccmemory.o \
 	  compiler/monitor.o compiler/obj.o compiler/object_.o \
 	  compiler/qsort.o compiler/switch_.o