Seg faults and 'could not read memory content' issues

Go To Last Post
6 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hi Guys,

 

After a productive few weeks I'm having a issue debugging array values. I've also had a few segfaults but only on a virtual PC.  I've attached a bare bones file (combines the .h and class files).  There is a 2 dimensional array that has either random values in it or can't be read in the locals window when at the break point (marked in code. 'bb++'  Had to add a variable that didn't get optimised away).

 

If I run the program and output the contents it's fine but I need to view the values in the array for debugging purposes.  What am I doing wrong?  I'm getting the same results in the simulator. (target was Atmega324pb)

 

Global I'm trying to look at is displayGroup[1][0-18]

 

regards

/*
 * test.cpp
 *
 * Created: 5/16/2019 4:20:51 PM
 * Author : Nik middleton
 */ 

// 16MHz clock
#define F_CPU 160000000UL
#define ALL	127

#include <avr/io.h>
#include <util/delay.h>
#include "avr/iom324pb.h"
//-------------------------------------------------------------------------------------
class testclass
{
	//variables
	public:
	volatile uint8_t displayGroup[16][18];
	//functions
	public:
	void groupClear(int8_t group=ALL);
	void groupSet(uint8_t group, uint8_t grouping[18]);
	testclass();
	~testclass();

	};

//------------------------------------------------------------------------------------
// default constructor
testclass::testclass()
{
} //testclass

void testclass::groupClear(int8_t group)
{
	int8_t groupNum;
	int8_t groupElement;

	if(group == ALL || (group >=0 && group < 16)){

		if(group == ALL){
			for(groupNum = 0;groupNum < 15;groupNum++){
				for(groupElement=0;groupElement<18;groupElement++){
					displayGroup[groupNum][groupElement] = 0;
				}
			}
			}else{
			for(groupElement=0;groupElement<18;groupElement++)
			displayGroup[group][groupElement] = 0;
		}
	}else return; //Invalid params
}

void testclass::groupSet(uint8_t group, uint8_t grouping[18]){
	volatile int8_t bb;
	bb = 1;
	for(int8_t xx=0; xx <18;xx++){
		displayGroup[group][xx] = grouping[xx];
	}
	bb++;  ///////////////  Set a break point here ///////////////////////////////////
}

// default destructor
testclass::~testclass()
{
} //~testclass

//-----------------------------------------------------------------------------------

//Init testclass Class
testclass testing ;

uint8_t grouping[18];

int main(void)
{
// Add some values
    grouping[0] = 32;
    grouping[1] = 6;
    grouping[2] = 5;
    grouping[3] = 4;
    grouping[4] = 3;
    grouping[5] = 2;
    grouping[6] = 1;
    grouping[17] = 99;

testing.groupClear(ALL); // Set all values in array to Zero

// Set 2 row of 2 dimensional array to values in grouping array as above
testing.groupSet(1, grouping);

    while (1)
    {
		_delay_ms(100);
    }
}

 

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
		if(group == ALL){
			for(groupNum = 0;groupNum < 15;groupNum++){
				for(groupElement=0;groupElement<18;groupElement++){
					displayGroup[groupNum][groupElement] = 0;
				}
			}
			}

Wouldn't that be easier as a single memset() ?

else return;

What's the point in that? It's going to do that anyway!

 

Anyway I don't see much point in trying to develop this on an AVR - there's nothing there that's AVR specific so I slightly modified it:

#include <stdint.h>
#include <stdio.h>

#define ALL	127

//-------------------------------------------------------------------------------------
class testclass
{
	//variables
	public:
	volatile uint8_t displayGroup[16][18];
	//functions
	public:
	void groupClear(int8_t group=ALL);
	void groupSet(uint8_t group, uint8_t grouping[18]);
	testclass();
	~testclass();

	};

//------------------------------------------------------------------------------------
// default constructor
testclass::testclass()
{
} //testclass

void testclass::groupClear(int8_t group)
{
	int8_t groupNum;
	int8_t groupElement;

	if(group == ALL || (group >=0 && group < 16)){

		if(group == ALL){
			for(groupNum = 0;groupNum < 15;groupNum++){
				for(groupElement=0;groupElement<18;groupElement++){
					displayGroup[groupNum][groupElement] = 0;
				}
			}
			}else{
			for(groupElement=0;groupElement<18;groupElement++)
			displayGroup[group][groupElement] = 0;
		}
	}else return; //Invalid params
}

void testclass::groupSet(uint8_t group, uint8_t grouping[18]){
	volatile int8_t bb;
	bb = 1;
	for(int8_t xx=0; xx <18;xx++){
		displayGroup[group][xx] = grouping[xx];
	}
	bb++;  ///////////////  Set a break point here ///////////////////////////////////
}

// default destructor
testclass::~testclass()
{
} //~testclass

//-----------------------------------------------------------------------------------

//Init testclass Class
testclass testing ;

uint8_t grouping[18];

int main(void)
{
// Add some values
    grouping[0] = 32;
    grouping[1] = 6;
    grouping[2] = 5;
    grouping[3] = 4;
    grouping[4] = 3;
    grouping[5] = 2;
    grouping[6] = 1;
    grouping[17] = 99;

testing.groupClear(ALL); // Set all values in array to Zero

// Set 2 row of 2 dimensional array to values in grouping array as above
testing.groupSet(1, grouping);

    for (int i=0; i < 18; i++) {
        printf("%d = %d\n", i, testing.displayGroup[1][i]);
    }
    while (1)
    {
    }
}

and built it with MSVC:

D:\c>cl group.cpp
Microsoft (R) C/C++ Optimizing Compiler Version 19.16.27027.1 for x86
Copyright (C) Microsoft Corporation.  All rights reserved.

group.cpp
Microsoft (R) Incremental Linker Version 14.16.27027.1
Copyright (C) Microsoft Corporation.  All rights reserved.

/out:group.exe
group.obj

D:\c>group
0 = 32
1 = 6
2 = 5
3 = 4
4 = 3
5 = 2
6 = 1
7 = 0
8 = 0
9 = 0
10 = 0
11 = 0
12 = 0
13 = 0
14 = 0
15 = 0
16 = 0
17 = 99

I don't see much wrong in that? It's copied grouping[] into displaygroup[1] as seems to have been the intention.

 

If you actually brought it into Visual Studio you could use its debugger to check the right data in the right places. I just picked printf() to show a quick result at the command line (which is the massive advantage of developing on a PC not an AVR!)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Thanks for looking at this.  It does work fine when running as you did, the issue is that this is a small subset of a larger program that uses TWI and SPI.  Am I correct in thinking that this is simple a debugger issue?  If it is then it doesn't give me a lot of confidence moving forwards

 

regards

 

 

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Who can say without seeing the rest of the code. Something may be running rogue in other parts of the code (like corrupted pointers etc) that has some influence on this small part. So I don't think you can necessarily assume it's just a debugger thing.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

A bit of confusion here.  To avoid any other corruption I took everything else out to eliminate that.  The code as posted causes an issue in Studio 7 when debugging and is repeatable both on the target and the sim, hence my concern.  Using another compiler/debugger isn't really an option.  I'm grateful for you taking the time to having a look at it though and appreciate it.

 

regards

 

 

 

Last Edited: Thu. May 16, 2019 - 05:55 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

This may have been covered, as I did not read all of the thread:

 

Debugging in an optimizing compiler requires some tricks and minor code changes to enhance the ability to debug the code.

Using the" -Og" debug optimization level while debugging helps.

 

Things like making watch variables volatile or static to prevent them from being optimized out / visible while debugging.

Knowing that the debug pointer (PC) may jump to the bottom of a "for/do/while loop" to do the index comparison, addition then jumping back to the top of the loop can be bewildering at first,

knowing the optimizer may change the order of the code from the way it is written, and learning enough asm code to understand the program flow is helpful as well.

 

Jim

 

 

 

Click Link: Get Free Stock: Retire early! PM for strategy

share.robinhood.com/jamesc3274
get $5 free gold/silver https://www.onegold.com/join/713...

 

 

 

 

Last Edited: Thu. May 16, 2019 - 06:42 PM