This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

Compiler: Possible bug in C++ compiler in CGT8.3.4



Tool/software: TI C/C++ Compiler

Hello!

We have observed a strange behavior of C++ compiler in CGT8.3.4. The generated code issues an illegal read to the zero address, triggering NMI in K2 DSP cores.

Let me go to the details of my findings. Crash occurs just after the execution is branched to delete operand (Please find the whole class definition in the attachment (vector.hpp)):

void reserve(unsigned int argSize)
{
    dataT* tmpPtr;
    // calculate new buffer size as multiple of CVECTOR_BLOCKSIZE
    unsigned int newBufferSize = ((argSize + CVECTOR_BLOCKSIZE - 1) / CVECTOR_BLOCKSIZE) * CVECTOR_BLOCKSIZE;
    if (newBufferSize > m_bufferSize)
    {
        // if the new size is larger than the old
        // allocate new memory
        // allocate one additional element as end element
        if (g_poolId > 0) // take from memory pool
        {
             tmpPtr = new(g_poolId) dataT[newBufferSize + 1];
         }
        else
        {
            // take from heap
            tmpPtr = new dataT[newBufferSize + 1];
        }
        if (tmpPtr)
        {
           // copy old buffer to new buffer
           std::memcpy(tmpPtr, m_buffer, m_numElements * sizeof(dataT));
           // clear copied buffer area, so that we can delete it (this calls the destructors, which should do nothing).
           std::memset(m_buffer, 0, m_numElements * sizeof(dataT));
           // delete old buffer
            delete [] m_buffer;  -> implementation of delete operand can be found in attachment.
            // set buffer pointer and size
            m_buffer = tmpPtr;
            m_bufferSize = newBufferSize;
        }
        else
        {
             AaSysLogPrint(EAaSysLogSeverityLevel_Error, "allocate heap failed.g_poolId : %x", g_poolId);
        }
    } // if (newBufferSize > m_bufferSize)
} // reserve()

Looking at the generated assembly code (the whole function can be found in disasm_CGT8.txt):

17818450 $C$L75:
17818450 0586 MV.L1 A11,A0
17818452 d2ba [!A0] BNOP.S1 $C$L77 (PC+148 = 0x178184d4),5
17818454 00282264 LDW.D1T1 *+A10[1],A0
17818458 02286266 LDW.D1T2 *+A10[3],B4
1781845c e3008000 .fphead n, l, W, BU, br, nosat, 0011000b
17818460 8586 MV.L1 A11,A4
17818462 2c6e NOP 2
17818464 00806ca0 SHL.S1 A0,0x3,A1
17818468 00041c40 ADDAW.D1 A1,A0,A0
1781846c 10058413 CALLP.S2 $Tramp$S$$memcpy (PC+11296 = 0x1781b080),B3
17818470 03000fd8 || MV.L1 A0,A6
17818474 $C$RL146:
17818474 00282264 LDW.D1T1 *+A10[1],A0
17818478 02286264 LDW.D1T1 *+A10[3],A4
1781847c e0200000 .fphead n, l, W, BU, nobr, nosat, 0000001b
17818480 0627 MVK.L2 0,B4
17818482 2c6e NOP 2
17818484 00806ca0 SHL.S1 A0,0x3,A1
17818488 00041c40 ADDAW.D1 A1,A0,A0
1781848c 10057613 CALLP.S2 $Tramp$S$$memset (PC+11184 = 0x1781b030),B3
17818490 03000fd8 || MV.L1 A0,A6
17818494 $C$RL148:
17818494 01286264 LDW.D1T1 *+A10[3],A2
17818498 04681028 MVK.S1 0xffffd020,A8
1781849c e0200000 .fphead n, l, W, BU, nobr, nosat, 0000001b
178184a0 0442e968 MVKH.S1 0x85d20000,A8
178184a4 8e27 MVK.L2 12,B4
178184a6 8726 MVK.L1 4,A6
178184a8 b012a120 [!A2] BNOP.S1 $C$RL150 (PC+36 = 0x178184c4),5
178184ac 02286264 LDW.D1T1 *+A10[3],A4
178184b0 6c6e NOP 4
178184b2 004c LDW.D1T1 *A4[0],A4
178184b4 6c6e NOP 4
178184b6 106c LDW.D1T2 *A4[0],B6  -> This read causes points to zero address, causing the NMI
178184b8 02286265 LDW.D1T1 *+A10[3],A4
178184bc e6400000 .fphead n, l, W, BU, nobr, nosat, 0110010b
178184c0 10057412 || CALLP.S2 $Tramp$S$$__cxa_vec_delete3 (PC+11168 = 0x1781b060),B3

Internal registers:

A0 = 0x1 = _ZN13HistoryBuffer14CHistoryBuffer9HBTimerIdE (o = 0x00000000)
A1 = 0x74 = 116
A2 = 0x1784fd0c = _sys_memory (o = 0x0000410c)
A3 = 0x1784fd84 = _sys_memory (o = 0x00004184)
A4 = 0x1784fd0c = _sys_memory (o = 0x0000410c)
A5 = 0x0 = _ZN13HistoryBuffer14CHistoryBuffer9HBTimerIdE (o = 0x00000000)
A6 = 0x4 = 4
A7 = 0x70 = 112
A8 = 0x85d2d020 = *:_ZdaPvj (o = 0x00000000)
A9 = 0x1784fd0c = _sys_memory (o = 0x0000410c)
A10 = 0x178d6c04 = systemPool (o = 0x00009b64)
B0 = 0x0 = _ZN13HistoryBuffer14CHistoryBuffer9HBTimerIdE (o = 0x00000000)
B1 = 0x1 = _ZN13HistoryBuffer14CHistoryBuffer9HBTimerIdE (o = 0x00000000)
B2 = 0x17850384 = _sys_memory (o = 0x00004784)
B3 = 0x178184c4 = *:_ZN7CVectorI7CStringE7reserveEj (o = 0x00000144)
B4 = 0xc = 12
B5 = 0x0 = _ZN13HistoryBuffer14CHistoryBuffer9HBTimerIdE (o = 0x00000000)
B6 = 0x85e0cf50 = _ZTV7CString (o = 0x00000008)
B7 = 0x4 = 4
B8 = 0x934ce9ac = _unlock (o = 0x00000000)
B9 = 0x85d2e200 = bmmRangeInfo (o = 0x00000000)
B10 = 0x14 = 20
NRP = 0x85cd2c00 = *:__cxa_vec_delete3 (o = 0x00000000)

Memory dumps from the addresses pointed by the registers (A4 and A10)

|0x1784fd0c: 0x00000000 |....| -> (null) o=0x0
|0x1784fd10: 0x00000000 |....| -> (null) o=0x0
|0x1784fd14: 0x00000000 |....| -> (null) o=0x0

|0x178d6c04: 0xd81a8417 |....| -> (null) o=0x0
|0x178d6c08: 0x0a000000 |....| -> (null) o=0x0
|0x178d6c0c: 0x0a000000 |....| -> (null) o=0x0
|0x178d6c10: 0x0cfd8417 |....| -> (null) o=0x0 -> LE: 0x1784fd0c

Are you able to explain the behavior? As can be seen in the attachment, the current compiler (CGT7.3.23) creates very different code, and the same phenomenon is not visible there.

Br,

Risto Alasaarela

  • 1782d480            _ZN7CVectorI7CStringE7reserveEj:
    1782d480       35f7           STW.D2T2      B11,*B15--[2]
    1782d482       3577           STW.D2T2      B10,*B15--[2]
    1782d484       31f7           STW.D2T2      B3,*B15--[2]
    1782d486       8577           STDW.D2T1     A11:A10,*B15--[1]
    1782d488   07bf005a           SUB.L2        B15,0x8,B15
    1782d48c       4646           MV.L1         A4,A10
    1782d48e       0247 ||        MV.L2         B4,B0
    1782d490   026666aa           MVK.S2        0xffffcccd,B4
    1782d494   0266666b           MVKH.S2       0xcccc0000,B4
    1782d498   0001205a ||        ADD.L2        9,B0,B0
    1782d49c   e1600040           .fphead       n, l, W, BU, nobr, nosat, 0001011b
    1782d4a0   00008632           MPY32U.M2     B4,B0,B1:B0
    1782d4a4   00004000           NOP           3
    1782d4a8   000469a2           SHRU.S2       B1,0x3,B0
    1782d4ac       641b           SHL.S2        B0,0x3,B1
    1782d4ae       0001 ||        ADD.L2        B0,B0,B0
    1782d4b0   0500207a           ADD.L2        B1,B0,B10
    1782d4b4   00284264           LDW.D1T1      *+A10[2],A0
    1782d4b8   00281bf8           CMPLTU.L1X    A0,B10,A0
    1782d4bc   e1100040           .fphead       p, l, W, BU, nobr, nosat, 0001000b
    1782d4c0   d08aa120    [!A0]  BNOP.S1       $C$L288 (PC+276 = 0x1782d5d4),5
    1782d4c4   0267f828           MVK.S1        0xffffcff0,A4
    1782d4c8   020bc668           MVKH.S1       0x178c0000,A4
    1782d4cc       000c           LDW.D1T1      *A4[0],A0
    1782d4ce       6c6e           NOP           4
    1782d4d0       1026           CMPLT.L1      0,A0,A0
    1782d4d2       ad3a    [!A0]  BNOP.S1       $C$L285 (PC+104 = 0x1782d528),5
    1782d4d4   00a8205a           ADD.L2        1,B10,B1
    1782d4d8   00046ca2           SHL.S2        B1,0x3,B0
    1782d4dc   e3008000           .fphead       n, l, W, BU, br, nosat, 0011000b
    1782d4e0   00003c42           ADDAW.D2      B0,B1,B0
    1782d4e4       9247           MV.L2X        A4,B4
    1782d4e6       104d           LDW.D2T2      *B4[0],B4
    1782d4e8   104ca413 ||        CALLP.S2      _Znaji (PC+156960 = 0x17853a00),B3
    1782d4ec   05a8205b ||        ADD.L2        1,B10,B11
    1782d4f0       9440 ||        ADD.L1X       B0,4,A4
    1782d4f2            $C$RL303:
    1782d4f2       0246           MV.L1         A4,A0
    1782d4f4   d0332120    [!A0]  BNOP.S1       $C$L286 (PC+102 = 0x1782d546),1
    1782d4f8   05908059           ADD.L1        4,A4,A11
    1782d4fc   e2400008           .fphead       n, l, W, BU, nobr, nosat, 0010010b
    1782d500   0271b028 ||        MVK.S1        0xffffe360,A4
    1782d504   020bc168           MVKH.S1       0x17820000,A4
    1782d508       05a6           MVK.L1        0,A3
    1782d50a       d247           MV.L2X        A4,B6
    1782d50c       8586 ||        MV.L1         A11,A4
    1782d50e       8b12 ||        MVK.S1        12,A6
    1782d510   04000041 ||        MVK.D1        0,A8
    1782d514   022c06a2 ||        MV.S2         B11,B4
    1782d518   10052613           CALLP.S2      $Tramp$S$$__cxa_vec_ctor (PC+10544 = 0x1782fe30),B3
    1782d51c   e18000e0           .fphead       n, l, W, BU, nobr, nosat, 0001100b
    1782d520   05ac2076 ||        STW.D1T2      B11,*-A11[1]
    1782d524            $C$RL304:
    1782d524       84ca           BNOP.S1       $C$L286 (PC+38 = 0x1782d546),4
    1782d526       6586           MV.L1         A11,A3
    1782d528            $C$L285:
    1782d528   0372202a           MVK.S2        0xffffe440,B6
    1782d52c   030bc16a           MVKH.S2       0x17820000,B6
    1782d530   10052013           CALLP.S2      $Tramp$S$$__cxa_vec_new (PC+10496 = 0x1782fe20),B3
    1782d534   02283059 ||        ADD.L1X       1,B10,A4
    1782d538       8e27 ||        MVK.L2        12,B4
    1782d53a       8312 ||        MVK.S1        4,A6
    1782d53c   e840b000           .fphead       n, l, W, BU, br, nosat, 1000010b
    1782d540   04000040 ||        MVK.D1        0,A8
    1782d544            $C$RL305:
    1782d544       6246           MV.L1         A4,A3
    1782d546            $C$L286:
    1782d546       01c6           MV.L1         A3,A0
    1782d548   c018a120    [ A0]  BNOP.S1       $C$L287 (PC+48 = 0x1782d570),5
    1782d54c   0026782a           MVK.S2        0x4cf0,B0
    1782d550   000bc2eb           MVKH.S2       0x17850000,B0
    1782d554   0267f828 ||        MVK.S1        0xffffcff0,A4
    1782d558   020bc669           MVKH.S1       0x178c0000,A4
    1782d55c   e0400000           .fphead       n, l, W, BU, nobr, nosat, 0000010b
    1782d560       bc05 ||        STW.D2T2      B0,*B15[1]
    1782d562       000c           LDW.D1T1      *A4[0],A0
    1782d564       8626           MVK.L1        4,A4
    1782d566       4c6e           NOP           3
    1782d568   1fc0dc13           CALLP.S2      AaSysLogPrint (PC-129312 = 0x1780dc40),B3
    1782d56c       cc05 ||        STW.D2T1      A0,*B15[2]
    1782d56e            $C$RL306:
    1782d56e       ae8a           BNOP.S1       $C$L288 (PC+116 = 0x1782d5d4),5
    1782d570            $C$L287:
    1782d570   00a82266           LDW.D1T2      *+A10[1],B1
    1782d574   020c0fd8           MV.L1         A3,A4
    1782d578   02286266           LDW.D1T2      *+A10[3],B4
    1782d57c   e1608000           .fphead       n, l, W, BU, br, nosat, 0001011b
    1782d580       65c6           MV.L1         A3,A11
    1782d582       0c6e           NOP           1
    1782d584   00046ca2           SHL.S2        B1,0x3,B0
    1782d588   00003c42           ADDAW.D2      B0,B1,B0
    1782d58c       0c6e           NOP           1
    1782d58e       d046           MV.L1X        B0,A6
    1782d590   1fd05412 ||        CALLP.S2      memcpy (PC-97632 = 0x17815820),B3
    1782d594            $C$RL307:
    1782d594   00282264           LDW.D1T1      *+A10[1],A0
    1782d598   02286264           LDW.D1T1      *+A10[3],A4
    1782d59c   e1200080           .fphead       n, l, W, BU, nobr, nosat, 0001001b
    1782d5a0       0627           MVK.L2        0,B4
    1782d5a2       2c6e           NOP           2
    1782d5a4       641a           SHL.S1        A0,0x3,A1
    1782d5a6       4402           SHL.S1        A0,0x2,A0
    1782d5a8   1fd06413           CALLP.S2      memset (PC-97504 = 0x178158c0),B3
    1782d5ac   03002078 ||        ADD.L1        A1,A0,A6
    1782d5b0            $C$RL308:
    1782d5b0   0362a02a           MVK.S2        0xffffc540,B6
    1782d5b4   030bc1ea           MVKH.S2       0x17830000,B6
    1782d5b8   10052013           CALLP.S2      $Tramp$S$$__cxa_vec_delete (PC+10496 = 0x1782fea0),B3
    1782d5bc   e0600000           .fphead       n, l, W, BU, nobr, nosat, 0000011b
    1782d5c0   02286265 ||        LDW.D1T1      *+A10[3],A4
    1782d5c4       8e27 ||        MVK.L2        12,B4
    1782d5c6       8726 ||        MVK.L1        4,A6
    1782d5c8            $C$RL309:
    1782d5c8   002c0fd8           MV.L1         A11,A0
    1782d5cc   00286274           STW.D1T1      A0,*+A10[3]
    1782d5d0   05284276           STW.D1T2      B10,*+A10[2]
    1782d5d4            $C$L288:
    1782d5d4   07bd005a           ADD.L2        8,B15,B15
    1782d5d8       c577           LDDW.D2T1     *++B15[1],A11:A10
    1782d5da       6c6e           NOP           4
    1782d5dc   e8400004           .fphead       n, l, W, BU, nobr, nosat, 1000010b
    1782d5e0   01bc52e6           LDW.D2T2      *++B15[2],B3
    1782d5e4   00006000           NOP           4
    1782d5e8   053c52e6           LDW.D2T2      *++B15[2],B10
    1782d5ec   00006000           NOP           4
    1782d5f0   05bc52e6           LDW.D2T2      *++B15[2],B11
    1782d5f4   00006000           NOP           4
    1782d5f8   008ca362           BNOP.S2       B3,5
    1782d5fc   00000000           NOP           
    

    17818380            _ZN7CVectorI7CStringE7reserveEj:
    17818380   1005a210           CALLP.S1      $Tramp$S$$__c6xabi_push_rts (PC+11536 = 0x1781b090),A3
    17818384            $C$RL154:
    17818384   07bf005b           SUB.L2        B15,0x8,B15
    17818388       b5c6 ||        MV.L1X        B3,A13
    1781838a       0247           MV.L2         B4,B0
    1781838c   05100fd8 ||        MV.L1         A4,A10
    17818390   026666aa           MVK.S2        0xffffcccd,B4
    17818394   0266666b           MVKH.S2       0xcccc0000,B4
    17818398   0001205a ||        ADD.L2        9,B0,B0
    1781839c   e0800020           .fphead       n, l, W, BU, nobr, nosat, 0000100b
    178183a0   00008632           MPY32U.M2     B4,B0,B1:B0
    178183a4   00004000           NOP           3
    178183a8   000469a2           SHRU.S2       B1,0x3,B0
    178183ac   00806ca2           SHL.S2        B0,0x3,B1
    178183b0   00041a42           ADDAH.D2      B1,B0,B0
    178183b4   05000fda           MV.L2         B0,B10
    178183b8   00284266           LDW.D1T2      *+A10[2],B0
    178183bc   e0100000           .fphead       p, l, W, BU, nobr, nosat, 0000000b
    178183c0   000149fa           CMPGTU.L2     B10,B0,B0
    178183c4   3098a120    [!B0]  BNOP.S1       $C$RL152 (PC+304 = 0x178184f0),5
    178183c8   0667542a           MVK.S2        0xffffcea8,B12
    178183cc   060bc66a           MVKH.S2       0x178c0000,B12
    178183d0   003002e6           LDW.D2T2      *+B12[0],B0
    178183d4       6c6e           NOP           4
    178183d6       1027           CMPLT.L2      0,B0,B0
    178183d8   303aa120    [!B0]  BNOP.S1       $C$L74 (PC+116 = 0x17818434),5
    178183dc   e4000000           .fphead       n, l, W, BU, nobr, nosat, 0100000b
    178183e0   05a8205a           ADD.L2        1,B10,B11
    178183e4   002c6ca2           SHL.S2        B11,0x3,B0
    178183e8   00017c42           ADDAW.D2      B0,B11,B0
    178183ec       8607           MV.L2         B12,B4
    178183ee       104d           LDW.D2T2      *B4[0],B4
    178183f0   104e0013 ||        CALLP.S2      _Znaji (PC+159744 = 0x1783f3e0),B3
    178183f4       9440 ||        ADD.L1X       B0,4,A4
    178183f6            $C$RL140:
    178183f6       4246           MV.L1         A4,A2
    178183f8   b0382120    [!A2]  BNOP.S1       $C$L75 (PC+112 = 0x17818450),1
    178183fc   e5000080           .fphead       n, l, W, BU, nobr, nosat, 0101000b
    17818400   01c91028           MVK.S1        0xffff9220,A3
    17818404   018bc0e8           MVKH.S1       0x17810000,A3
    17818408   0400a359           MVK.L1        0,A8
    1781840c   05800028 ||        MVK.S1        0x0000,A11
    17818410       d1c7           MV.L2X        A3,B6
    17818412       862e ||        ADDK.S1       4,A4
    17818414   06108059 ||        ADD.L1        4,A4,A12
    17818418   03018041 ||        MVK.D1        12,A6
    1781841c   e2000300           .fphead       n, l, W, BU, nobr, nosat, 0010000b
    17818420   022c06a2 ||        MV.S2         B11,B4
    17818424   10056613           CALLP.S2      $Tramp$S$$__cxa_vec_ctor (PC+11056 = 0x1781af50),B3
    17818428   05b02076 ||        STW.D1T2      B11,*-A12[1]
    1781842c            $C$RL142:
    1781842c   000c8120           BNOP.S1       $C$L75 (PC+48 = 0x17818450),4
    17818430   05b00fd8           MV.L1         A12,A11
    17818434            $C$L74:
    17818434   0349802a           MVK.S2        0xffff9300,B6
    17818438   030bc0ea           MVKH.S2       0x17810000,B6
    1781843c   10056413           CALLP.S2      $Tramp$S$$__cxa_vec_new (PC+11040 = 0x1781af40),B3
    17818440   02283059 ||        ADD.L1X       1,B10,A4
    17818444   04000029 ||        MVK.S1        0x0000,A8
    17818448   03008041 ||        MVK.D1        4,A6
    1781844c       8e27 ||        MVK.L2        12,B4
    1781844e            $C$RL144:
    1781844e       6646           MV.L1         A4,A11
    17818450            $C$L75:
    17818450       0586           MV.L1         A11,A0
    17818452       d2ba    [!A0]  BNOP.S1       $C$L77 (PC+148 = 0x178184d4),5
    17818454   00282264           LDW.D1T1      *+A10[1],A0
    17818458   02286266           LDW.D1T2      *+A10[3],B4
    1781845c   e3008000           .fphead       n, l, W, BU, br, nosat, 0011000b
    17818460       8586           MV.L1         A11,A4
    17818462       2c6e           NOP           2
    17818464   00806ca0           SHL.S1        A0,0x3,A1
    17818468   00041c40           ADDAW.D1      A1,A0,A0
    1781846c   10058413           CALLP.S2      $Tramp$S$$memcpy (PC+11296 = 0x1781b080),B3
    17818470   03000fd8 ||        MV.L1         A0,A6
    17818474            $C$RL146:
    17818474   00282264           LDW.D1T1      *+A10[1],A0
    17818478   02286264           LDW.D1T1      *+A10[3],A4
    1781847c   e0200000           .fphead       n, l, W, BU, nobr, nosat, 0000001b
    17818480       0627           MVK.L2        0,B4
    17818482       2c6e           NOP           2
    17818484   00806ca0           SHL.S1        A0,0x3,A1
    17818488   00041c40           ADDAW.D1      A1,A0,A0
    1781848c   10057613           CALLP.S2      $Tramp$S$$memset (PC+11184 = 0x1781b030),B3
    17818490   03000fd8 ||        MV.L1         A0,A6
    17818494            $C$RL148:
    17818494   01286264           LDW.D1T1      *+A10[3],A2
    17818498   04681028           MVK.S1        0xffffd020,A8
    1781849c   e0200000           .fphead       n, l, W, BU, nobr, nosat, 0000001b
    178184a0   0442e968           MVKH.S1       0x85d20000,A8
    178184a4       8e27           MVK.L2        12,B4
    178184a6       8726           MVK.L1        4,A6
    178184a8   b012a120    [!A2]  BNOP.S1       $C$RL150 (PC+36 = 0x178184c4),5
    178184ac   02286264           LDW.D1T1      *+A10[3],A4
    178184b0       6c6e           NOP           4
    178184b2       004c           LDW.D1T1      *A4[0],A4
    178184b4       6c6e           NOP           4
    178184b6       106c           LDW.D1T2      *A4[0],B6
    178184b8   02286265           LDW.D1T1      *+A10[3],A4
    178184bc   e6400000           .fphead       n, l, W, BU, nobr, nosat, 0110010b
    178184c0   10057412 ||        CALLP.S2      $Tramp$S$$__cxa_vec_delete3 (PC+11168 = 0x1781b060),B3
    178184c4            $C$RL150:
    178184c4            $C$L76:
    178184c4   002c0fd8           MV.L1         A11,A0
    178184c8   00286274           STW.D1T1      A0,*+A10[3]
    178184cc   05284276           STW.D1T2      B10,*+A10[2]
    178184d0   000ca120           BNOP.S1       $C$RL152 (PC+48 = 0x178184f0),5
    178184d4            $C$L77:
    178184d4   000da028           MVK.S1        0x1b40,A0
    178184d8   000bc268           MVKH.S1       0x17840000,A0
    178184dc   003c22f5           STW.D2T1      A0,*+B15[1]
    178184e0       8607 ||        MV.L2         B12,B4
    178184e2       100d           LDW.D2T2      *B4[0],B0
    178184e4       8626           MVK.L1        4,A4
    178184e6       4c6e           NOP           3
    178184e8   10056613           CALLP.S2      $Tramp$S$$AaSysLogPrint (PC+11056 = 0x1781b010),B3
    178184ec   003c42f6 ||        STW.D2T2      B0,*+B15[2]
    178184f0            $C$RL152:
    178184f0            $C$L78:
    178184f0   10056e11           CALLP.S1      $Tramp$S$$__c6xabi_pop_rts (PC+11120 = 0x1781b050),A3
    178184f4   07bd005b ||        ADD.L2        8,B15,B15
    178184f8   01b416a2 ||        MV.S2X        A13,B3
    178184fc   e0600000           .fphead       n, l, W, BU, nobr, nosat, 0000011b
    

    /*-----------------------------------------------------------------------------
     * Description:  Implementation for delete []
     *---------------------------------------------------------------------------*/
    void operator delete [](void *ptr)
    {
        if (ptr > reinterpret_cast<void*>(0x80000000))
        {
            AaMemUnRef((const void **)&ptr);
        }
        else
        {
            if (ptr) free(ptr);
        }
        // if (ptr) free(ptr);
    } /* delete [] */
    

    #ifndef VECTOR_HPP_
    #define VECTOR_HPP_
    #include <cstring>
    #include <mem.hpp>
    
    // allocation block size
    // size of allocated memory will usually be a multiple of this
    #define CVECTOR_BLOCKSIZE 10
    extern i32 g_poolId;
    
    // vector class template
    template<typename dataT> class CVector
    {
    protected:
        // number of elements in vector
        unsigned int m_numElements;
        // size of allocated buffer
        unsigned int m_bufferSize;
        // pointer to buffer
        dataT* m_buffer;
    public:
        // default constructor
        CVector() : m_numElements(0), m_bufferSize(0), m_buffer(0) {}
        // constructor with size and init value
        CVector(unsigned int argSize, const dataT& val = dataT())
            : m_numElements(0), m_bufferSize(0), m_buffer(0)
        {
            resize(argSize, val);
        }
        // destructor
        virtual ~CVector()
        {
            clear();
        }
    
        // copy operator for CVector
        CVector& operator=(const CVector& copyVector)
        {
            // check assignment to self
            if (this == &copyVector)
                return *this;
            // get new size
            unsigned int newSize = copyVector.size();
            if (newSize > m_bufferSize)
            {
                // reserve new buffer
                reserve(newSize);
                // if buffer is OK, copy each element of vector
                if (m_bufferSize >= newSize)
                {
                    for (int i = 0; i < newSize; i++)
                        m_buffer[i] = copyVector.m_buffer[i];
                    m_numElements = newSize;
                }
            }
            return *this;
        }  // operator=()
        // reserve buffer size for vector
        void reserve(unsigned int argSize)
        {
            dataT* tmpPtr;
            // calculate new buffer size as multiple of CVECTOR_BLOCKSIZE
            unsigned int newBufferSize = ((argSize + CVECTOR_BLOCKSIZE - 1) / CVECTOR_BLOCKSIZE) * CVECTOR_BLOCKSIZE;
            if (newBufferSize > m_bufferSize)
            {
                // if the new size is larger than the old
                // allocate new memory
                // allocate one additional element as end element
                if (g_poolId > 0)             // take from memory pool
                {
                    tmpPtr = new(g_poolId) dataT[newBufferSize + 1];
                }
                else
                {
                    // take from heap
                    tmpPtr = new dataT[newBufferSize + 1];
                }
                if (tmpPtr)
                {
                    // copy old buffer to new buffer
                    std::memcpy(tmpPtr, m_buffer, m_numElements * sizeof(dataT));
                    // clear copied buffer area, so that we can delete it (this calls the destructors, which should do nothing).
                    std::memset(m_buffer, 0, m_numElements * sizeof(dataT));
                    // delete old buffer
                    delete [] m_buffer;
                    // set buffer pointer and size
                    m_buffer = tmpPtr;
                    m_bufferSize = newBufferSize;
                }
                else
                {
                    AaSysLogPrint(EAaSysLogSeverityLevel_Error, "allocate heap failed.g_poolId : %x", g_poolId);
                }
            }  // if (newBufferSize > m_bufferSize)
        }  // reserve()
        unsigned int size() const
        {
            return m_numElements;
        }
        unsigned int capacity() const
        {
            return m_bufferSize;
        }
        dataT* begin() const
        {
            return m_buffer;
        }  // begin()
        dataT* end() const
        {
            if (m_buffer)
                return m_buffer + m_numElements;
            else
                return 0;
        }  // end()
        dataT& front()
        {
            return m_buffer[0];
        }
        const dataT& front() const
        {
            return m_buffer[0];
        }
        dataT& back()
        {
            return m_buffer[m_numElements - 1];
        }
        const dataT& back() const
        {
            return m_buffer[m_numElements - 1];
        }
        // add element at end of vector
        void push_back(const dataT& data = dataT())
        {
            // if buffer is too small for additional element,
            // allocate new buffer
            if (m_numElements + 1 > m_bufferSize)
                reserve(m_numElements + 1);
            // if the buffer is now large enough
            if (m_numElements + 1 <= m_bufferSize)
            {
                // add new element as last element
                m_buffer[m_numElements] = data;
                // increment number of elements
                m_numElements++;
            }
        }  // push_back()
        // remove last element from vector
        void pop_back()
        {
            if (m_numElements > 0)
            {
                m_numElements--;
            }
        }  // pop_back()
        dataT& operator[](unsigned int index)
        {
            return m_buffer[index];
        }
        const dataT& operator[](unsigned int index) const
        {
            return m_buffer[index];
        }
        // resize vector
        void resize(unsigned int argSize, const dataT& val = dataT())
        {
            // if the new size is smaller than the old size
            // we leave the content and just set the new size
            if (argSize <= m_numElements)
            {
                m_numElements = argSize;
            }
            // if the new size is larger than the old size,
            // but smaller than the allocated buffer,
            // we initialize all newly created elements to val and
            // set the new vector size
            else if (argSize <= m_bufferSize)
            {
                // initialize new buffer area to data
                for (int i = m_numElements; i < argSize; i++)
                    m_buffer[i] = val;
                m_numElements = argSize;
            }
            // if the buffer is too small for the new size,
            // we enlarge the buffer and then set all newly
            // created elements to val
            else
            {
                // reserve a larger buffer
                reserve(argSize);
                if (argSize <= m_bufferSize)
                {
                    // initialize new buffer area to data
                    for (int i = m_numElements; i < argSize; i++)
                        m_buffer[i] = val;
                    m_numElements = argSize;
                }
            }
        }  // resize()
        void clear()
        {
            // free buffer memory, calls destructor for each element
            if (m_buffer) delete [] m_buffer;
            m_buffer = 0;
            m_numElements = 0;
            m_bufferSize = 0;
        }
    };  // class CVector
    
    #endif /*VECTOR_HPP_*/
    

  • I presume you know which C++ source file instantiates the problem instance of template<typename dataT> class CVector. For this source file, please follow the directions in the article How to Submit a Compiler Test Case.

    I want to clarify one thing. In this sequence of instructions ...

    Risto Alasaarela1 said:
    178184b2 004c LDW.D1T1 *A4[0],A4
    178184b4 6c6e NOP 4
    178184b6 106c LDW.D1T2 *A4[0],B6  -> This read causes points to zero address, causing the NMI

    The LDW at address 0x178184b2 loads the value zero into A4. The LDW at address 0x178184b6 attempts to access memory location 0, and this causes the NMI.  Is this description correct?

    Thanks and regards,

    -George

  • Hello!

    The LDW at address 0x178184b2 loads the value zero into A4. The LDW at address 0x178184b6 attempts to access memory location 0, and this causes the NMI.  Is this description correct?

    Yes, this is correct.

    Please find the preprocessed example file as attached.

    Br,

    Risto

    rtm.zip

  • Unfortunately, I am unable to reproduce the issue.  I had to guess at the compiler flags, and I cannot seem to find the same ones you used.  Please show the entire invocation of the compiler when this source file is built.

    Thanks and regards,

    -George

  • Hello!

    Here are the requested flags:

    --mem_model:data=far -pdse9 -pdse48 -pdse190 -pdse225 -pdse262 -pdse849 -pdse994 -mi1000 -mv6600 -mo --strip_coff_underscore
    -pden -pds1 -pds69 -pds112 -pds195 -pds238 -pds880 -pds885 -pds403 -pds681
    -g -ms0 -o0 --preproc_with_comment --preproc_with_compile

    Br,

    Risto

  • I plan to file an SDOWP entry against the compiler.  I'll do that tomorrow and let you know the ID number.  In the meantime, I want to let you know I am confident a workaround is to add code to not call array delete when the m_buffer data member is NULL.  Something similar to ...

    if (m_buffer)
        delete [] m_buffer;
    

    Make this change inside the member function reserve in the template class CVector.

    Thanks and regards,

    -George

  • Hello!

    Yes, the proposed solution works for this case. However, how on earth we can be sure that this same problem does not exist anywhere else in the code (with different symptoms)? This kind of problem can be even hidden in our SW stack having tens of thousands of code lines, due to the fact that all of the code lines cannot be tested in the real HW...

    Br,

    Risto

  • Unfortunately, I cannot explain why this happened.  So, I filed the entry CODEGEN-7034 in the SDOWP system to have this issue investigated.  You are welcome to follow it with the SDOWP link below in my signature.

    Thanks and regards,

    -George

  • Hello!

    I cannot find the mentioned ticket in SDOWP system. Are you able to estimate the timeline for the feedback for the problem? What is the priority of the investigation?

    Br,

    Risto

  • Something appears to be wrong with SDOWP.  I'll contact the team responsible for it.

    Analysis of the problem has started, but it is not complete.  Until then, no estimate can be made.  I can tell you that, for problems of similar complexity, a fix was available in a release a few months later.

    Thanks and regards,

    -George

  • Hello!

    I have good news to share.We have observed, that CGT8 behaves with this piece of code exactly in the same way as with GCC compiler. Our interpretation is that the call of memset cleared vptr used in the virtual destructor of the class. By changing the function implementation like this, the problem disappeared:

    void reserve(unsigned int argSize)
    {
        dataT* tmpPtr;
        // calculate new buffer size as multiple of CVECTOR_BLOCKSIZE
        unsigned int newBufferSize = ((argSize + CVECTOR_BLOCKSIZE - 1) / CVECTOR_BLOCKSIZE) * CVECTOR_BLOCKSIZE;
        if (newBufferSize > m_bufferSize)
        {
            // if the new size is larger than the old
            // allocate new memory
            // allocate one additional element as end element
            if (g_poolId > 0) // take from memory pool
            {
                 tmpPtr = new(g_poolId) dataT[newBufferSize + 1];
             }
            else
            {
                // take from heap
                tmpPtr = new dataT[newBufferSize + 1];
            }
            if (tmpPtr)
            {

                    // copy old buffer to new buffer                                                

                    for (i = 0; i < m_numElements; i++)

                    {

                        tmpPtr[i] = m_buffer[i];

                    }

                delete [] m_buffer;

                // set buffer pointer and size
                m_buffer = tmpPtr;
                m_bufferSize = newBufferSize;
            }
            else
            {
                 AaSysLogPrint(EAaSysLogSeverityLevel_Error, "allocate heap failed.g_poolId : %x", g_poolId);
            }
        } // if (newBufferSize > m_bufferSize)
    } // reserve()

    The fact that CGT7 works differently remains still unclear. However, this is not our main focus at the moment. I would say that this ticket can be closed, since the expectation is that CGT8 works as expected with this piece of code.

    Thank you!

    Br,

    Risto