繁体   English   中英

读取访问冲突。 _Mycont在C ++中将udp数据转换为向量时出现nullptr错误

[英]Read access violation. _Mycont was nullptr error while getting udp data into vectors in C++

[未解决]

我读了此错误文章,我知道在哪种情况下会发生此错误,但是我尝试在代码中找到这种情况,但我一直在努力寻找问题的根源。

总体代码说明:

我从以太网中获取UDP数据包,并通过计算丢失的片段数来分析我的用户创建的标头,以查看是否有丢失的片段(数据包)。 lostFragmentCount++ )在执行此操作时,我在while循环中将数据(数据包)连接到数组中。 FrameFragmentNoPrevFrameFragmentNo可以看作是跟踪帧以检测丢失的片段的指针。

有问题的部分是在此行之后concatAry.insert(it+intData.size(),GetIntArrayFromByteArray(vec).begin(), GetIntArrayFromByteArray(vec).end());

在他的那行,我抛出了异常:读取访问冲突。 _Mycont为nullptr。 错误。 当它第三次调用GetIntArrayFromByteArray()方法时。 (它不会给错误,他的第一名)

我在转换时放置了断点来跟踪那些数组的大小,它看起来是正确的,我怀疑当我们在获取数据的同时从以太网中获取大量数据时,它可能会溢出,但是如果是这种情况,缓冲区应该在进入while之前给出错误。

问题可能源于insert()方法的使用 我想弄清楚。

我不明白为什么要经过一段时间(从以太网获取数据的第n次迭代)后出现此错误。 有人有主意吗?

相关变量

char buf[1550];//message gets here

uint16_t MessageID = 0;
uint16_t MessageLength = 0;
uint32_t FrameCount = 0;
uint16_t TotalFragmentCount = 0;
uint16_t FrameFragmentNo = 0;
uint16_t Reserved = 0;
uint16_t SkipFrameFlag = 1;
uint16_t PrevFrameFragmentNo =0;
uint16_t Ethernet_Packet_Header_Length = 14;
vector<uint16_t> intData;
uint32_t PrevFrameCount = 0;
int ReceivedFrameCount = 0;
int ReceivedFrameLen;
int lostFragmentCount = 0;
uint64_t NumberofFrame = 0;

这是我的while循环,它采用udp数据包剥离(移位)用户创建的标头来保存其余数据:

while (true)
        {
            ZeroMemory(&client, clientLength); // Clear the client structure
            ZeroMemory(buf, 1550); // Clear the receive buffer

            // Wait for message
            int bytesIn = recvfrom(in, buf, 1550, 0, (sockaddr*)&client, &clientLength);

            if (bytesIn == SOCKET_ERROR)
            {
                cout << "Error receiving from client " << WSAGetLastError() << endl;
                continue;
            }


            //parse the user created header for further use
            MessageID = (uint16_t)(buf[0] << 8 | buf[1]);
            FrameCount = (uint32_t)(buf[2] << 24 | buf[3] << 16 | buf[4] << 8 | buf[5] << 0);
            TotalFragmentCount = (uint16_t)(buf[6] << 8 | buf[7]);
            FrameFragmentNo = (uint16_t)(buf[8] << 8 | buf[9]);
            Reserved = (uint16_t)(buf[10] << 8 | buf[11]);
            MessageLength = (uint16_t)(buf[12] << 8 | buf[13]);


            if (FrameFragmentNo == 1 && SkipFrameFlag == 1)  // After the skip flag, catch the start of frame.
            {
                SkipFrameFlag = 0;
                PrevFrameFragmentNo = 0;
                //Array.Clear(intData, 0, intData.Length);
            }

            if (FrameFragmentNo != (PrevFrameFragmentNo + 1)) //Fragment is lost. Skip Frame
            {
                SkipFrameFlag = 1;
                lostFragmentCount++;
            }


            if (SkipFrameFlag == 1)
                continue;

            //skip user created header
            int shift = 14;
            int length = sizeof(buf);
            memmove(buf, buf + shift, length - shift);
            memset(buf + length - shift, '0', shift);

            //char buf ----> vecor<char> vec
            int n = sizeof(buf) / sizeof(*buf);//number of elements
            vector<char> vec(buf, buf + n);

            if (FrameFragmentNo == 1)// First fragment
            {
                intData = GetIntArrayFromCharArray(vec);
                PrevFrameFragmentNo = FrameFragmentNo;
            }
            else if (FrameFragmentNo <= TotalFragmentCount)  // Other Fragments
            {
            std::vector<uint16_t>::iterator it;


            vector<uint16_t> concatAry;
            it = concatAry.begin();

            concatAry.insert(concatAry.begin(), intData.begin(), intData.end());


            concatAry.insert(it + intData.size(),GetIntArrayFromCharArray(vec).begin(), GetIntArrayFromCharArray(vec).end());


            intData = concatAry;
            PrevFrameFragmentNo = FrameFragmentNo;
            count++;
}


            if (FrameFragmentNo == TotalFragmentCount && intData.size() != 0) // Frame Fragmentation Completed
            {
                PrevFrameFragmentNo = 0;
                PrevFrameCount = FrameCount;
                ReceivedFrameCount++;
                ReceivedFrameLen = intData.size();

                //apply till here 

                    NumberofFrame++;
            }
            //Write data into a file 
            filePutContents("C:\\Users\\Dell\\UDPClientServerBasic\\UDP_Server\\UDP_Server\\recordings.txt", intData, true);


        }//end of while 

这是GetIntArrayFromCharArray()方法

     vector<uint16_t> GetIntArrayFromCharArray(vector<char> arr)
        {
            // If the number of bytes is not even, put a zero at the end
            if ((arr.size() % 2) == 1)
                arr.resize(arr.size()+1);
            //arr.push_back(0);


            vector<uint16_t> intArray;

            for (int i = 0; i < arr.size(); i += 2)
                intArray.push_back((uint16_t)((arr[i] << 8) | arr[i + 1]));

    /*arr[i + 1] gives warning saying "Arithmetic overflow: Using operator '+' on a 4 byte value 
and then casting the result to a 8 byte value." 

But I don't think this could be a issue since it is just for loop's iterator
    */
            return intArray;
        }

[EDIT]更清晰地查看错误

第一次追踪 很重要的一点 2,跟踪出现错误 错误镜头

迭代器it = concatAry.begin(); 第一次插入后无效。 在第二个插入中使用concatAry.begin()代替it

concatAry.insert(concatAry.begin()+intData.size(),GetIntArrayFromCharArray(vec).begin(), , GetIntArrayFromCharArray(vec).end());

似乎在假定std::copy时使用了insert insert之前使用std::copy或删除大小构造函数(使用vector<uint16_t> concatAry;不带size参数)。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM