Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. Dismiss Notice

unity crash in IL2CPP RELEASE scriptping backend

Discussion in 'Scripting' started by HatteFox, Feb 4, 2021.

  1. HatteFox

    HatteFox

    Joined:
    Jan 20, 2021
    Posts:
    12
    Hello everyone!
    Maybe my technical level is not enough, this question makes me very difficult to understand!
    I have a program that can write Buffer,this is the code
    Code (CSharp):
    1.  
    2. public class WriteBuffer
    3. {
    4.     private byte[] beginPtr;
    5.  
    6.     private int position;
    7.  
    8.     private int length;
    9.  
    10.     public WriteBuffer(int len)
    11.     {
    12.         beginPtr = new byte[len];
    13.         position = 0;
    14.         length = 0;
    15.         if (beginPtr != null)
    16.         {
    17.             length = len;
    18.         }
    19.     }
    20.  
    21.     public PbError.ErrorType writeUInt8(byte src)
    22.     {
    23.         if (beginPtr == null)
    24.         {
    25.             return PbError.ErrorType.PB_ERR_ARG_IS_NULL;
    26.         }
    27.  
    28.         if (1 > length - position)
    29.         {
    30.             return PbError.ErrorType.PB_ERR_WRITE_BUFF_INSUFFIX;
    31.         }
    32.  
    33.         beginPtr[position++] = src;
    34.         return PbError.ErrorType.PB_NO_ERROR;
    35.     }
    36.  
    37.     public PbError.ErrorType writeInt32(int src)
    38.     {
    39.         if (beginPtr == null)
    40.         {
    41.             return PbError.ErrorType.PB_ERR_ARG_IS_NULL;
    42.         }
    43.  
    44.         if (4 > length - position)
    45.         {
    46.             return PbError.ErrorType.PB_ERR_WRITE_BUFF_INSUFFIX;
    47.         }
    48.  
    49.         if (BitConverter.IsLittleEndian)
    50.         {
    51.             src = IPAddress.HostToNetworkOrder(src);
    52.         }
    53.  
    54.         WriteBytes(src, beginPtr, ref position);
    55.         return PbError.ErrorType.PB_NO_ERROR;
    56.     }
    57.  
    58.     public PbError.ErrorType writeInt64(long src)
    59.     {
    60.         if (beginPtr == null)
    61.         {
    62.             return PbError.ErrorType.PB_ERR_ARG_IS_NULL;
    63.         }
    64.  
    65.         if (8 > length - position)
    66.         {
    67.             return PbError.ErrorType.PB_ERR_WRITE_BUFF_INSUFFIX;
    68.         }
    69.  
    70.         if (BitConverter.IsLittleEndian)
    71.         {
    72.             src = IPAddress.HostToNetworkOrder(src);
    73.         }
    74.  
    75.         WriteBytes(src, beginPtr, ref position);
    76.         return PbError.ErrorType.PB_NO_ERROR;
    77.     }
    78.  
    79.     public unsafe void WriteBytes(int val, byte[] dest, ref int offset)
    80.     {
    81.         if (dest == null)
    82.         {
    83.             throw new ArgumentNullException("dest");
    84.         }
    85.  
    86.         if (offset < 0 || offset + 4 > dest.Length)
    87.         {
    88.             throw new ArgumentNullException("offset");
    89.         }
    90.  
    91.         fixed (byte* ptr = dest)
    92.         {
    93.             *(int*)(ptr + offset) = val;
    94.         }
    95.  
    96.         offset += 4;
    97.     }
    98.  
    99.     public unsafe void WriteBytes(long val, byte[] dest, ref int offset)
    100.     {
    101.         if (dest == null)
    102.         {
    103.             throw new ArgumentNullException("dest");
    104.         }
    105.  
    106.         if (offset < 0 || offset + 8 > dest.Length)
    107.         {
    108.             throw new ArgumentNullException("offset");
    109.         }
    110.  
    111.         fixed (byte* ptr = dest)
    112.         {
    113.             *(long*)(ptr + offset) = val;
    114.         }
    115.  
    116.         offset += 8;
    117.     }
    118. }
    119.  
    and a test code here:write byte value first

    Code (CSharp):
    1.  
    2. public class Main : MonoBehaviour
    3. {
    4.     private byte byte1;
    5.     private long long1;
    6.     private int int1;
    7.  
    8.     private const string LOG_FILTER_TAG = "SELF_LOG: ";
    9.     WriteBuffer writeBuf = new WriteBuffer(1024);
    10.  
    11.     private void Start()
    12.     {
    13.         byte1 = 1;
    14.         long1 = 10L;
    15.         int1 = 100;
    16.     }
    17.  
    18.     private void OnGUI()
    19.     {
    20.         if (GUILayout.Button("Write To Buffer", GUILayout.Height(100f), GUILayout.Width(200f)))
    21.         {
    22.             //write byte
    23.             var ret = writeBuf.writeUInt8(byte1);
    24.             Debug.Log(LOG_FILTER_TAG + (ret == PbError.ErrorType.PB_NO_ERROR ? "Byte Success" : ret.ToString()));
    25.             //write long
    26.             ret = writeBuf.writeInt64(long1);
    27.             Debug.Log(LOG_FILTER_TAG + (ret == PbError.ErrorType.PB_NO_ERROR ? "long Success" : ret.ToString()));
    28.             //write int
    29.             ret = writeBuf.writeInt32(int1);
    30.             Debug.Log(LOG_FILTER_TAG + (ret == PbError.ErrorType.PB_NO_ERROR ? "int Success" : ret.ToString()));
    31.  
    32.         }
    33.     }
    34. }
    35.  
    36.  
    I made an Android apk which scripting backend is IL2CPP RELEASE and ran it .The crash happened when I executed the code in OnGUI.The log found this content:signal 7 (SIGBUS), code 1 (BUS_ADRALN) !This means there is a problem with the memory alignment,Then I used libil2cpp.sym.so to locate the problem in the line of code
    Code (CSharp):
    1.  *(long*)(ptr + position) = val;
    I guess this may be because I first wrote a byte, and then wrote a long at the Offset + ptr, but the address of this position is not a multiple of 8, so it crashed.
    Then I changed my code:write long value first
    Code (CSharp):
    1.    
    2.     private void OnGUI()
    3.     {
    4.         if (GUILayout.Button("Write To Buffer", GUILayout.Height(100f), GUILayout.Width(200f)))
    5.         {
    6.            
    7.             //write long
    8.            var ret = writeBuf.writeInt64(long1);
    9.             Debug.Log(LOG_FILTER_TAG + (ret == PbError.ErrorType.PB_NO_ERROR ? "long Success" : ret.ToString()));
    10.             //write byte
    11.             ret = writeBuf.writeUInt8(byte1);
    12.             Debug.Log(LOG_FILTER_TAG + (ret == PbError.ErrorType.PB_NO_ERROR ? "Byte Success" : ret.ToString()));
    13.             //write int
    14.             ret = writeBuf.writeInt32(int1);
    15.             Debug.Log(LOG_FILTER_TAG + (ret == PbError.ErrorType.PB_NO_ERROR ? "int Success" : ret.ToString()));
    16.  
    17.         }
    18.     }
    19.  
    Just such a change does not crash anymore.This is also something that makes me very confused,Why won't it crash this time.After writing byte, write int again. At this time, offset+ptr is definitely not a multiple of 4, but why doesn't it crash anymore?Did I understand something wrong?
    By the way, the crash is only issued in IL2CPP RELEASE,IL2CPP DEBUG or Mono will not.
     
    Last edited: Feb 5, 2021
  2. HatteFox

    HatteFox

    Joined:
    Jan 20, 2021
    Posts:
    12
    No one replied to me:(