Serial1 crashing on arduino mega?

hi all.

apologies in advance if this is the wrong forum, not sure if its a hardware or software issue.

Background info;
I have an arduino mega node in my home renewable energy system controlling a bank of 30+ relays for home automation & lighting etc

i am controlling some of the relays via wall remotes and key fobs that use the X10 RF protocol

The RF signals are decoded into an NEC type protocol via a serial dongle, then a level shifter sits between the decoder and the mega serial1

when installed in its home where it will live (a low voltage distribution cabinet) the mega is powered from a 5V 2A switch mode IC 78SR http://www.murata-ps.com/data/meters/mpm_78sr-2a_a00.pdf
As this is a low voltage setup (& every watt counts) the 5V switch mode IC supplies the power through the USB can as not to encounter the losses in the arduino 5V regulator

ive written a couple of functions to decode the actual serial data, it doesnt use any handshakes or stop/start packets, the data is 4 bytes, 2 are complimentary parity packets, and the other two contain the actual data.

here is a quick overview of the hardware setup

RF Remote
|
W800RF Decoder----12VRegulator----24V
|
Level Shifter
|
Arduino Mega------5vRegulator------24V
|
Relay Boards-----12VRegulator------24V
|
12V Loads

The Problem;
when i power the mega from my laptop USB, the code works perfectly for weeks and weeks.

As soon as i move the mega to its relay board home, the decoding ability crashes randomly, yet all other aspects (ethernet, timers etc) continue to work, so the whole arduino doesnt crash.

The crash can occur in as little as 30 minutes, or 12 hours, there doesnt seem to be any logic to it.

If i move the mega back to my laptop USB port, the damn thing works perfectly fine for weeks... grrrrrr

i initially thought this may be the RF decoder (W800RF) device, so when a crash occurs i have disconnected its serial lead and tested it externally on another device and its working fine (without power cycling it).

i next assumed this might be my code/functions, but lacking the ability to do serial monitor without powering it from my laptop, i decided to attach a small serial LCD to serial2 on the mega, and i grabbed a quick bit of code of the forum to stream the bytes received on serial1 out to the LCD on serial2.

what i discovered (keeping in mind that the serial1 to serial2 data loop is before my decoding functions) was that when a crash occurs, the data that the mega thinks its receiving on serial1 is total and utter rubish, a quick press of the reset and the data streamed to serial2 returns to normal.

im no expert but it would appear that the serial port on the micro controler is crashing (or changing its baud/settings).

the only thing that changes between its cabinet home and the laptop is the power supply, which ive swapped out for another (in the same series though)

i dont really have any other serial devices to confirm this with, but i have tried another arduino mega i have, and it does the exact same thing when on external power via the USB can but works when powered from a laptop.

what really puzzles me is that all other code functions, i.e. ethernet shield, SD card storage, timers etc all continue to work ok when serial1 starts to receive rubish

just in case someone wants to see the code (forgive me if its a bit newbie/lame)

int houseCode; // holds the house output decoded
int unitCode; // holds the unit output decoded
char House_Code[]={'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P'};
int Unit_Code[]={1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16}; 
//options for RF receiver code via serial port
int RXByte = 0, byte1 = 1, byte2 = 1, byte3 = 1, byte4 = 1;

char State = 'D';
int House[32] = {96, 112, 64, 80, 128, 144, 160, 176, 224, 240, 192, 208, 0, 16, 32, 48, 100, 116, 68, 84, 132, 148, 164, 180, 228, 244, 196, 212, 4, 20, 36, 52};  
int Unit[16] = {0, 16, 8, 24, 64, 80, 72, 88, 32, 48, 40, 56, 96, 112, 104, 120}; //1-8 are ON codes for 1-8 & 9-16, 9-16 are off codes for 1-8 & 9-16 respectively

//FUNCIONS FOR DECODING RF DATA
void Parse_Frame() { //routine for parsing the house/unit codes for the main program        
    for (int i=0; i<sizeof(House)/sizeof(House[0]); ++i){
      
        if (House[i] == houseCode & i <=15){ // house code is in unit 1-8 TRUE
          houseCode = i+65;
            for (int b=0; b<sizeof(Unit)/sizeof(Unit[0]); ++b){         
              if (Unit[b] == unitCode & b <=7){
              unitCode = b+1;
              State = 'T';
              break;
              }
              else if (Unit[b] == unitCode & b >7){
              unitCode = b-7;
              State = 'F';
              break;
              }}}
              
        else if (House[i] == houseCode & i >15){ // house code is in unit 9-16 TRUE
          houseCode = i+49;
            for (int b=0; b<sizeof(Unit)/sizeof(Unit[0]); ++b){         
              if (Unit[b] == unitCode & b <=7){
              unitCode = b+9;
              State = 'T';
              break;
              }
              else if (Unit[b] == unitCode & b >7){
              unitCode = b+1;
              State = 'F';
              break;
              }}}
    }
   }


void rf_decode(){//capture serial data from RF receiver
if (Serial1.available() > 0) { // is there active serial data ?
RXByte = Serial1.read(); // read the incoming RXByte:

      // Below is the encoding buffer, it takes the RXByte value for each pass/loop, and assigns it into one of four blocks
        if (RXByte >=0 && byte1 ==1) { byte1 = RXByte;     
        } if (RXByte >=0 && byte1 !=1 && byte2 ==1 && RXByte != byte1){ byte2 = RXByte;
        } if (RXByte >=0 && byte1 !=1 && byte2 !=1 && byte3 ==1 && RXByte != byte2){ byte3 = RXByte;
        } if (RXByte >=0 && byte1 !=1 && byte2 !=1 && byte3 !=1 &&byte4 ==1 && RXByte != byte3){ byte4 = RXByte;
        }
        // End of encoding buffer      
       
if (byte1 !=1 && byte2 !=1 && byte3 !=1 && byte4 !=1){ //if the buffer set is loaded, process code bellow

//houseCode = nibbleShift(byte1);
//unitCode = nibbleShift(byte3);

houseCode = byte1;
unitCode = byte3;

Parse_Frame();

byte1 =1; // Clear the buffer set back to 1 = OFF
byte2 =1; // Clear the buffer set back to 1 = OFF
byte3 =1; // Clear the buffer set back to 1 = OFF
byte4 =1;} // Clear the buffer set back to 1 = OFF
}
}

anyway, im hoping someone can see something obvious, its probably using a switch mode IC thats doing it :frowning:

thanks in advance

satmanuk