General noob programing question

Hi guys, i'm fairly new at programming and i'm getting some errors with my code.

can't figure out what's wrong with it and why i'm getting compiler errors and also i'd appreciate if you find other problems with it to let me know so i can correct them...

Cheers :cry:

dadada.ino

#include "NTPTime.h"

#define SECONDS_IN_DAY 86400
#define START_YEAR 1900
#define TIME_ZONE +1
//static int days_in_month[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};


PROGMEM const static char website[] = "time.google.com";  


// ethernet interface mac address, must be unique on the LAN
static byte mymac[] = { 
  0x74,0x69,0x69,0x2D,0x30,0x31 };

//uint32_t timeStamp;
//boolean requestSent;



//byte Ethernet::buffer[700];
//BufferFiller bfill;


void setup () {

  Serial.begin(57600);
  Serial.println("NTP Demo");

  if (ether.begin(sizeof Ethernet::buffer, mymac) == 0)
    Serial.println( "Failed to access Ethernet controller");

  if (!ether.dhcpSetup())
    Serial.println("Failed to get configuration from DHCP");
  else
    Serial.println("DHCP configuration done");
 
  ether.printIp("IP Address:\t", ether.myip);
  ether.printIp("Netmask:\t", ether.netmask);
  ether.printIp("Gateway:\t", ether.gwip);

  if(ether.dnsLookup (website, false)){
Serial.println( "dnsLookup ok");
}else{
Serial.println( "dnsLookup faild");
}

ether.printIp("SRV: ", ether.hisip);

//ether.printIp("Old: ",ntpServer);
//ether.copyIp(ntpServer, ether.hisip );
//ether.printIp("New: ",ntpServer);

  Serial.println();


}


void loop() {

 
}

NTPTime.cpp

#include "NTPTime.h"


void NTPTime::initialSetup (EtherCard ether) {

  this->_ether = &ether;
  if (ether.dnsLookup (ntpServerAddress, false)) {
    Serial.println( "dnsLookup ok");
  } else {
    Serial.println( "dnsLookup faild");
  }
  requestSent = false;
}


String NTPTime::printDate(uint32_t timeStamp) {

  String fullFormatedDate = "";
  
  unsigned int year = START_YEAR;
  while (1) {
    uint32_t seconds;
    if (isLeapYear(year)) seconds = SECONDS_IN_DAY * 366;
    else seconds = SECONDS_IN_DAY * 365;
    if (timeStamp >= seconds) {
      timeStamp -= seconds;
      year++;
    } else break;
  }

  unsigned int month = 0;
  while (1) {
    uint32_t seconds = SECONDS_IN_DAY * days_in_month[month];
    if (isLeapYear(year) && month == 1) seconds = SECONDS_IN_DAY * 29;
    if (timeStamp >= seconds) {
      timeStamp -= seconds;
      month++;
    } else break;
  }
  month++;

  unsigned int day = 1;
  while (1) {
    if (timeStamp >= SECONDS_IN_DAY) {
      timeStamp -= SECONDS_IN_DAY;
      day++;
    } else break;
  }

  unsigned int hour = timeStamp / 3600;
  unsigned int minute = (timeStamp - (uint32_t)hour * 3600) / 60;
  unsigned int second = (timeStamp - (uint32_t)hour * 3600) - minute * 60;
  hour = hour + 2;

  fullFormatedDate = String(year) + "" + String(month) + "" + String(day) + "" + String(hour) + "" + String(minute);
  return fullFormatedDate;
}

boolean NTPTime::isLeapYear(unsigned int year) {

  return (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
}

String NTPTime::getfullformatedtime() {
  NTPTime ntp;
  String fullTime = "";
  ether.ntpRequest(ether.hisip, srcPort);
  delay(100);
  ether.packetLoop(ether.packetReceive());
  ether.ntpProcessAnswer(this->timeStamp, srcPort);
  fullTime = ntp.printDate(timeStamp);
  return fullTime;
}

NTPTime.h

#pragma once

#include "Arduino.h"
#include <EtherCard.h>

#define SECONDS_IN_DAY 86400
#define START_YEAR 1900
#define TIME_ZONE +1
#define INTERVAL 10000


class NTPTime {
  private:
    EtherCard* _ether;
    BufferFiller bfill;
    unsigned long lastTime = 0;
    uint32_t timeStamp;
    boolean requestSent;
    
    
  public:
    void initialSetup (EtherCard ether);
    String printDate(uint32_t timeStamp);
    boolean isLeapYear(unsigned int year);
    String getfullformatedtime();


};
static int days_in_month[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};


PROGMEM const static char ntpServerAddress[] = "time.google.com";
static byte ntpServer[] = {193, 204, 114, 232};
static byte srcPort = 0;

byte Ethernet::buffer[700];

Error

sketch\dadasadsa.ino.cpp.o (symbol from plugin): In function `setup':

(.text+0x0): multiple definition of `ENC28J60::buffer'

sketch\NTPTime.cpp.o (symbol from plugin):(.text+0x0): first defined here

collect2.exe: error: ld returned 1 exit status

Multiple libraries were found for "EtherCard.h"
 Used: C:\Users\Eli\Documents\Arduino\libraries\EtherCard
exit status 1
Error compiling for board Arduino Nano.

I solved the problem by moving the "byte Ethernet::buffer[700];" from the NTPTime.h back to dadada.ino. Now it compiles fine but when i try to access it in the main .ino the output isn't correct and it seems that it keeps calling the dadada.ino, over and over again.

ntpTime.initialSetup(ether);
Serial.println(ntpTime.getfullformatedtime());
}

NTP Demo
DHCP configuration done
IP Address: 192.168.1.8
Netmask: 255.255.255.0
Gateway: 192.168.1.1
dnsLookup ok
SRV: 216.239.35.4

dnsLookup ok
DHCP configuration done
IP Address: 192.168.1.8
Netmask: 255.255.255.0
Gateway: 192.168.1.1
dnsLookup ok
SRV: 216.239.35.12

dnsLookup ok
NTP Demo
DHCP configuration done
IP Address: 192.168.1.8
Netmask: 255.255.255.0
Gateway: 192.168.1.1
dnsLookup ok
SRV: 216.239.35.8

dnsLookup ok
DHCP configuration done
IP Address: 192.168.1.8
Netmask: 255.255.255.0
Gateway: 192.168.1.1
dnsLookup ok
SRV: 216.239.35.4

dnsLookup ok
NTP Demo
DHCP configuration done
IP Address: 192.168.1.8
Netmask: 255.255.255.0
Gateway: 192.168.1.1
dnsLookup ok
SRV: 216.239.35.12

dnsLookup ok
19001120

It looks like the board is resetting. I'm betting it is a memory corruption. Can you post your latest sketch?

The reason you had to move

byte Ethernet::buffer[700];

is because without the keyword 'static' it is a global and every include redefined it. On the other hand, you don't want it declared statically in each module either so having it in the .ino is the correct place to define it.

void NTPTime::initialSetup (EtherCard ether) {

  this->_ether = &ether;

"ether" is local to this function. You cannot save the address of it to use later.

I think I know what your problem may be. In the following function there is no need to pass the ether object:

void NTPTime::initialSetup (EtherCard ether) {

  this->_ether = &ether;
  if (ether.dnsLookup (ntpServerAddress, false)) {
    Serial.println( "dnsLookup ok");
  } else {
    Serial.println( "dnsLookup faild");
  }
  requestSent = false;
}

Change it to this and see if it stops resetting:

void NTPTime::initialSetup (void) {

  if (ether.dnsLookup (ntpServerAddress, false)) {
    Serial.println( "dnsLookup ok");
  } else {
    Serial.println( "dnsLookup faild");
  }
  requestSent = false;
}

It may be that the EtherCard object is not properly copied or it is so large it is overrunning the stack.

arduino_new:

void NTPTime::initialSetup (EtherCard ether) {

this->_ether = &ether;




"ether" is local to this function. You cannot save the address of it to use later.

arduino_new is correct as well. Since you passed by value, the ENTIRE object gets copied to the stack. The address that is being saved is a temporary address!!!

It is customary to pass large objects using a pointer or (better yet) a reference. In any case, there is no reason to pass 'ether' because it is a global object.

ToddL1962:
It looks like the board is resetting. I'm betting it is a memory corruption. Can you post your latest sketch?

The reason you had to move

byte Ethernet::buffer[700];

is because without the keyword 'static' it is a global and every include redefined it. On the other hand, you don't want it declared statically in each module either so having it in the .ino is the correct place to define it.

Thank you both for your reply,

Here is the latest sketch, which is still restarting:

dada.ino

#include "NTPTime.h"

#define SECONDS_IN_DAY 86400
#define START_YEAR 1900
#define TIME_ZONE +1
//static int days_in_month[] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};


PROGMEM const static char website[] = "time.google.com";  


// ethernet interface mac address, must be unique on the LAN
static byte mymac[] = { 
  0x74,0x69,0x69,0x2D,0x30,0x31 };

//uint32_t timeStamp;
//boolean requestSent;


byte Ethernet::buffer[700];
//byte Ethernet::buffer[700];
//BufferFiller bfill;
NTPTime ntpTime;



void setup () {

  Serial.begin(57600);
  Serial.println("NTP Demo");

  if (ether.begin(sizeof Ethernet::buffer, mymac) == 0)
    Serial.println( "Failed to access Ethernet controller");

  if (!ether.dhcpSetup())
    Serial.println("Failed to get configuration from DHCP");
  else
    Serial.println("DHCP configuration done");
 
  ether.printIp("IP Address:\t", ether.myip);
  ether.printIp("Netmask:\t", ether.netmask);
  ether.printIp("Gateway:\t", ether.gwip);

  if(ether.dnsLookup (website, false)){
Serial.println( "dnsLookup ok");
}else{
Serial.println( "dnsLookup faild");
}

ether.printIp("SRV: ", ether.hisip);



//ether.printIp("Old: ",ntpServer);
//ether.copyIp(ntpServer, ether.hisip );
//ether.printIp("New: ",ntpServer);

  Serial.println();
ntpTime.initialSetup();
Serial.println(ntpTime.getfullformatedtime());
}


void loop() {


}

NTPTime.cpp

#include "NTPTime.h"


void NTPTime::initialSetup (void) {

  if (ether.dnsLookup (ntpServerAddress, false)) {
    Serial.println( "dnsLookup ok");
  } else {
    Serial.println( "dnsLookup faild");
  }
  requestSent = false;
}


String NTPTime::printDate(uint32_t timeStamp) {

  String fullFormatedDate = "";
  
  unsigned int year = START_YEAR;
  while (1) {
    uint32_t seconds;
    if (isLeapYear(year)) seconds = SECONDS_IN_DAY * 366;
    else seconds = SECONDS_IN_DAY * 365;
    if (timeStamp >= seconds) {
      timeStamp -= seconds;
      year++;
    } else break;
  }

  unsigned int month = 0;
  while (1) {
    uint32_t seconds = SECONDS_IN_DAY * days_in_month[month];
    if (isLeapYear(year) && month == 1) seconds = SECONDS_IN_DAY * 29;
    if (timeStamp >= seconds) {
      timeStamp -= seconds;
      month++;
    } else break;
  }
  month++;

  unsigned int day = 1;
  while (1) {
    if (timeStamp >= SECONDS_IN_DAY) {
      timeStamp -= SECONDS_IN_DAY;
      day++;
    } else break;
  }

  unsigned int hour = timeStamp / 3600;
  unsigned int minute = (timeStamp - (uint32_t)hour * 3600) / 60;
  unsigned int second = (timeStamp - (uint32_t)hour * 3600) - minute * 60;
  hour = hour + 2;

  fullFormatedDate = String(year) + "" + String(month) + "" + String(day) + "" + String(hour) + "" + String(minute);
  return fullFormatedDate;
}

boolean NTPTime::isLeapYear(unsigned int year) {

  return (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
}

String NTPTime::getfullformatedtime() {
  NTPTime ntp;
  String fullTime = "";
  ether.ntpRequest(ether.hisip, srcPort);
  delay(100);
  ether.packetLoop(ether.packetReceive());
  ether.ntpProcessAnswer(this->timeStamp, srcPort);
  fullTime = ntp.printDate(timeStamp);
  return fullTime;
}

NTPTime.h

#include "NTPTime.h"


void NTPTime::initialSetup (void) {

  if (ether.dnsLookup (ntpServerAddress, false)) {
    Serial.println( "dnsLookup ok");
  } else {
    Serial.println( "dnsLookup faild");
  }
  requestSent = false;
}


String NTPTime::printDate(uint32_t timeStamp) {

  String fullFormatedDate = "";
  
  unsigned int year = START_YEAR;
  while (1) {
    uint32_t seconds;
    if (isLeapYear(year)) seconds = SECONDS_IN_DAY * 366;
    else seconds = SECONDS_IN_DAY * 365;
    if (timeStamp >= seconds) {
      timeStamp -= seconds;
      year++;
    } else break;
  }

  unsigned int month = 0;
  while (1) {
    uint32_t seconds = SECONDS_IN_DAY * days_in_month[month];
    if (isLeapYear(year) && month == 1) seconds = SECONDS_IN_DAY * 29;
    if (timeStamp >= seconds) {
      timeStamp -= seconds;
      month++;
    } else break;
  }
  month++;

  unsigned int day = 1;
  while (1) {
    if (timeStamp >= SECONDS_IN_DAY) {
      timeStamp -= SECONDS_IN_DAY;
      day++;
    } else break;
  }

  unsigned int hour = timeStamp / 3600;
  unsigned int minute = (timeStamp - (uint32_t)hour * 3600) / 60;
  unsigned int second = (timeStamp - (uint32_t)hour * 3600) - minute * 60;
  hour = hour + 2;

  fullFormatedDate = String(year) + "" + String(month) + "" + String(day) + "" + String(hour) + "" + String(minute);
  return fullFormatedDate;
}

boolean NTPTime::isLeapYear(unsigned int year) {

  return (year % 4 == 0 && (year % 100 != 0 || year % 400 == 0));
}

String NTPTime::getfullformatedtime() {
  NTPTime ntp;
  String fullTime = "";
  ether.ntpRequest(ether.hisip, srcPort);
  delay(100);
  ether.packetLoop(ether.packetReceive());
  ether.ntpProcessAnswer(this->timeStamp, srcPort);
  fullTime = ntp.printDate(timeStamp);
  return fullTime;
}

Any thought on what else i should change ?

You need to narrow it down to the function that is causing the reset. Eliminate the function calls in the loop one at a time until you find the culprit. When you find the function causing the reset use Serial.prints or comment code out that function until you find the offending code.

One thing about using Serial.print in situations like this is that it is likely the serial buffer will not be emptied before the board resets so you may or may not be able to tell anything from the output.

You keep using "ether" object in both .ino and .cpp files. Where is it defined?

arduino_new:
You keep using "ether" object in both .ino and .cpp files. Where is it defined?

arduino_new that is the global object supplied by the library.