Description
Sometimes I get exception 3 when trying to clear() a std::vector.
Hardware
Hardware: ESP-07S
ESP8266-Arduino library core version: 2.4.0-rc1
Settings in IDE
Module: Generic ESP8266 Module
Flash Size: 4MB
CPU Frequency: 160Mhz
Flash Mode: qio
Flash Frequency: 40Mhz
Upload Using: OTA / SERIAL
Reset Method: ck
Stacktrace
This is stacktrace from Arduino's Exception Decoder:
Exception 3: LoadStoreError: Processor internal physical address or data error during load or store
Decoding 30 results
0x401000b7: umm_disconnect_from_free_list at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266\umm_malloc/umm_malloc.c line 1151
0x4021e9bc: memmove at /Users/igrokhotkov/e/newlib-xtensa/xtensa-lx106-elf/newlib/libc/string/../../../.././newlib/libc/string/memmove.c line 69 (discriminator 1)
0x40217464: Print::write(unsigned char const*, unsigned int) at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266/Print.cpp line 38
0x4010020c: _umm_free at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266\umm_malloc/umm_malloc.c line 1287
0x4010068c: free at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266\umm_malloc/umm_malloc.c line 1733
0x40215b04: operator delete(void*) at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266/abi.cpp line 57
0x40207940: std::_Vector_base >::_M_deallocate(double*, unsigned int) at C:\Users\Defozo\Documents\Arduino\jeszcze nowsza wersja laser_na_stacje_v2\laser_na_stacje_v2/laser_na_stacje_v2.ino line 565
0x402088ac: std::_Vector_base >::~_Vector_base() at c:\users\defozo\appdata\local\arduino15\packages\esp8266\tools\xtensa-lx106-elf-gcc\1.20.0-26-gb404fb9-2\xtensa-lx106-elf\include\c++\4.8.2\bits/stl_vector.h line 161
0x40209748: std::vector >::_M_erase_at_end(double*) at c:\users\defozo\appdata\local\arduino15\packages\esp8266\tools\xtensa-lx106-elf-gcc\1.20.0-26-gb404fb9-2\xtensa-lx106-elf\include\c++\4.8.2\bits/stl_vector.h line 1353
: (inlined by) std::vector >::clear() at c:\users\defozo\appdata\local\arduino15\packages\esp8266\tools\xtensa-lx106-elf-gcc\1.20.0-26-gb404fb9-2\xtensa-lx106-elf\include\c++\4.8.2\bits/stl_vector.h line 1126
: (inlined by) loop at C:\Users\Defozo\Documents\Arduino\jeszcze nowsza wersja laser_na_stacje_v2\laser_na_stacje_v2/laser_na_stacje_v2.ino line 412
0x40217082: std::default_delete ::operator()(TransportTraits*) const at c:\users\defozo\appdata\local\arduino15\packages\esp8266\tools\xtensa-lx106-elf-gcc\1.20.0-26-gb404fb9-2\xtensa-lx106-elf\include\c++\4.8.2\bits/unique_ptr.h line 68
0x4010020c: _umm_free at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266\umm_malloc/umm_malloc.c line 1287
0x401020ea: wDev_ProcessFiq at ?? line ?
0x40215d84: loop_wrapper at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266/core_esp8266_main.cpp line 124
0x4010070c: cont_norm at C:\Users\Defozo\AppData\Local\Arduino15\packages\esp8266\hardware\esp8266\2.4.0-rc1\cores\esp8266/cont.S line 109
This is reset cause:
Hardware Watchdog
Fatal exception:4 flag:1 (WDT) epc1:0x40000f83 epc2:0x00000000 epc3:0x4000dd3b excvaddr:0x40023c5c depc:0x00000000
Code
I'm initializing vectors like that:
std::vector<double> dhtTempVector, dhtHumidityVector;
std::vector<double> dhtTempMedianVector, dhtHumidityMedianVector;
std::vector<double> bmpTempVector, bmpPressureVector;
std::vector<double> bmpTempMedianVector, bmpPressureMedianVector;
dhtTempVector.reserve(5);
dhtHumidityVector.reserve(5);
bmpTempVector.reserve(5);
bmpPressureVector.reserve(5);
dhtTempMedianVector.reserve(6);
dhtHumidityMedianVector.reserve(6);
bmpPressureMedianVector.reserve(6);
bmpTempMedianVector.reserve(6);
Inserting new values like that:
if (!isnan(temp) && !isnan(hum)) {
dhtTempVector.push_back(temp);
dhtHumidityVector.push_back(hum);
}
and:
if (!dhtTempVector.empty()) {
dhtTempMedianVector.push_back(median(dhtTempVector));
dhtTempVector.clear();
}
if (!dhtHumidityVector.empty()) {
dhtHumidityMedianVector.push_back(median(dhtHumidityVector));
dhtHumidityVector.clear(); //line number 412
}
This is the median function:
double median(std::vector<double> v)
{
size_t n = v.size() / 2;
std::nth_element(v.begin(), v.begin()+n, v.end());
double vn = v[n];
if(v.size()%2 == 1) {
return vn;
} else {
std::nth_element(v.begin(), v.begin()+n-1, v.end());
return 0.5*(vn+v[n-1]);
}
}
Additional debug information
This is a result:
dhtTempVector size: 4
dhtTempMedianVector size: 5
dhtHumidityVector size: 4
dhtHumidityMedianVector size: 5
29.00 29.00 29.00 29.00 --
28.70 28.75 28.80 28.90 28.90 --
41.20 41.30 41.80 41.40 --
42.65 42.55 41.80 42.30 41.75 --
of these lines of code:
Serial.print("dhtTempVector size: ");
Serial.println(dhtTempVector.size());
Serial.print("dhtTempMedianVector size: ");
Serial.println(dhtTempMedianVector.size());
Serial.print("dhtHumidityVector size: ");
Serial.println(dhtHumidityVector.size());
Serial.print("dhtHumidityMedianVector size: ");
Serial.println(dhtHumidityMedianVector.size());
for (int k = 0; k < dhtTempVector.size(); ++k) {
Serial.print(dhtTempVector.at(k));
Serial.print(" ");
}
Serial.println("--");
for (int k = 0; k < dhtTempMedianVector.size(); ++k) {
Serial.print(dhtTempMedianVector.at(k));
Serial.print(" ");
}
Serial.println("--");
for (int k = 0; k < dhtHumidityVector.size(); ++k) {
Serial.print(dhtHumidityVector.at(k));
Serial.print(" ");
}
Serial.println("--");
for (int k = 0; k < dhtHumidityMedianVector.size(); ++k) {
Serial.print(dhtHumidityMedianVector.at(k));
Serial.print(" ");
}
Serial.println("--");
just before the exception is thrown.
Summary
It looks like the exception is thrown during clearing the vector. I think I experienced exceptions thrown at the end of the loop() function too - so at the time when destructors of the vectors are fired. I'd think it's a problem with destroying the elements of the vectors but they're just double numbers.
What could be the problem?
#Edit
The Arduino-ESP8266 library that I'm using is available here:
https://github.com/esp8266
Here is umm_malloc.c:
https://github.com/esp8266/Arduino/blob/master/cores/esp8266/umm_malloc/umm_malloc.c
Print.cpp:
https://github.com/esp8266/Arduino/blob/4897e0006b5b0123a2fa31f67b14a3fff65ce561/cores/esp8266/Print.cpp
cont.S:
https://github.com/esp8266/Arduino/blob/4897e0006b5b0123a2fa31f67b14a3fff65ce561/cores/esp8266/cont.S
Specific lines from umm_malloc.c:
1151:
UMM_NFREE(UMM_PFREE(c)) = UMM_NFREE(c);
https://github.com/esp8266/Arduino/blob/master/cores/esp8266/umm_malloc/umm_malloc.c#L1151
1287:
if( UMM_NBLOCK(UMM_PBLOCK(c)) & UMM_FREELIST_MASK ) {
https://github.com/esp8266/Arduino/blob/master/cores/esp8266/umm_malloc/umm_malloc.c#L1287
1733:
void umm_free( void *ptr ) {
ptr = GET_UNPOISONED(ptr);
/* check poison of each blocks, if poisoning is enabled */
if (!CHECK_POISON_ALL_BLOCKS()) {
return;
}
/* check full integrity of the heap, if this check is enabled */
if (!INTEGRITY_CHECK()) {
return;
}
_umm_free( ptr );
} //1733
https://github.com/esp8266/Arduino/blob/master/cores/esp8266/umm_malloc/umm_malloc.c#L1733
Specific line from Print.cpp:
size_t Print::write(const uint8_t *buffer, size_t size) {
size_t n = 0;
while(size--) {
n += write(*buffer++); //line number 38
}
return n;
}
https://github.com/esp8266/Arduino/blob/4897e0006b5b0123a2fa31f67b14a3fff65ce561/cores/esp8266/Print.cpp#L38
Specific line from core_esp8266_main.cpp:
static void loop_wrapper() {
static bool setup_done = false;
preloop_update_frequency();
if(!setup_done) {
setup();
#ifdef DEBUG_ESP_PORT
DEBUG_ESP_PORT.setDebugOutput(true);
#endif
setup_done = true;
}
loop();
run_scheduled_functions(); //line number 124
esp_schedule();
}
Line number 109 from cont.S:
https://github.com/esp8266/Arduino/blob/4897e0006b5b0123a2fa31f67b14a3fff65ce561/cores/esp8266/cont.S#L109
Related
An error sometimes occurs during program running.
It doesn't happen every time.
I don't know why I get an error in this part.
The length of strAckData is greater than 13
x_FWCommunity->sRevDataStr = strAckData.GetAt(13); '
User SourceCode
void CMLT2App::AckTotalFusingMsg(CString strAckData)
{
char szLog[512];
CString strCmd(""), strResult(""), strTemp(""), strLen("");
char cResult;
int nCmd = 0, nPos = 0, nDataLen = 0;
strTemp = strAckData;
nPos = strTemp.Find(0x02);
strAckData = strTemp.Mid(nPos, strAckData.GetLength() - nPos);
if (strAckData.GetAt(0) != 0x02) return; // Check STX
if (strAckData.GetAt((strAckData.GetLength() - 1)) != 0x03) // Check ETX
return;
strCmd.Format("%s", strAckData.Mid(7, 2)); // Get Command;
sscanf(strCmd, "%X", &nCmd); // String Convert to Hex
cResult = strAckData.GetAt(13); // String Convert to Decimal
x_FWCommunity->sRevCmdStr = strCmd;
strLen.Format("%s", strAckData.Mid(9, 4));
sscanf(strLen, "%X", &nDataLen);
// strCmd 는 0xBD
if (strCmd == "FE" || strCmd == "5E")
{
x_FWCommunity->sRevDataStr = strAckData.Mid(13, nDataLen);
// AfxMessageBox(x_FWCommunity->sRevDataStr);
}
else
x_FWCommunity->sRevDataStr = strAckData.GetAt(13); ← Error Point
switch (nCmd)
{
case CMD_CTRL_FUSING_SYSTEM:
case CMD_CTRL_FUSING_CONTROL_PTN:
case CMD_CTRL_FUSING_PREDISP_PTN:
Call Stack Log
MSVCRTD! 102136a8()
MSVCRTD! 102135b1()
operator delete(void * 0x01a11f28) line 351 + 12 bytes
CString::FreeData() line 146 + 15 bytes
CString::Release() line 157
CString::AllocBeforeWrite(int 1) line 200
CString::AssignCopy(int 1, const char * 0x01e2e684) line 315
CString::operator=(char 48) line 88
CMLT2App::AckTotalFusingMsg(CString {"A2A100BD002300375000011320373000000630331000000C3"}) line 6029
CMLT2App::RS232C_ReceivedFusingInfo(unsigned char * 0x01e2eb8c) line 5412
ThreadWatchComm1(CPortController * 0x01514010) line 966
KERNEL32! 7c7db729()
I have some constraints where the addon is built with nan.h and v8 (not the new node-addon-api).
The end function is a part of a library. It accepts std::vector<char> that represents the bytes of an image.
I tried creating an image buffer from Node.js:
const img = fs.readFileSync('./myImage.png');
myAddonFunction(Buffer.from(img));
I am not really sure how to continue from here. I tried creating a new vector with a buffer, like so:
std::vector<char> buffer(data);
But it seems like I need to give it a size, which I am unsure how to get. Regardless, even when I use the initial buffer size (from Node.js), the image fails to go through.
terminate called after throwing an instance of 'std::bad_alloc'
what(): std::bad_alloc
[1] 16021 abort (core dumped)
However, when I read the image directly from C++, it all works fine:
std::ifstream ifs ("./myImage.png", std::ios::binary|std::ios::ate);
std::ifstream::pos_type pos = ifs.tellg();
std::vector<char> buffer(pos);
ifs.seekg(0, std::ios::beg);
ifs.read(&buffer[0], pos);
// further below, I pass "buffer" to the function and it works just fine.
But of course, I need the image to come from Node.js. Maybe Buffer is not what I am looking for?
Here is an example based on N-API; I would also encourage you to take a look similar implementation based on node-addon-api (it is an easy to use C++ wrapper on top of N-API)
https://github.com/nodejs/node-addon-examples/tree/master/array_buffer_to_native/node-addon-api
#include <assert.h>
#include "addon_api.h"
#include "stdio.h"
napi_value CArrayBuffSum(napi_env env, napi_callback_info info)
{
napi_status status;
const size_t MaxArgExpected = 1;
napi_value args[MaxArgExpected];
size_t argc = sizeof(args) / sizeof(napi_value);
status = napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
assert(status == napi_ok);
if (argc < 1)
napi_throw_error(env, "EINVAL", "Too few arguments");
napi_value buff = args[0];
napi_valuetype valuetype;
status = napi_typeof(env, buff, &valuetype);
assert(status == napi_ok);
if (valuetype == napi_object)
{
bool isArrayBuff = 0;
status = napi_is_arraybuffer(env, buff, &isArrayBuff);
assert(status == napi_ok);
if (isArrayBuff != true)
napi_throw_error(env, "EINVAL", "Expected an ArrayBuffer");
}
int32_t *buff_data = NULL;
size_t byte_length = 0;
int32_t sum = 0;
napi_get_arraybuffer_info(env, buff, (void **)&buff_data, &byte_length);
assert(status == napi_ok);
printf("\nC: Int32Array size = %d, (ie: bytes=%d)",
(int)(byte_length / sizeof(int32_t)), (int)byte_length);
for (int i = 0; i < byte_length / sizeof(int32_t); ++i)
{
sum += *(buff_data + i);
printf("\nC: Int32ArrayBuff[%d] = %d", i, *(buff_data + i));
}
napi_value rcValue;
napi_create_int32(env, sum, &rcValue);
return (rcValue);
}
The JavaScript code to call the addon
'use strict'
const myaddon = require('bindings')('mync1');
function test1() {
const array = new Int32Array(10);
for (let i = 0; i < 10; ++i)
array[i] = i * 5;
const sum = myaddon.ArrayBuffSum(array.buffer);
console.log();
console.log(`js: Sum of the array = ${sum}`);
}
test1();
The Output of the code execution:
C: Int32Array size = 10, (ie: bytes=40)
C: Int32ArrayBuff[0] = 0
C: Int32ArrayBuff[1] = 5
C: Int32ArrayBuff[2] = 10
C: Int32ArrayBuff[3] = 15
C: Int32ArrayBuff[4] = 20
C: Int32ArrayBuff[5] = 25
C: Int32ArrayBuff[6] = 30
C: Int32ArrayBuff[7] = 35
C: Int32ArrayBuff[8] = 40
C: Int32ArrayBuff[9] = 45
js: Sum of the array = 225
here is my code. i am trying to find min distance(diff in indices) b/w 2 equal elements:
#include<iostream>
#include<string>
#include<stdio.h>
#include<algorithm>
#include<vector>
#include<math.h>
using namespace std;
vector<string> split_string(string);
int n;
int minimumDistances(vector<int> a) {
int mn=n,flag=0,mch,pos,diff=0;
for (int i = 0;i < n-1;i++) {
//mch = a[i];
for (int j = i + 1;j < n;j++) {
if (a[j]==a[i]) {
flag = 1;
pos = j;
diff = j - i;
}
}
if (diff<mn) {
mn = diff;
}
}
if (flag==0) {
return -1;
}
return mn;
}
int main()
{
cin >> n;
cin.ignore(numeric_limits<streamsize>::max(), '\n');
string a_temp_temp;
getline(cin, a_temp_temp);
vector<string> a_temp = split_string(a_temp_temp);
vector<int> a(n);
for (int i = 0; i < n; i++) {
int a_item = stoi(a_temp[i]);
a[i] = a_item;
}
int result = minimumDistances(a);
cout << result;
cin.get();
return 0;
}
vector<string> split_string(string input_string) {
string::iterator new_end = unique(input_string.begin(), input_string.end(),
[](const char &x, const char &y) {
return x == y and x == ' ';
});
input_string.erase(new_end, input_string.end());
while (input_string[input_string.length() - 1] == ' ') {
input_string.pop_back();
}
vector<string> splits;
char delimiter = ' ';
size_t i = 0;
size_t pos = input_string.find(delimiter);
while (pos != string::npos) {
splits.push_back(input_string.substr(i, pos - i));
i = pos + 1;
pos = input_string.find(delimiter, i);
}
splits.push_back(input_string.substr(i, min(pos, input_string.length()) - i +
1));
return splits;
}
The exception occurs at pt marked by arrow
when n=10 no error
when =1000 exception occurs
Why is this exception only occurring at large values?
sample input :
39572 89524 21749 94613 75569 74800 91713 62107 28574 22617 22271 22624 28116 67573 53717 9358 65220 59894 78686 10945 33641 11708 8851 11860 66780 64697 799 47782 41971 54170 8960 81543 60047 47061 92508 51968 38213 84221 14075 66787 23191 52698 5764 51307 20271 59481 77018 1843 19375 55704 12789 53016 83764 37992 64877 50545 19041 82028 98327 61012 52551 7287 42555 12598 70700 51416 80918 8914 35637 11345 75701 58828 80395 97817 26488 17019 57299 3506 18862 93026 75562 48003 62395 59327 85996 27272 9872 5037 25652 8199 82402 78203 31838 41309 7153 18890 92725 88071 27804 28363 99416 19858 3543 79812 17675 30031 96831 91326 49889 15693 84353 25452 80049 46748 84779 66045 90372 94651 87434 16024 19202 69836 94228 67392 27498 1381 86282 20223 5805 14087 48586 5221 50297 68482 85033 67972 98513 98216 59299 48403 30262 60004 73855 10311 6752 74986 92708 13476 85989 96494 29500 5191 82683 40080 88935 10181 57814 75217 30404 63619 5656 95343 68840 55953 63825 70226 23926 62338 68442 99577 27093 15056 59581 17300 25367 82685 92286 34427 96161 78275 30922 25661 99818 13605 82094 88753 23786 39908 80323 54190 3527 85979 65885 72367 41933 29710 58945 82211 8401 43740 81788 35494 58796 57721 69147 516 40406 77785 34943 36567 72413 65865 78580 72231 95822 60674 77337 35960 582 57660 6503 4109 43639 72388 92829 1924 2099 51774 84135 10500 95514 82275 62346 70663 39996 31493 71179 80402 9279 6122 16969 81692 88340 11902 70275 514 72576 47612 36475 73159 21624 42978 93620 65264 15366 86449 67188 17465 54576 67676 44317 50090 49951 6664 20753 89948 54509 8284 86702 80140 14407 20024 78184 19099 31926 48460 19613 4502 12424 72440 94013 34049 15418 87634 99313 30785 90435 82853 64602 45011 50529 25272 11454 481 48288 48559 6781 2797 56844 93483 82938 87603 13507 61122 6702 45433 25934 42667 66288 38359 15108 60301 72408 46878 64287 88073 94015 54723 87278 74970 99734 37808 242 27540 54641 48530 76100 61422 67679 32944 54905 66969 20547 84765 44444 43601 30198 86730 2620 12838 25089 17728 73140 13849 64607 53779 18274 74974 8502 5553 49944 24589 59713 50186 52129 14354 15068 28229 75776 99100 77525 47033 66069 98072 31798 26865 41673 78349 13596 44294 7539 55037 78374 80679 68887 59333 50811 3513 34308 59313 9066 84252 254 85131 50791 52384 99485 82211 96965 91613 81311 74491 38647 63733 88915 86797 90598 46941 65146 20546 7587 72686 75584 85961 69717 60823 61647 36880 64336 12307 96194 89755 12911 12800 74886 63702 65184 90724 45914 78502 82337 43577 52993 20984 7310 41908 24134 97909 88849 5632 18455 96436 94670 10391 98750 80740 71214 60397 17620 51903 89056 30166 41658 1967 42967 32896 65670 8151 23620 27936 86653 5958 71513 55998 43294 78824 14259 67428 93085 19460 73061 27892 15897 84083 54636 30999 64823 25850 7748 82444 77753 96804 12610 35763 98771 55577 68660 80793 80081 92280 8729 83086 14590 96595 55437 57885 91771 69696 41665 1208 89156 31078 29100 21405 15162 83736 52404 79985 25939 60152 78781 3692 73308 7744 39456 72080 63321 24468 69225 59754 33100 94307 42841 47691 90902 98278 21928 82673 84326 63593 83881 73482 11024 29333 94888 42538 29422 63644 38875 71713 40149 17657 75405 13457 25401 31213 1889 5074 72033 71115 64829 5134 65422 24022 52825 72676 22300 91105 71701 6626 54698 55582 96460 82074 1267 7700 24612 47041 71345 63488 18754 11494 97497 10512 41303 39250 58077 59545 44324 30111 47012 25505 35245 28786 49527 4422 1462 88179 95527 73163 11157 66577 45097 7618 48652 62716 31670 89616 9758 3015 69456 28512 30861 83305 39024 88517 22555 97102 48062 83232 43565 95074 8737 78810 23860 74617 99584 25322 62796 95111 14837 90306 61688 59934 14276 26692 22650 45946 32661 48760 48962 2117 77273 96175 1775 32649 84692 24330 46103 32754 23914 89668 44180 49004 84830 84392 23621 84414 9714 2769 95877 40903 93075 73918 17189 7351 16962 56192 53298 49623 4952 18612 68093 98577 31139 69868 47579 15832 10550 93682 64938 34465 99703 25471 83469 885 9863 23442 1652 35930 26211 97529 76833 35639 87799 94023 59342 4762 50215 28992 54385 71519 47604 38830 70097 78744 8698 17676 10928 19249 27710 92218 70066 27413 17689 53535 44651 27553 76977 46303 63483 19540 43832 56668 55179 31632 50691 30874 52746 17258 59866 7131 5130 23823 45962 75227 18919 71012 9255 29847 6613 53317 38417 76679 97083 56107 46566 41734 83660 23543 88037 63495 59436 48221 20163 30967 96205 87207 61841 48951 20817 38060 56083 25947 61883 18397 17526 80802 5761 26781 27001 12375 96451 81770 89054 93534 37877 35621 35268 37889 75516 23305 1384 34952 71526 21548 82272 67732 25107 44113 16683 45924 98525 89118 71872 60408 23867 5750 57562 29629 48884 915 42004 45335 82686 47410 38869 36915 83031 74137 74805 74900 97442 76189 26204 85320 14089 8476 69404 55548 68942 2440 1473 67467 7910 89697 44228 31778 95447 1790 77759 44331 19058 36115 89666 18096 83525 44887 55011 82909 19024 29816 57809 32818 22358 365 34491 52799 8842 3895 8348 94136 22687 26173 61603 30598 15870 5831 78728 27669 23974 56487 88353 59384 92602 94371 77480 92479 39259 32491 91740 58283 78660 65901 91102 1018 66267 25593 70169 91461 45840 78517 85597 68528 4690 47200 99126 36912 69384 94206 64582 93358 50693 52935 52742 59647 47306 46574 68478 86565 95417 60219 44849 74077 26120 52303 91447 8739 94248 61617 200 40088 40134 85797 8616 61177 32998 24094 98089 18734 34652 62671 12092 1697 31958 81186 61344 79265 44112 46175 82182 39529 22746 43383 13607 65218 95686 5054 73958 6286 66671 74158 46375 23158 76308 71343 84335 25658 11790 82424 44392 46442 61448 72836 48140 93406 70374 25836 89023 14486 88363 71206 54015 11109 14589 83974 76328 26628 89029 66638 32914 72052 57148 95641 11562 33456 66985 95897 59114 95127 94674 19858 57921 56122 92694 6061 65880 79420 48250 54904 93906 36613 26110 64274 64075 57051 48248 40403 31 37277 7041 49298 25682 64189 44939 37244 13998 28276 49494 89464 23403 44168 9323 97677 16642 18369 3738 82522 97790 68340
I have got executable module iCoreTest.exe, wich dynamicly loaded library IRTest.rs. I want to debug it via lldb c++ api.
When I create "iCoreTest.exe" process under lldb throug lldb::SBTarget::Launch(..); everything works fine. With fine, I mean I can set breakpoints BreakpointCreateByLocation and when the debugger stops on it get the event from SBListener.WaitForEvent();
Problems begins when I want to attach to the currently running process.
Create target and attach to process
m_debugData->currentTarget=m_debugData>debugger.CreateTarget(executable.c_str());
m_debugData->currentProcess = m_debugData>currentTarget.AttachToProcessWithName(m_debugData->listener, processName.c_str(), false, error);
Load module "IRTest.rs"
auto module = m_debugData->currentTarget.AddModule("IRTest.rs", "i386-pc-windows-msvc", nullptr);
After that lldb stops on "ntdll.dll`DbgBreakPoint + 1"
I execute command m_debugData->currentProcess.Continue();
So, ICoreTest.exe is running..
Add breakpoint m_debugData->currentTarget.BreakpointCreateByLocation("IRTest.st", 58);
The added breakpoint does not triggered
After this I print the existing breakpoints using the following code:
void LLDBRunner::printBreakpoints()
{
for (int i = 0; i < m_debugData->currentTarget.GetNumBreakpoints(); i++)
{
auto bp = m_debugData->currentTarget.GetBreakpointAtIndex(i);
for (int j = 0; j < bp.GetNumLocations(); j++)
{
auto loc = bp.GetLocationAtIndex(j);
lldb::SBStream stream;
loc.GetDescription(stream, lldb::DescriptionLevel::eDescriptionLevelFull);
auto str = stream.GetData();
}
}
}
And output was:
1.1: where = IRTest.rs`Add + 421 at IRTest.st:58, address = IRTest.rs[0x10001525], unresolved, hit count = 0
Which means my breakpoint is unresolved..Why? :)
Also!
When i use lldb command line breakpoint is resolved, and working:
(lldb) attach -p 17448
Process 17448 stopped
* thread #1: tid = 0x0ae0, 0x77bc8d21 ntdll.dll`DbgBreakPoint + 1, stop reason = Exception 0x80000003 encountered at address 0x77bc8d20
frame #0: 0x77bc8d21 ntdll.dll`DbgBreakPoint + 1
ntdll.dll`DbgBreakPoint:
-> 0x77bc8d21 <+1>: retl
0x77bc8d22 <+2>: int3
0x77bc8d23 <+3>: int3
0x77bc8d24 <+4>: int3
Executable module set to "iCoreTest.exe".
Architecture set to: i386-pc-windows-msvc.
(lldb) b IRTest.st:58
Breakpoint 1: where = IRTest.rs`Add + 421 at IRTest.st:58, address = 0x07ca1525
(lldb) b
Current breakpoints:
1: file = 'IRTest.st', line = 58, exact_match = 0, locations = 1, resolved = 1, hit count = 0
1.1: where = IRTest.rs`Add + 421 at IRTest.st:58, address = 0x07ca1525, resolved, hit count = 0
(lldb) c
Process 17448 resuming
Process 17448 stopped
* thread #6: tid = 0x2560, 0x07ca1525 IRTest.rs`Add(X1=2, X2=42, X3=(RANGE = 1, MIN_SCALE = -4095, MAX_SCALE = 4095)) + 421 at IRTest.st:58, stop reason = breakpoint 1.1
frame #0: 0x07ca1525 IRTest.rs`Add(X1=2, X2=42, X3=(RANGE = 1, MIN_SCALE = -4095, MAX_SCALE = 4095)) + 421 at IRTest.st:58
55 i, j : INT;
56 END_VAR
57
-> 58 tmpInteg();
59
60
61
(lldb)
UPDATE:
I write a simple program wich reproduce bug
prog.cpp:
#include <cstdio>
void doSomething(void);
void doSomething(void)
{
int loop = 0;
loop += 1;
loop += 2;
loop += 3;
}
int main(void)`
{
printf("start \n");
while(1)
{
doSomething();
}
return 0;
}
Compile it..
gcc prog.cpp -g -O0
When i`m trying to set break point
m_debugData->currentTarget.BreakpointCreateByLocation("prog.cpp", 7);
I get same result
1.1: where = a.exe`doSomething() + 6 at prog.cpp:7, address = a.exe[0x00401356], unresolved, hit count = 0
My little research:
I compare lldb behavior in two versions:
Launch new process(is ok)
Attach to process(broken)
I found that in method
lldb::break_id_t
Process::CreateBreakpointSite (const BreakpointLocationSP &owner, bool use_hardware)
line..
load_addr = owner->GetAddress().GetOpcodeLoadAddress (&GetTarget());
return LLDB_INVALID_ADDRESS in version when I attach to process.
CallStack:
liblldb.dll!lldb_private::Process::CreateBreakpointSite(const std::shared_ptr<lldb_private::BreakpointLocation> & owner, bool use_hardware) Line 2094 C++
liblldb.dll!lldb_private::BreakpointLocation::ResolveBreakpointSite() Line 523 C++
liblldb.dll!lldb_private::BreakpointLocationList::AddLocation(const lldb_private::Address & addr, bool resolve_indirect_symbols, bool * new_location) Line 254 C++
liblldb.dll!lldb_private::Breakpoint::AddLocation(const lldb_private::Address & addr, bool * new_location) Line 102 C++
liblldb.dll!lldb_private::BreakpointResolver::AddLocation(lldb_private::Address loc_addr, bool * new_location) Line 214 C++
liblldb.dll!lldb_private::BreakpointResolver::SetSCMatchesByLine(lldb_private::SearchFilter & filter, lldb_private::SymbolContextList & sc_list, bool skip_prologue, const char * log_ident) Line 184 C++
liblldb.dll!lldb_private::BreakpointResolverFileLine::SearchCallback(lldb_private::SearchFilter & filter, lldb_private::SymbolContext & context, lldb_private::Address * addr, bool containing) Line 94 C++
liblldb.dll!lldb_private::SearchFilter::DoModuleIteration(const lldb_private::SymbolContext & context, lldb_private::Searcher & searcher) Line 190 C++
liblldb.dll!lldb_private::SearchFilter::Search(lldb_private::Searcher & searcher) Line 118 C++
liblldb.dll!lldb_private::BreakpointResolver::ResolveBreakpoint(lldb_private::SearchFilter & filter) Line 62 C++
liblldb.dll!lldb_private::Breakpoint::ResolveBreakpoint() Line 355 C++
liblldb.dll!lldb_private::Target::AddBreakpoint(std::shared_ptr<lldb_private::Breakpoint> bp_sp, bool internal) Line 695 C++
liblldb.dll!lldb_private::Target::CreateBreakpoint(std::shared_ptr<lldb_private::SearchFilter> & filter_sp, std::shared_ptr<lldb_private::BreakpointResolver> & resolver_sp, bool internal, bool request_hardware, bool resolve_indirect_symbols) Line 672 C++
liblldb.dll!lldb_private::Target::CreateBreakpoint(const lldb_private::FileSpecList * containingModules, const lldb_private::FileSpec & file, unsigned int line_no, unsigned __int64 offset, lldb_private::LazyBool check_inlines, lldb_private::LazyBool skip_prologue, bool internal, bool hardware, lldb_private::LazyBool move_to_nearest_code) Line 411 C++
liblldb.dll!lldb::SBTarget::BreakpointCreateByLocation(const lldb::SBFileSpec & sb_file_spec, unsigned int line, unsigned __int64 offset) Line 832 C++
liblldb.dll!lldb::SBTarget::BreakpointCreateByLocation(const lldb::SBFileSpec & sb_file_spec, unsigned int line) Line 803 C++
liblldb.dll!lldb::SBTarget::BreakpointCreateByLocation(const char * file, unsigned int line) Line 796 C++
ConsoleApplication1.exe!Debugger::LLDBRunner::setBreakpoint(std::basic_string<char,std::char_traits<char>,std::allocator<char> > file, unsigned int line) Line 204 C++
ConsoleApplication1.exe!main() Line 28 C++
UPDATE 2:
I print 'a.exe' module sections using the following code:
for (int i = 0; i < m_debugData->currentTarget.GetNumModules(); i++)
{
auto module = m_debugData->currentTarget.GetModuleAtIndex(i);
auto moduleName = module.GetFileSpec().GetFilename();
for (int j = 0; j < module.GetNumSections(); j++)
{
auto section = module.GetSectionAtIndex(j);
auto sectionName = section.GetName();
auto addr = section.GetLoadAddress(m_debugData->currentTarget);
auto isValid = LLDB_INVALID_ADDRESS != addr;
std::cout << "Module: " << moduleName << "; Section: " << sectionName << "; IsValid: " << isValid << std::endl;
}
}
An output was:
State changed unknown->stopped
Module: a.exe; Section: .text; IsValid: 0
Module: a.exe; Section: .data; IsValid: 0
Module: a.exe; Section: .rdata; IsValid: 0
Module: a.exe; Section: .eh_frame; IsValid: 0
Module: a.exe; Section: .bss; IsValid: 0
Module: a.exe; Section: .idata; IsValid: 0
Module: a.exe; Section: .CRT; IsValid: 0
Module: a.exe; Section: .tls; IsValid: 0
Module: a.exe; Section: .debug_aranges; IsValid: 0
Module: a.exe; Section: .debug_info; IsValid: 0
Module: a.exe; Section: .debug_abbrev; IsValid: 0
Module: a.exe; Section: .debug_line; IsValid: 0
Module: a.exe; Section: .debug_frame; IsValid: 0
It's hard to say with certainty, but the python APIs and the command line apis are not entirely the same. They both have their own set of things they do internally before running the "actual" command you requested. Debugging on Windows is definitely not as mature as on other platforms, in part because there are not a lot of people using it yet. I would suggest reporting this as a bug on the lldb bug tracker.
In the meantime, maybe you can try creating a target manually, and setting the breakpoint BEFORE you attach to the process. I don't know if this will work, but resolving a breakpoint dynamically when a module is loaded, versus trying to resolve it immediately when you drop the breakpoint down are two different codepaths, so it's possible it will work if the breakpoint is already there.
I have taken code from here Webduino Network Setp
I added one more field.
struct config_t
{
....
...
.....
byte subnet[4];
byte dns_server[4];
unsigned int webserverPort;
char HostName[10]; // Added code Here..
} eeprom_config;
Snippet..
#define NAMELEN 5
#define VALUELEN 10
void setupNetHTML(WebServer &server, WebServer::ConnectionType type, char *url_tail, bool tail_complete)
{
URLPARAM_RESULT rc;
char name[NAMELEN];
char value[VALUELEN];
boolean params_present = false;
byte param_number = 0;
char buffer [13];
.....
.....
}
Added Lines to read date from web page and Wire to eeprom
Write to eeprom: ( Facing issue here, I need to copy value to eeprom_config.HostName[0] ... )
// read Host Name
if (param_number >= 25 && param_number <= 35) {
// eeprom_config.HostName[param_number - 25] = strtol(value, NULL, 10);
eeprom_config.HostName[param_number - 25] = value ; // Facing Issue here..
}
and...
for (int a = 0; a < 10; a++) {
server.printP(Form_input_text_start);
server.print(a + 25);
server.printP(Form_input_value);
server.print(eeprom_config.HostName[a]);
server.printP(Form_input_size1);
server.printP(Form_input_end);
}
Issue was resolved.
Thanks , got idea from this post.
invalid conversion from char' tochar*'
How ! changed
// read Host Name
if (param_number >= 25 && param_number <= 35) {
// eeprom_config.HostName[param_number - 25] = strtol(value, NULL, 10);
eeprom_config.HostName[param_number - 25] = value ; // Facing Issue here..
}
changed to
// read Host Name
if (param_number >= 25 && param_number <= 35) {
eeprom_config.HostName[param_number - 25] = value[0];
}