0

I am writing my program for my DataMining project. I get segmentation error on my code. I tried to debug using the gdb and created core dump using ulimit in ubuntu.

Below is the error I was able to backtrace in gdb.

Python Exception <class 'gdb.MemoryError'> Cannot access memory at address 0x7fff48c47738: #0  0x000000000040cdb0 in TokenReader::getToken (
this=<error reading variable: Cannot access memory at address 0x7fff48c47718>, 
this@entry=<error reading variable: Cannot access memory at address 0x7fff48c47738>, 
buf=<error reading variable: Cannot access memory at address 0x7fff48c47710>, 
buf@entry=<error reading variable: Cannot access memory at address 0x7fff48c47738>) at src/tokread.c++:26
Cannot access memory at address 0x7fff48c47738

My code:

/*********************************************************
 * Project: 2
 * File: tokread.h
 * Anil Pediredla, KUID 28056
 *********************************************************/

#ifndef _TOKREAD_H_
#define _TOKREAD_H_

#include <iostream>
using namespace std;

const short NEW_LINE = 0;
const short SPACE    = 1;
const short TOKEN    = 2;
const short COMMENT  = 3;

class TokenReader {
  public:

    TokenReader(istream &in);

    char* getToken(char* buf);

  private:
    istream &in;
    short state;
};



#endif //_TOKREAD_H_

/*********************************************************
 * Project: 2
 * File: tokread.h
 * Anil Pediredla, KUID 28056
 *********************************************************/

#include <sstream>
#include <cstdlib>

using namespace std;

#include "tokread.h"


/*********************************************************
 * Class: TokenReader
 *********************************************************/
TokenReader::TokenReader(istream &in):
  in(in), state(NEW_LINE) {
}


char* TokenReader::getToken(char* buf) {
  bool done = false;
  int tokLen = 0;
  while (!done && !in.eof()) {           //error here
    char ch = in.get();
    switch (state) {
      case NEW_LINE:
        if (ch == '!') state = COMMENT;
        else {
          in.unget();
          state = SPACE;
        }
      break;
      case SPACE: 
        if ((ch == 13) && (in.peek() == '\n')) in.get();
        if (ch == '\n') {
          state = NEW_LINE;
          break;
        }
        if ((ch != ' ') && (ch != '\t')) {
          in.unget();
          state = TOKEN;
        }
      break;
      case TOKEN:
        if ((ch == 13) && (in.peek() == '\n')) in.get();
        if (ch == '\n') {
          state = NEW_LINE;
          done = true;
          break;
        }
        if ((ch == ' ') || (ch == '\t')) {
          in.unget();
          state = SPACE;
          done = true;
          break;
        }
        buf[tokLen++] = ch;
      break;
      case COMMENT:
       if (ch == '\n'){
           state = NEW_LINE;
       }
      break;
    }
  }
  buf[tokLen] = '\0';
  return buf;
}

I am calling my classes through a main function which looks like

int main(int argc, char* argv[]) {

  fstream input(inFileName, ios::in);
  if (!input) {
    cerr << "Could not open file " << inFileName << endl;
    exit(-1);
/* calling my error class here. 
*/  
  TokenReader reader(input);
  Table* table = new Table(reader, maxDistAttrVal);

  table->mlem2(intvFormat, output1, output2, output3);

}

}

Anil Pediredla
  • 704
  • 2
  • 8
  • 20
  • 3
    related: [Why is “while ( !feof (file) )” always wrong](http://stackoverflow.com/questions/5431941/why-is-while-feof-file-always-wrong) – NathanOliver May 30 '15 at 03:16
  • 3
    can you also try to create a minimal example? – Geradlus_RU May 30 '15 at 03:27
  • I changed the code from while(!in.eof) to if(!in.eof) and used while to loop. But, I still get the same issue. – Anil Pediredla May 30 '15 at 04:05
  • 2
    The most likely cause of a SIGSEGV is having the caller not provide a buffer big enough for the token to be stored in. Separately, `in.get()` returns an `int` not a `char`. And you'd be much better off returning a `std::string` - harder to screw that up and crash your program. Re giving us a minimal example - that should include the simplest input that you can find that reproduces the crash, and you should put a big comment in the code at the line that's crashing (26 in the .c++ file). – Tony Delroy May 30 '15 at 04:11
  • 2
    It's also noteworthy that your error report says "Python Exception" - you should create a simple `main` program to call your code from C++ and check whether it works... if the problem is in python bindings, that's not something anyone here can diagnose from the code you've posted. – Tony Delroy May 30 '15 at 04:19
  • @Anil You gave us a `main` function that doesn't call the function you're having an issue with. – PaulMcKenzie May 30 '15 at 04:42

1 Answers1

0

if you are building it for Window, you would be able to use the build in data leak code they provided for Visual Studioes(I have not tested the code outside Visual Basics)

   //-----MICROSOFT ONLY----------
  #define _CRT_DEBUG_MAP_ALLOC
  #include <crtdbg.h> //C-runtime debug header 
 //must be placed before include's
 //------------------------------

 //Must be place at the top of your main method
 #if defined(_DEBUG)
int dbgFlags = _CrtSetDbgFlag(_CRTDBG_REPORT_FLAG);
dbgFlags |= _CRTDBG_CHECK_ALWAYS_DF; //check block intergerity on every memory
dbgFlags |= _CRTDBG_DELAY_FREE_MEM_DF; //dont remove blocks on delete
dbgFlags |= _CRTDBG_LEAK_CHECK_DF; //check for leaks at process termination
_CrtSetDbgFlag(dbgFlags);
#endif

This code will make sure of any memorey leaks are cleaned up and the blocks wont be removed.

Gorilla
  • 112
  • 11
  • I suggest using [VLD](https://vld.codeplex.com/) rather than the built-in CRT heap check functionality. It's simpler to set up (just `#include `), it provides more useful information (stack trace of the allocation that leaked, rather than just the file/line), it handles any kind of allocation, including `malloc`/`free`, and it won't mess up with custom allocators or overloaded `new`/`delete`. – bcrist May 30 '15 at 09:46