Guest User

Untitled

a guest
May 30th, 2013
200
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 37.83 KB | None | 0 0
  1. #include "DomoS.h"
  2. #include <Serial.h>
  3. #include <arduino.h>
  4. #include <EEPROM.h>
  5.  
  6. const byte DomoS::SETUP[DomoS::START] = {
  7.   168, 63};
  8.  
  9. const char* DomoS::COMMAND[DomoS::NCOMMAND] = {
  10.   "create",  //Create a new peripheral
  11.   //syntax: create [name test] [as 42/b00101010]
  12.  
  13.   "turn",    //Sent a signal to a peripheral
  14.   //syntax: turn name high/low/%10/v2.3
  15.  
  16.   "delete",  //Delete a peripheral
  17.   //syntax: delete name
  18.  
  19.   "exit",    //Turn off the DomoS Module
  20.   //syntax: exit
  21.  
  22.   "name",   //Define the name of the new peripheral
  23.   //Max 9 character
  24.   //Can be blank
  25.  
  26.   "as",     //Define the custom number/addressment of the new peripheral
  27.   //Can be blank
  28.   //Accept both decimal number and binary number
  29.  
  30.   "reset",      //Reset the DomoS module deletting the first two cells of EEPROM
  31.  
  32.   "list"        //Give a list of all the installed peripheral
  33. };
  34.  
  35. const char* DomoS::PHRASE[DomoS::NPHRASE] = {
  36.   "Write the number of address pins (max 8): ", //0
  37.   "Write the address pin: ", //1
  38.   "Do you want to store peripherals data into EEPROM? (-1 for yes or the CSpin): ", //2
  39.   "Error! Reinsert the asked data: ", //3
  40.   "Pin already used! Select another: ", //4
  41.   "Digital pin 6 will automatically used for output, don't select them!", //5
  42.   "Peripheral N whit number M (addressing B) created succesfully!", //6
  43.   "Welcome to DomoS", //7
  44.   "Resetting complete, now reset your arduino", //8
  45.   "Buy buy from me and my creator ;)", //9
  46.   "Peripheral N whit number M (addressing B)", //10
  47.   "Peripheral deletted succesfully" //11
  48. };
  49.  
  50. const char* DomoS::ERROR[DomoS::NERROR] = {
  51.   "YESH, no error :)",
  52.   "The command string you entered exeded 64 character,.",
  53.   "One of your sub command is too long.",
  54.   "Your main command wasn't recognized.",
  55.   "There are no command in your string.",
  56.   "One of the sub command wasn't recognized.",
  57.   "The name of the peripheral wasn't defined.",
  58.   "The name you entered is too long.",
  59.   "The address wasn't defined.",
  60.   "The binary number you entered is too long.",
  61.   "The EEPROM is full.",
  62.   "The peripheral you entered wasn't found.",
  63.   "Turn parameters wasn't recognized.",
  64.   "Random errors sometimes occurs.",
  65.   "The peripheral with number zero is not allowed.",
  66.   "The maximum number of allowed peripheral was reach.",
  67.   "The name you entered is not unique.",
  68.   "The number you entered is not unique.",
  69.   "Can't find a free standard name.",
  70.   "Can't find free address",
  71.   "The voltage you entered is too low.",
  72.   "he voltage you entered is too high.",
  73.   "The number you entered is too big.",
  74.   "There are no peripheral to be showed"
  75. };
  76.  
  77. DomoS::DomoS()
  78. /*  Standard costructor for the DomoS Module
  79.     At first, check if DomoS was already setup using the CheckSetupData
  80.     If is the first start call the FirstStart function then initialize the module whit Initialize,
  81.     else go directly to Initialize
  82.    
  83.     Debugged: Don't need to eb debugged
  84.  */
  85. {
  86.   Serial.begin(9600);
  87.   if (!CheckSetupData())
  88.     FirstStart();
  89.  
  90.   Initialize();
  91.  
  92.   Serial.println(PHRASE[7]);
  93.   return;
  94. }
  95.  
  96. boolean DomoS::CheckSetupData()
  97. /*  Check if the two setup value are present in the first two EEPROM cells
  98.  
  99.     Debugged: OK
  100.  */
  101. {
  102.   boolean ok;
  103.  
  104.   if ((EEPROM.read(0) == SETUP[0]) && (EEPROM.read(1) == SETUP[1]))
  105.     ok = true;
  106.   else
  107.     ok = false;
  108.  
  109.   return ok;
  110. }
  111.  
  112. void DomoS::Initialize()
  113. /*  Initialize all the DomoS' components
  114.     At first read all the configuration parameters from the EEPROM using
  115.     GetConfigurationDataFromEeprom, then initialize all the DomoS variables at a known state
  116.    
  117.     Debugged: Don't need to be debugged
  118.  */
  119. {
  120.   GetConfigurationDataFromEeprom();
  121.   _lastError = OK;      //Set the last error at no error (OK)
  122.   _command[0] = '\0';   //Set the command string at empty string
  123.   _subCommand[0] = '\0';    //Set the subcommand string at empty string
  124.   _on = true;               //Set the on parameter at true
  125.  
  126.   for(byte i = 0; i<_numAddressPin; i++)
  127.     pinMode(_addressPin[i], OUTPUT);
  128.  
  129.   pinMode(_outputPin, OUTPUT);
  130.  
  131.   /*if(_writeToEeprom != -1)
  132.    pinMode(_writeToEeprom, OUTPUT);*/
  133.  
  134.   return;
  135. }
  136.  
  137. void DomoS::GetConfigurationDataFromEeprom()
  138. /*  Get all the configuration parameters from the internal arduino EEPROM
  139.     Starting from START address start reading all the parameters following a specific sequence
  140.     if someone modify this sequence go to modify also WriteConfigurationDataToEeprom()
  141.    
  142.     Debugged: OK
  143.  */
  144. {
  145.   byte i;
  146.  
  147.   i = START;
  148.  
  149.   //Start reading all data
  150.   //After each reading increment i
  151.   _fileVer = EEPROM.read(i);
  152.   i++;
  153.   _numPeripheral = EEPROM.read(i);
  154.   i++;
  155.   _numAddressPin = EEPROM.read(i);
  156.   i++;
  157.  
  158.   //Cycle for avoid a sequence of 8 single reading
  159.   //After the cycle increment i
  160.   //Here are been used two index, j for the _adressPin and i for reading
  161.   for(byte j = 0; j<MAXADDRESSPIN; j++, i++)
  162.     _addressPin[j] = EEPROM.read(i);
  163.  
  164.   _outputPin = EEPROM.read(i);
  165.   i++;
  166.   _writeToEeprom = EEPROM.read(i);
  167.  
  168.   return;
  169. }
  170.  
  171. void DomoS::FirstStart()
  172. /*  Act the first start of DomoS
  173.     Clear the EEPROM, write the two inizial value into the EEPROM, ask all the configuration Data
  174.     and write them to the EEPROM
  175.    
  176.     Debugged: Don't need to be debugged
  177.  */
  178. {
  179.   DomoSFileHeader data;
  180.  
  181.   ClearEeprom();
  182.  
  183.   AskData(data);
  184.  
  185.   WriteConfigurationDataToEeprom(data);
  186.  
  187.   WriteSetupData();
  188.  
  189.   return;
  190. }
  191.  
  192. void DomoS::WriteSetupData()
  193. /*  Write the two setup value into the first two EEPROM cells
  194.    
  195.     Debugged: OK
  196.  */
  197. {
  198.   EEPROM.write(0, SETUP[0]);
  199.   EEPROM.write(1, SETUP[1]);
  200.  
  201.   return;
  202. }
  203.  
  204. void DomoS::ClearEeprom()
  205. /*  Clear all the EEPROM setting at 0 all the EEPROM cells
  206.     E2END constant contain the number of the last EEPROM cell
  207.    
  208.     Debugged: OK
  209.  */
  210. {
  211.   int i;
  212.  
  213.   //Cycle for all the EEPROM cells and set to 0
  214.   for(i = 0; i <= E2END; i++)
  215.     if(EEPROM.read(i) != 0)
  216.       EEPROM.write(i, 0);
  217.  
  218.   return;
  219. }
  220.  
  221. void DomoS::AskData(DomoSFileHeader & data)
  222. /*  Ask all the configuration data to the user usign the serial interface
  223.     Also check for correctness of inserted values
  224.    
  225.     Debugged: OK
  226.     Solved a problem into the part that ask the address pin
  227.     The first pin wont be checked if was equal to output pin
  228.  */
  229. {
  230.   byte val; //The value read by parseInt
  231.   byte i, j;
  232.   boolean ok;   //Tell if the values readed are correctly
  233.  
  234.   Serial.begin(9600); //Start the serial communication
  235.  
  236.   //Allarm the user about pin 6
  237.   Serial.println(PHRASE[5]);
  238.   data.outputPin = 6;
  239.  
  240.   //Read variable value for numAddressPin
  241.   Serial.println(PHRASE[0]); //Maybe i should create a custom function for writing phrases
  242.  
  243.   val = (byte)parseInt(); //Read the value
  244.  
  245.   //Check if the inserted value is greater than maximum
  246.   //Cycle until a correct value is read
  247.   while(val > MAXADDRESSPIN)
  248.   {
  249.     Serial.println(PHRASE[3]);
  250.  
  251.     val = (byte)parseInt();
  252.   }
  253.  
  254.   data.numAddressPin = val;
  255.   //End reading of numAddressPin
  256.  
  257.   //Read variable values for array addressPin
  258.  
  259.   //Cycle until read all the addressPin was read
  260.   i = 0;
  261.   while(i < data.numAddressPin)
  262.   {
  263.     Serial.println(PHRASE[1]);
  264.  
  265.     do //Read the value and search for duplicates
  266.     {
  267.       ok = true; //Assume that a correct value is read
  268.  
  269.       val = (byte)parseInt(); //Read the value
  270.  
  271.       //Check if this value is different from the previous
  272.       //Cycle until checked all the previous values or found an identical value
  273.       j = 0;
  274.       if(val != data.outputPin)
  275.       {
  276.         while ((j < i) && (ok))
  277.         {
  278.           if ((val == data.addressPin[j]))
  279.             ok = false;
  280.           else
  281.             j++;
  282.         }
  283.       }
  284.       else
  285.         ok = false;
  286.  
  287.       if (!ok)
  288.         Serial.println(PHRASE[3]);
  289.  
  290.  
  291.     }
  292.     while (!ok);
  293.  
  294.     data.addressPin[i] = val; //Write the value and go ahead
  295.     i++;
  296.   }
  297.  
  298.   //Now that we read all the requested value, fill whit -1 all the other values
  299.   for(i = i; i < MAXADDRESSPIN; i++)
  300.     data.addressPin[i] = -1;
  301.  
  302.   //End reading of array addressPin
  303.  
  304.   //Read variable value for writeToEeprom
  305.   Serial.println(PHRASE[2]);
  306.  
  307.   val = (byte)parseInt();
  308.  
  309.   data.writeToEeprom = val;
  310.   //End reading for writeToEeprom
  311.  
  312.   data.fileVer = FILEVER; //Set fileVer to the internal file version
  313.   data.numPeripheral = 0; //Set the number of peripheral to 0
  314.  
  315.     return;
  316. }
  317.  
  318. int DomoS::parseInt()
  319. /*  Parse an int from the first arduino serial port
  320.     Don't substitute the originale Serial.parseInt function
  321.     Use some trick for being sure that data was read
  322.    
  323.     Debugged: OK
  324.  */
  325. {
  326.   boolean serialFetch;  //Tell if data was read from the serial port
  327.   int val;              //The value returned from Serial.parseInt
  328.  
  329.   serialFetch = false; //No dafa was read from the serial port
  330.   while(!serialFetch) //Cycle until data was read
  331.     if(Serial.available())
  332.     {
  333.       delay(4); //Wait 4 millisecons for allowing the serial port to ger data
  334.       val = (int)Serial.parseInt(); //Parse the integer value from the serial port
  335.       serialFetch = true;
  336.     }
  337.   Serial.flush(); //Free the serial buffer
  338.  
  339.   return val;
  340. }
  341.  
  342. void DomoS::WriteConfigurationDataToEeprom (DomoSFileHeader data)
  343. /*  Write the configuration parameters contain in data
  344.     Starting from START address start writing all the parameters following a specific sequence
  345.     If someone modify this sequence go to modify also GetConfigurationDataFromEeprom()
  346.    
  347.     Debugged: OK
  348.  */
  349. {
  350.   byte i;
  351.  
  352.   i = START;
  353.  
  354.   //Start writing all data
  355.   //After each writing increment i
  356.   EEPROM.write(i, data.fileVer);
  357.   i++;
  358.   EEPROM.write(i, data.numPeripheral);
  359.   i++;
  360.   EEPROM.write(i, data.numAddressPin);
  361.   i++;
  362.  
  363.   //Cycle for avoid a sequence of 8 single writing
  364.   //After the cycle increment i
  365.   //Here are been used two index, j for the _addressPin and i for writing
  366.   for(byte j = 0; j < MAXADDRESSPIN; i++, j++)
  367.     EEPROM.write(i, data.addressPin[j]);
  368.  
  369.   EEPROM.write(i, data.outputPin);
  370.   i++;
  371.   EEPROM.write(i, data.writeToEeprom);
  372.  
  373.   return;
  374. }
  375.  
  376. boolean DomoS::ConvertDecimalToBinary(int number, boolean result[])
  377. /*  Convert a decimal number into an array of boolean value, false for 0, true for 1
  378.     Return false if the number is too big for the conversion, true if the conversion goes right
  379.    
  380.     Debugged: OK
  381.     Corrected a typo on the first if [<= -> >=]
  382.     Solved a problem on the first if, div should be divided by 2
  383.  */
  384. {
  385.   int part;
  386.   int div;
  387.   int i;
  388.   boolean ok;
  389.  
  390.   ok = true; //Assume the conversion goes right
  391.   div = 1 << _numAddressPin; //Equal to 2 ^ _numAddressPin
  392.   if ((div - 1) >= number) //Check if the number is too big
  393.   {
  394.     div = div/2;
  395.     i = 0;
  396.     part = number;
  397.  
  398.     while (i < _numAddressPin)
  399.     {
  400.       if (part / div == 1)
  401.       {
  402.         result[i] = true;
  403.         part = part % div;
  404.       }
  405.       else
  406.         result[i] = false;
  407.  
  408.       i++;
  409.       div = div / 2;
  410.     }
  411.   }
  412.   else
  413.     ok = false;
  414.  
  415.   return ok;
  416. }
  417.  
  418. void DomoS::SetAddressing(boolean addressing[])
  419. /*  Set the addressing pin to the values contained in addressing array
  420.    
  421.     Debugged: OK
  422.  */
  423. {
  424.   byte i;
  425.  
  426.   //Cycle for all the addressing pin
  427.   for (i = 0; i < _numAddressPin; i++)
  428.     //Set the addressing pin to HIGH or LOW depending on addressing values
  429.     digitalWrite(_addressPin[i], (addressing[i] ? HIGH : LOW));
  430.  
  431.   return;
  432. }
  433.  
  434. byte DomoS::SeparateCommandBySpace()
  435. /*  Separate the _command string into two string:
  436.     The _subCommand string which contain the first word of _command before a space and the _command
  437.     string which contain the original _command string whitouth the word in _subCommand
  438.    
  439.     Debugged: OK
  440.     Added in the first while the control for the string terminator
  441.     Added a control for eliminate the space after a word
  442.     Solved an error in the do...while
  443.  */
  444. {
  445.   byte i, j;
  446.   byte readChar;
  447.  
  448.   readChar = 0; //Assume we don't read any character
  449.   i = 0;
  450.   j = 0;
  451.  
  452.   //Cycle until hw found a space or _subCommand is too long
  453.   while ((_command[i] != ' ') && (_command[i] != '\0') && (j < SUBSTRINGMAXLEN))
  454.   {
  455.     _subCommand[j] = _command[i]; //Copy the first word
  456.     i++;
  457.     j++;
  458.   }
  459.  
  460.   if (j < SUBSTRINGMAXLEN) //Check if _subCommand is too long
  461.   {
  462.     _subCommand[j] = '\0'; //Terminate the string
  463.     readChar = j; //Set the number of character readed
  464.  
  465.     if (_command[i] == ' ') //_command[i] can be ' ' or '\0', go jump of one character if is a
  466.       //space, not if is the string terminator
  467.       i++;
  468.  
  469.     //Start deletting the first word into _command string
  470.     j = 0;
  471.     //Cycle until we found the string terminator
  472.     do
  473.     {
  474.       _command[j] = _command[i];
  475.       j++;
  476.       i++;
  477.     }
  478.     while(_command[i - 1] != '\0');
  479.  
  480.     _command[j]= '\0'; //Terminate the string
  481.   }
  482.   else
  483.   {
  484.     _lastError = SUBCOMMANDSTRINGTOOLONG; //Set the error
  485.     //Deletting _command and _subCommand
  486.     _command[0] = '\0';
  487.     _subCommand[0] = '\0';
  488.  
  489.     readChar = -1; //Setting readChar at an error state
  490.   }
  491.  
  492.   return readChar;
  493. }
  494.  
  495. byte DomoS::CompareSubCommand()
  496. /*  Compare the _subCommand string whit the commands dictnionary
  497.     For avoid useless comparisons we set and start and end parameters
  498.     If don't found the command return the successive index
  499.    
  500.     Debugged: OK
  501.  */
  502. {
  503.   boolean find;
  504.   byte i;
  505.  
  506.   find = false;
  507.   i = 0;
  508.   //Cycle until find or don't find the command
  509.   while((!find) && (i < NCOMMAND))
  510.   {
  511.     if(strcmp(_subCommand, COMMAND[i]) == 0) //Compare _subCommand whit a command
  512.       find = true;
  513.     else
  514.       i++;
  515.   }
  516.  
  517.   return i;
  518. }
  519.  
  520. void DomoS::CommandToLowerCase()
  521. /*  Convert the command string into lower case
  522.    
  523.     Debugged: OK
  524.  */
  525. {
  526.   byte i;
  527.  
  528.   i = 0;
  529.   //Cycle until string terminator
  530.   while (_command[i] != '\0')
  531.   {
  532.     //Check if there's an upper case character
  533.     if ((_command[i] >= 'A') && (_command[i] <= 'Z'))
  534.       _command[i] += 32; //Convert to lower case (es: A == 65 -> a == 97)
  535.  
  536.     i++;
  537.   }
  538.  
  539.   return;
  540. }
  541.  
  542. void DomoS::Work()
  543. /*  This function allow the DomoS to work
  544.    
  545.     Debugged: Don't need to be debugged
  546.  */
  547. {
  548.   if (GetError() == OK) //Control if there's an error pending
  549.   {
  550.     if(Serial.available()) //Controll if there's something to be read from the serial port
  551.     {
  552.       if(FetchCommand()) //Fetch the command from the serial port
  553.       {
  554.         CommandToLowerCase(); //Convert the _command string to lower case
  555.         if(SeparateCommandBySpace() > 0) //Separate _command string and check if separation
  556.           //end correclty
  557.         {
  558.           DoCommand(CompareSubCommand()); //Compare the command whit the dictionary and
  559.           //execute the relative command
  560.         }
  561.       }
  562.     }
  563.   }
  564.   else
  565.     ThrownError();
  566.  
  567.   return;
  568. }
  569.  
  570. byte DomoS::GetCommand(char* command)
  571. /*  Get the index of a command from the COMMAND array
  572.  */
  573. {
  574.   boolean find;
  575.   byte i;
  576.  
  577.   find = false;
  578.   i = 0;
  579.   //Cycle until find or don't find the command
  580.   while((!find) && (i < NCOMMAND))
  581.   {
  582.     if(strcmp(command, COMMAND[i]) == 0) //Compare _command whit a command
  583.       find = true;
  584.     else
  585.       i++;
  586.   }
  587.  
  588.   return i;
  589. }
  590.  
  591. boolean DomoS::FetchCommand()
  592. /*  Fetch a command from the serial port
  593.     This function can be changed to whatever change the _command for input of commands
  594.    
  595.     Debugged: In part
  596.     Need more tests
  597.     Logically is right, but in case the user input too much character the serial buffer wont be free
  598.  */
  599. {
  600.   boolean ok;
  601.   byte i;
  602.  
  603.   i = 0;
  604.   ok = true; //Assume to read a correct string
  605.   //Cycle until a character is avaible from the serial port and too many character are read
  606.   while ((Serial.available() > 0) && (i < STRINGMAXLEN))
  607.   {
  608.     _command[i] = Serial.read(); //Put the readed character into the _command string
  609.     i++;
  610.     delay(2); //Wait 2ms for allowing the serial buffer to fill whit the next character
  611.   }
  612.  
  613.   //Check if too many character was read
  614.   if (i < STRINGMAXLEN)
  615.     _command[i]='\0'; //Terminate the string
  616.   else
  617.   {
  618.     //Too much character was read
  619.     Serial.flush(); //Free the serial buffer
  620.     _lastError = COMMANDSTRINGTOOLONG; //Set the error
  621.     _command[0] = '\0'; //Empty the string
  622.     ok = false;
  623.   }
  624.  
  625.   return ok;
  626. }
  627.  
  628. void DomoS::DoCommand(byte numCommand)
  629. /*  Execute one of the basic comman
  630.    
  631.     Debugged: Don't need to be debugged
  632.  */
  633. {
  634.   switch (numCommand)
  635.   {
  636.   case 0:
  637.     Create();
  638.     break;
  639.  
  640.   case 1:
  641.     Turn();
  642.     break;
  643.  
  644.     /*case 2:
  645.                 Delete();
  646.                 break;
  647.             */    //Maybe in some next version i'll develope this, but for instance get rid of it!
  648.  
  649.   case 3:
  650.     Exit();
  651.     break;
  652.  
  653.   case 6:
  654.     Reset();
  655.     break;
  656.  
  657.   case 7:
  658.     List();
  659.     break;
  660.  
  661.   default:
  662.     //If the command aren't recognized, return an error
  663.     _lastError = COMMANDNOTRECOGNIZED;
  664.   }
  665.  
  666.   return;
  667. }
  668.  
  669. void DomoS::Create()
  670. /*  This fuction act the creation of a new peripheral
  671.     Check the _command string for all the configuration parameters
  672.    
  673.     If everithing went right, write this new peripheral into the EEPROM/file
  674.  */
  675. {
  676.   byte readChar; //The number opf character separed from the separator
  677.   boolean error;
  678.   DomoSFileBody newPeripheral; //The new peripheral to be write
  679.   byte val, i;
  680.  
  681.   BlankNewPeripheral(newPeripheral); //Initialize the newPeripheral to known value
  682.  
  683.   error = false; //Assume there's no error
  684.   if (_numPeripheral < ((1 << _numAddressPin) - 1))
  685.   {
  686.     if(SeparateCommandBySpace() > 0)
  687.     {
  688.       //Cycle when we have more parameters and there're no error
  689.       do //Start cycle for checking parameters
  690.       {
  691.         switch(CompareSubCommand()) //Start extern switch
  692.         {
  693.         case 4: //Define the name of the new peripheral
  694.           readChar = SeparateCommandBySpace();
  695.           if (readChar > 0) //Check if separation goes right
  696.           {
  697.             if(readChar < MAXNAMELEN) //Check if the name wasn't too long
  698.             {
  699.               for (i = 0; _subCommand[i] != '\0'; i++) //Copy the name into the
  700.                 //new peripheral
  701.                 newPeripheral.name[i] = _subCommand[i];
  702.  
  703.               newPeripheral.name[i] = '\0';
  704.             }
  705.             else //Else set an error
  706.             {
  707.               _lastError = NAMETOOLONG;
  708.               error = true;
  709.             }
  710.           }
  711.           else
  712.           {
  713.             _lastError = NAMENOTDEFINED;
  714.             error = true;
  715.           }
  716.           break;
  717.  
  718.           //Define the custom address name for the new peripheral
  719.         case 5:
  720.           readChar = SeparateCommandBySpace();
  721.  
  722.           if (readChar > 0) //Check if separation goes right
  723.           {
  724.             if (_subCommand[0] == 'b') //Check if the user set a binary address
  725.             {
  726.               if(readChar > (_numAddressPin + 1)) //Check if there're too many bit
  727.               {
  728.                 error = true;
  729.                 _lastError = BINARYNUMBERTOOLONG;
  730.               }
  731.               else
  732.               {
  733.                 SubCommandShiftLeft();
  734.                 //Convert the binary string into a decimal number
  735.                 newPeripheral.number = ConvertBinaryStringToDecimal();
  736.               }
  737.             }
  738.             else
  739.             {
  740.               //Convert the decimal string into a decimal number
  741.               val = (byte)atoi(_subCommand);
  742.               if (val < (1 << _numAddressPin))
  743.                 newPeripheral.number = val;
  744.               else
  745.               {
  746.                 error = true;
  747.                 _lastError = DECIMALNUMBERTOOBIG;
  748.               }
  749.             }
  750.           }
  751.           else //Set an error state
  752.           {
  753.             error = true;
  754.             _lastError = ASNOTDEFINED;
  755.           }
  756.           break;
  757.  
  758.         default: //Set an error if no command was recognized
  759.           _lastError = SUBCOMMANDNOTRECOGNIZED;
  760.           error = true;
  761.           break;
  762.         } //End extern switch
  763.         readChar = SeparateCommandBySpace();
  764.       }
  765.       while((readChar > 0) && (!error)); //End cycle for checking parameters
  766.     }
  767.  
  768.     //If there're no error try creating the new peripheral
  769.     if(!error)
  770.     {
  771.       //Check if we have all the data needed
  772.       if (CreateParameterCheck(newPeripheral))
  773.       {
  774.         //Write the peripheral
  775.         if (WritePeripheral(newPeripheral, _numPeripheral))
  776.         {
  777.           UpdateNumPeripheral('+');
  778.           ComposeStringPeripheral(newPeripheral, 6);
  779.         }
  780.       }
  781.     }
  782.   }
  783.   else
  784.     _lastError = PERIPHERALMAXIMUMNUMBERREACH;
  785.  
  786.  
  787.   return;
  788. }
  789.  
  790. void DomoS::BlankNewPeripheral (DomoSFileBody & peripheral)
  791. /*  Initialize a peripheral to known values
  792.    
  793.     Debugged: Don't need to be debugged
  794.  */
  795. {
  796.   peripheral.name[0] = '\0';
  797.   peripheral.number = -1;
  798.  
  799.   return;
  800. }
  801.  
  802. boolean DomoS::CreateParameterCheck(DomoSFileBody & peripheral)
  803. /*  Controll if all the data needed for the creation of a peripheral are present
  804.     Also fill the empty values if they aren't required
  805.  */
  806. {
  807.   boolean ok;
  808.   boolean nameCustom, numberCustom; //True if the user defined a custom name/number
  809.  
  810.   nameCustom = true;
  811.   numberCustom = true; //Assume the user defined a custom name/number
  812.  
  813.   if (peripheral.number != 0) //Check if the number wasn't defined
  814.   {
  815.     if (peripheral.number == (byte)-1) //Check if the peripheral is 0
  816.     {
  817.       numberCustom = false;
  818.       peripheral.number = _numPeripheral + 1; //If not set the number at the current number of
  819.       //peripheral
  820.     }
  821.  
  822.     if (peripheral.name[0] == '\0') //Check if the name wasn't defined
  823.     {
  824.       nameCustom = false;
  825.       itoa((int)peripheral.number, peripheral.name, 10); //If not set the number as the
  826.       //name
  827.     }
  828.  
  829.     //Search if the currect peripheral have duplicated parameters and try to correct it
  830.     ok = SearchDuplicatedPeripheral(peripheral, nameCustom, numberCustom);
  831.   }
  832.   else
  833.   {
  834.     _lastError = PERIPHERALZERONOTALLOWED;
  835.     ok = false;
  836.   }
  837.  
  838.   return ok;
  839. }
  840.  
  841. boolean DomoS::WritePeripheral(DomoSFileBody peripheral, byte position)
  842. /*  Write the peripheral on the EEPROM or on the SD if was selected
  843.    
  844.     Debugged: Don't need to be debugged
  845.  */
  846. {
  847.   boolean ok;
  848.  
  849.   ok = true; //Assume the writing goes right
  850.  
  851.   if(_writeToEeprom == (byte)-1) //Check if a CSPin was set
  852.     ok = WritePeripheralToEeprom(peripheral, position); //If not write to EEPROM
  853.   /*else
  854.         ok = WritePeripheralToSd(peripheral, position);*/  //Because i don't own a sd card to test, for the
  855.   //instance i wont develope this function
  856.  
  857.   return ok;
  858. }
  859.  
  860. boolean DomoS::WritePeripheralToEeprom(DomoSFileBody peripheral, byte position)
  861. /*  Write the peripheral to the EEPROM
  862.    
  863.     Debugged: OK
  864.     Solved a erroneus increment of i
  865.  */
  866. {
  867.   DomoSFileHeader configuration; //Only used for sizeof function
  868.   int start; //The starting address
  869.   byte i, j;
  870.   boolean ok;
  871.  
  872.   ok = true; //Assume the writing goes right
  873.  
  874.   //Start to write the new peripheral from the address described by this formula
  875.   //2 = the first two cells are occupied by the setup values
  876.   //sizeof(configuration) = the next cells are occupied by the configuration parameters
  877.   //In the EEPROM there're _numPeripheral peripheral big sizeof(peripheral), so go ahead
  878.   //for all this peripheral
  879.   start = 2 + sizeof(configuration) + (sizeof(peripheral) * position);
  880.  
  881.   if ((start + sizeof(peripheral)) < E2END) //Check if the EEPROM can contain the new peripheral
  882.   {
  883.     //Start writing peripheral
  884.     for(j = 0; j < MAXNAMELEN; j++, start++)
  885.       EEPROM.write(start, peripheral.name[j]);
  886.  
  887.     EEPROM.write(start, peripheral.number);
  888.   }
  889.   else  //ERROR, the EEPROM is full
  890.   {
  891.     ok = false;
  892.     _lastError = EEPROMISFULL;
  893.   }
  894.  
  895.   return ok;
  896. }
  897.  
  898. void DomoS::UpdateNumPeripheral(char type)
  899. /*  Update the number of peripheral
  900.    
  901.     Debugged: Don't need to be debugged
  902.  */
  903. {
  904.   if (type == '+')
  905.     _numPeripheral++;
  906.   else
  907.     _numPeripheral--;
  908.   EEPROM.write(3, _numPeripheral);
  909.   //TODO Update also the number contained on the SDCard
  910.  
  911.   return;
  912. }
  913.  
  914. void DomoS::Turn()
  915. /*  Act the Turn command
  916.  */
  917. {
  918.   byte peripheral;
  919.   int val;
  920.   boolean addressing[_numAddressPin];
  921.  
  922.   SeparateCommandBySpace();
  923.  
  924.   peripheral = SearchPeripheralByName(_subCommand); //Find the peripheral
  925.   if(peripheral != (byte)-1)
  926.   {
  927.     SeparateCommandBySpace();
  928.  
  929.     switch(_subCommand[0]) //Controll the first _subCommand character
  930.     {
  931.     case '%': //If there's an % the user set a percentage
  932.       SubCommandShiftLeft(); //delete the % simbol
  933.       val = map(atoi(_subCommand), 0, 100, 0, 255); //Convert from percentage to val
  934.       break;
  935.  
  936.     case 'v': //If there's an v the user set a voltage
  937.       SubCommandShiftLeft(); //Delete the v simobl
  938.       val = atof(_subCommand);
  939.  
  940.       //Check if the voltage is too high or low
  941.       if ((val >= 0) && (val <= 5))
  942.         val = map(atof(_subCommand), 0, 5, 0, 255); //Convert from volt to val
  943.       else if (val < 0)
  944.         _lastError = VOLTAGETOOLOW;
  945.       else
  946.         _lastError = VOLTAGETOOHIGH;
  947.       break;
  948.  
  949.     case 'l': //If there's an l the user set a logic low signal
  950.       val = 0; //Set val to 0
  951.       break;
  952.  
  953.     case 'h': //If there's an h the user set a logic high signal
  954.       val = 255; //set val to 255
  955.       break;
  956.  
  957.     default: //If something else was set, set an error
  958.       val = -1;
  959.       _lastError = STRANGETURNPARAMETER;
  960.       break;
  961.     }
  962.  
  963.     if (val > -1)
  964.     {
  965.       byte number;
  966.       GetPeripheralNumber(peripheral, number);
  967.       //Convert the peripheral number into binary for the addressing
  968.       if (ConvertDecimalToBinary(number, addressing))
  969.       {
  970.         analogWrite(_outputPin, val); //Set the outputPin at val
  971.         delay(RCLOAD); //Wait for charging of rc circuit
  972.  
  973.         SetAddressing(addressing); //Set the addressing line
  974.        
  975.         delay(1000); //Wait for spread of signals
  976.        
  977.         //Clean everything
  978.         analogWrite(_outputPin, 0);
  979.         ConvertDecimalToBinary(0, addressing);
  980.         SetAddressing(addressing);
  981.       }
  982.       else //If we can't convert into binary... IMPOSSIBURU
  983.       _lastError = BADTHINGSHAPPEN;
  984.     }
  985.   }
  986.   else //If the peripheral isn't present set an error
  987.   _lastError = PERIPHERALNOTFOUND;
  988. }
  989.  
  990. void DomoS::Exit()
  991. /*  Act the exit from the system
  992.    
  993.     Debugged: Don't need to be debugged
  994.  */
  995. {
  996.   _on = false;
  997.   Serial.println(PHRASE[9]);
  998.   Serial.end();
  999.  
  1000.   return;
  1001. }
  1002.  
  1003. void DomoS::SubCommandShiftLeft()
  1004. /*  Shift of one character to left the _subCommand string
  1005.    
  1006.     Debugged: OK
  1007.     Corrected some typo
  1008.  */
  1009. {
  1010.   byte i;
  1011.  
  1012.   i = 0;
  1013.   do
  1014.   {
  1015.     _subCommand[i] = _subCommand[i+1];
  1016.     i++;
  1017.   }
  1018.   while (_subCommand[i] != '\0');
  1019.  
  1020.   return;
  1021. }
  1022.  
  1023. byte DomoS::SearchPeripheralByName(char peripheral[])
  1024. /*  Search the peripheral by name
  1025.     The function return the index of the peripheral or -1 if not found
  1026.    
  1027.     Debugged: OK
  1028.  */
  1029. {
  1030.   boolean find;
  1031.   byte i;
  1032.   char name[MAXNAMELEN];
  1033.  
  1034.   find = false; //Assume we don't find the peripheral
  1035.   //Cycle until we find the peripheral or the peripherals are finished
  1036.   i = 0;
  1037.   while ((i < _numPeripheral) && (!find))
  1038.   {
  1039.     GetPeripheralName(i, name); //Get the name of the i-th peripheral
  1040.  
  1041.     if (strcmp(peripheral, name) == 0) //Check if the name are equal
  1042.       find = true; //We find the peripheral
  1043.     else
  1044.       i++; //Go ahead
  1045.   }
  1046.  
  1047.   if (!find) //if the peripheral wasn't find set an error
  1048.     i = -1;
  1049.  
  1050.   return i;
  1051. }
  1052.  
  1053. void DomoS::GetPeripheralName(byte numPeripheral, char name[])
  1054. /*  Put into char name[] the name of the numPeripheral-th peripheral
  1055.    
  1056.     Debugged: Ok
  1057.     Modify the second sizeof for calculate the size of the correct structure
  1058.  */
  1059. {
  1060.   int peripheral;
  1061.   DomoSFileBody body;
  1062.   DomoSFileHeader configuration;
  1063.   byte i;
  1064.  
  1065.   //The numPeripheral-th peripheral is stored from the address described by this formula
  1066.   //2 = the first two cells are occupied by the setup values
  1067.   //sizeof(configuration) = the next cells are occupied by the configuration parameters
  1068.   //In the EEPROM there're numPeripheral peripheral big sizeof(peripheral), so go ahead
  1069.   //for all this peripheral
  1070.   peripheral = 2 + sizeof(configuration) + (sizeof(body) * numPeripheral);
  1071.  
  1072.   for (i = 0; i < MAXNAMELEN; i++)
  1073.     name[i] = EEPROM.read(peripheral + i);
  1074.  
  1075.   return;
  1076. }
  1077.  
  1078. boolean DomoS::SearchDuplicatedPeripheral(DomoSFileBody & peripheral, boolean nameCustom, boolean numberCustom)
  1079. /*  Search for duplicated peripheral, both by name and number
  1080.     If no custom name and number was set, modify that for making the new peripheral unique
  1081.  */
  1082. {
  1083.   boolean error;
  1084.   byte i;
  1085.  
  1086.   error = false; //Assume that there aren't errors
  1087.   if (nameCustom) //Check if the user set the name
  1088.   {
  1089.     if (SearchPeripheralByName(peripheral.name) != (byte)-1) //Check if the user's name is already present
  1090.     {
  1091.       _lastError = PERIPHERALNAMENOTUNIQUE;
  1092.       error = true;
  1093.     }
  1094.   }
  1095.  
  1096.   if ((numberCustom) && (!error)) //Check if the user set a number and there aren't errors
  1097.   {
  1098.     if (SearchPeripheralByNumber(peripheral.number) != (byte)-1) //Check if the user's number is already present
  1099.     {
  1100.       _lastError = PERIPHERALNUMBERNOTUNIQUE;
  1101.       error = true;
  1102.     }
  1103.   }
  1104.  
  1105.   if ((!nameCustom) && (!error)) //Check if the user doesn't set a name and there aren't errors
  1106.   {
  1107.     i = 0;
  1108.     //Cycle until the allowed name are finished (a bit strange, but i think can happen) or
  1109.     //a free name was found
  1110.     while ((i < 255) && (SearchPeripheralByName(peripheral.name) != (byte)-1))
  1111.     {
  1112.       itoa((atoi(peripheral.name) + 1), peripheral.name, 10); //Same as peripheral.name++;
  1113.       i++;
  1114.     }
  1115.  
  1116.     if (i == 255) //Check if no available name was found
  1117.     {
  1118.       //If yes set an error
  1119.       error = true;
  1120.       _lastError = CANTFINDFREENAME;
  1121.     }
  1122.   }
  1123.  
  1124.   if ((!numberCustom) && (!error))
  1125.   {
  1126.     i = 0;
  1127.     //Cycle until the allowed number are finished (a bit strange, but i think can happen) or
  1128.     //a free number was found
  1129.     while ((i < ((1 << _numAddressPin) - 1)) && (SearchPeripheralByNumber(peripheral.number) != (byte)-1))
  1130.     {
  1131.       peripheral.number = ((peripheral.number + 1) % (1 << _numAddressPin));
  1132.       if(peripheral.number == 0)
  1133.         peripheral.number++;
  1134.       i++;
  1135.     }
  1136.  
  1137.     if (i == ((1 << _numAddressPin) - 1)) //Check if no available number was found
  1138.     {
  1139.       error = true;
  1140.       _lastError = CANTFINDFREENUMBER;
  1141.     }
  1142.   }
  1143.  
  1144.   return (!error);
  1145. }
  1146.  
  1147. byte DomoS::SearchPeripheralByNumber(byte peripheral)
  1148. /*  Search the peripheral by number
  1149.     The function return the index of the peripheral or -1 if not found
  1150.    
  1151.     Debugged: OK
  1152.  */
  1153. {
  1154.   boolean find;
  1155.   byte i;
  1156.   byte number;
  1157.  
  1158.   find = false; //Assume we don't find the peripheral
  1159.   //Cycle until we find the peripheral or the peripherals are finished
  1160.   i = 0;
  1161.   while ((i < _numPeripheral) && (!find))
  1162.   {
  1163.     GetPeripheralNumber(i, number); //Get the name of the i-th peripheral
  1164.  
  1165.     if (peripheral == number) //Check if the name are equal
  1166.       find = true; //We find the peripheral
  1167.     else
  1168.       i++; //Go ahead
  1169.   }
  1170.  
  1171.   if (!find) //if the peripheral wasn't find set an error
  1172.     i = -1;
  1173.  
  1174.   return i;
  1175. }
  1176.  
  1177. void DomoS::GetPeripheralNumber(byte numPeripheral, byte & number)
  1178. /*  Put into char name[] the name of the numPeripheral-th peripheral
  1179.    
  1180.     Debugged: Ok
  1181.     Modify the second sizeof for calculate the size of the correct structure
  1182.  */
  1183. {
  1184.   int peripheral;
  1185.   DomoSFileBody body;
  1186.   DomoSFileHeader configuration;
  1187.   byte i;
  1188.  
  1189.   //The numPeripheral-th peripheral is stored from the address described by this formula
  1190.   //2 = the first two cells are occupied by the setup values
  1191.   //sizeof(configuration) = the next cells are occupied by the configuration parameters
  1192.   //In the EEPROM there're numPeripheral peripheral big sizeof(peripheral), so go ahead
  1193.   //for all this peripheral
  1194.   //Before the number thare're the name of the peripheral, so go ahead of MAXNAMELEN cells
  1195.   peripheral = 2 + sizeof(configuration) + (sizeof(body) * numPeripheral) + MAXNAMELEN;
  1196.  
  1197.   number = EEPROM.read(peripheral);
  1198.  
  1199.   return;
  1200. }
  1201.  
  1202. void DomoS::ThrownError()
  1203. /*  Give a description of the last error occurred
  1204.    
  1205.     Debugged: Don't need to be debugged
  1206.  */
  1207. {
  1208.   //Get the error
  1209.   switch (GetError())
  1210.     //Give a little description
  1211.   {
  1212.   case COMMANDSTRINGTOOLONG:
  1213.     Serial.println(ERROR[COMMANDSTRINGTOOLONG]);
  1214.     break;
  1215.  
  1216.   case SUBCOMMANDSTRINGTOOLONG:
  1217.     Serial.println(ERROR[SUBCOMMANDSTRINGTOOLONG]);
  1218.     break;
  1219.  
  1220.   case COMMANDNOTRECOGNIZED:
  1221.     Serial.println(ERROR[COMMANDNOTRECOGNIZED]);
  1222.     break;
  1223.  
  1224.   case NOCOMMANDPARAMETERS:
  1225.     Serial.println(ERROR[NOCOMMANDPARAMETERS]);
  1226.     break;
  1227.  
  1228.   case SUBCOMMANDNOTRECOGNIZED:
  1229.     Serial.println(ERROR[SUBCOMMANDNOTRECOGNIZED]);
  1230.     break;
  1231.  
  1232.   case NAMENOTDEFINED:
  1233.     Serial.println(ERROR[NAMENOTDEFINED]);
  1234.     break;
  1235.  
  1236.   case NAMETOOLONG:
  1237.     Serial.println(ERROR[NAMETOOLONG]);
  1238.     break;
  1239.  
  1240.   case ASNOTDEFINED:
  1241.     Serial.println(ERROR[ASNOTDEFINED]);
  1242.     break;
  1243.  
  1244.   case BINARYNUMBERTOOLONG:
  1245.     Serial.println(ERROR[BINARYNUMBERTOOLONG]);
  1246.     break;
  1247.  
  1248.   case EEPROMISFULL:
  1249.     Serial.println(ERROR[EEPROMISFULL]);
  1250.     break;
  1251.  
  1252.   case PERIPHERALNOTFOUND:
  1253.     Serial.println(ERROR[PERIPHERALNOTFOUND]);
  1254.     break;
  1255.  
  1256.   case STRANGETURNPARAMETER:
  1257.     Serial.println(ERROR[STRANGETURNPARAMETER]);
  1258.     break;
  1259.  
  1260.   case BADTHINGSHAPPEN:
  1261.     Serial.println(ERROR[BADTHINGSHAPPEN]);
  1262.     break;
  1263.  
  1264.   case PERIPHERALZERONOTALLOWED:
  1265.     Serial.println(ERROR[PERIPHERALZERONOTALLOWED]);
  1266.     break;
  1267.  
  1268.   case PERIPHERALMAXIMUMNUMBERREACH:
  1269.     Serial.println(ERROR[PERIPHERALMAXIMUMNUMBERREACH]);
  1270.     break;
  1271.  
  1272.   case PERIPHERALNAMENOTUNIQUE:
  1273.     Serial.println(ERROR[PERIPHERALNAMENOTUNIQUE]);
  1274.     break;
  1275.  
  1276.   case PERIPHERALNUMBERNOTUNIQUE:
  1277.     Serial.println(ERROR[PERIPHERALNUMBERNOTUNIQUE]);
  1278.     break;
  1279.  
  1280.   case CANTFINDFREENAME:
  1281.     Serial.println(ERROR[CANTFINDFREENAME]);
  1282.     break;
  1283.  
  1284.   case CANTFINDFREENUMBER:
  1285.     Serial.println(ERROR[CANTFINDFREENUMBER]);
  1286.     break;
  1287.  
  1288.   case VOLTAGETOOLOW:
  1289.     Serial.println(ERROR[VOLTAGETOOLOW]);
  1290.     break;
  1291.  
  1292.   case VOLTAGETOOHIGH:
  1293.     Serial.println(ERROR[VOLTAGETOOHIGH]);
  1294.     break;
  1295.  
  1296.   case DECIMALNUMBERTOOBIG:
  1297.     Serial.println(ERROR[DECIMALNUMBERTOOBIG]);
  1298.     break;
  1299.  
  1300.   case THEREAREZEROPERIPHERAL:
  1301.     Serial.println(ERROR[THEREAREZEROPERIPHERAL]);
  1302.     break;
  1303.    
  1304.   default:
  1305.     Serial.println(ERROR[BADTHINGSHAPPEN]);
  1306.     break;
  1307.   }
  1308.  
  1309.   _lastError = OK;
  1310.  
  1311.   return;
  1312. }
  1313.  
  1314. byte DomoS::GetError()
  1315. /*  Return the last error
  1316.    
  1317.     Debugged: Don't need to be debugged
  1318.  */
  1319. {
  1320.   return _lastError;
  1321. }
  1322.  
  1323. byte DomoS::ConvertBinaryStringToDecimal()
  1324. /*  Convert the _subCommand string from binary to decimal
  1325.    
  1326.     Debugged: OK
  1327.     Corrected some typos [base/2 -> base = base/2], [_subCommand[i] == 1 -> == '1']
  1328.  */
  1329. {
  1330.   byte base;
  1331.   byte i;
  1332.   byte number;
  1333.  
  1334.   base = 1 << (_numAddressPin - 1);
  1335.  
  1336.   for (i = 0, number = 0; i < _numAddressPin; i++, base = base/2)
  1337.     if (_subCommand[i] == '1')
  1338.       number += base;
  1339.  
  1340.   return number;
  1341. }
  1342.  
  1343. boolean DomoS::IsOn()
  1344. /*  Tell if the system is active
  1345.    
  1346.     Debugged: Don't need to be debugged
  1347.  */
  1348. {
  1349.   return _on;
  1350. }
  1351.  
  1352. void DomoS::Reset()
  1353. /*  Reset the system writing 0 to the first two cells of EEPROM
  1354. */
  1355. {
  1356.   EEPROM.write(0,0);
  1357.   EEPROM.write(1,0);  //Delete the cells
  1358.  
  1359.   Serial.println(PHRASE[8]); //Tell the user of reset the arduino
  1360.  
  1361.   return;
  1362. }
  1363.  
  1364. void DomoS::ComposeStringPeripheral(DomoSFileBody peripheral, byte phrase)
  1365. /*  Build a string for visualizing the peripheral as a string output
  1366.    
  1367.     peripheral is the peripheral to be shown
  1368.     phrase is the phrase contained into PHRASE to be used as a base for the building
  1369. */
  1370. {
  1371.   char output[82];
  1372.   char buff[9];
  1373.   byte i, j, k;
  1374.  
  1375.   i = 0;
  1376.   j = 0;
  1377.   k = 0;
  1378.   //Cycle until the string isn't finished
  1379.   while (PHRASE[phrase][i] != '\0')
  1380.   {
  1381.     switch (PHRASE[phrase][i]) //Check every character for finding keychar
  1382.     {
  1383.     case 'N'://If the character is an 'N' put the name
  1384.       k = 0;
  1385.       while(peripheral.name[k] != '\0')
  1386.       {
  1387.         output[j] = peripheral.name[k]; //Write the name
  1388.         j++;
  1389.         k++;
  1390.       }
  1391.       break;
  1392.  
  1393.     case 'M': //If the character is a 'M' put the number in decimal
  1394.       itoa(peripheral.number, buff, 10); //Convert the number into a string
  1395.       k = 0;
  1396.       while(buff[k] != '\0') //Write the number
  1397.       {
  1398.         output[j] = buff[k];
  1399.         j++;
  1400.         k++;
  1401.       }
  1402.       break;
  1403.  
  1404.     case 'B': //If the character is a 'B' put the number in binary
  1405.       itoa(peripheral.number, buff, 2); //Convert the number into a string
  1406.       k = 0;
  1407.       while(buff[k] != '\0') //Write the number
  1408.       {
  1409.         output[j] = buff[k];
  1410.         j++;
  1411.         k++;
  1412.       }
  1413.       break;
  1414.  
  1415.     default:
  1416.       output[j] = PHRASE[phrase][i];
  1417.       j++;
  1418.       break;
  1419.     }
  1420.  
  1421.     i++;
  1422.   }
  1423.   output[j] = '\0';
  1424.  
  1425.   Serial.println(output); //Print to the output
  1426.  
  1427.   return;
  1428. }
  1429.  
  1430. void DomoS::List()
  1431. /*  List all the installed peripheral
  1432. */
  1433. {
  1434.   byte i;
  1435.   DomoSFileBody peripheral;
  1436.  
  1437.   for(i = 0; i < _numPeripheral; i++) //For every peripheral...
  1438.   {
  1439.     GetPeripheralName(i, peripheral.name); //...take the name...
  1440.     GetPeripheralNumber(i, peripheral.number); //...and the number...
  1441.    
  1442.     ComposeStringPeripheral(peripheral, 10); //...then print to the output
  1443.   }
  1444.  
  1445.   if(i == 0) //If there are no peripheral thrown an error
  1446.     _lastError = THEREAREZEROPERIPHERAL;
  1447.  
  1448.   return;
  1449. }
  1450.  
  1451. void DomoS::Delete()
  1452. /*  Delete a peripheral given the name
  1453. */
  1454. {
  1455.   byte position;
  1456.   DomoSFileBody newPeripheral;
  1457.  
  1458.   SeparateCommandBySpace();
  1459.  
  1460.   position = SearchPeripheralByName(_subCommand); //Search the peripheral
  1461.   if (position != (byte)-1) //Check if the peripheral exists
  1462.   {
  1463.     if (position < (_numPeripheral - 1)) //Check if the peripheral isn't in the last EEPROM position
  1464.     {
  1465.       //If not, copy the last peripheral into the position of the deletted peripheral
  1466.       GetPeripheralName(_numPeripheral, newPeripheral.name);
  1467.       GetPeripheralNumber(_numPeripheral, newPeripheral.number);
  1468.      
  1469.       WritePeripheral(newPeripheral, position);
  1470.     }
  1471.     //If not, only decrease the number of peripherals
  1472.     UpdateNumPeripheral('-');
  1473.    
  1474.     Serial.println(PHRASE[11]);
  1475.   }
  1476.   else
  1477.     _lastError = PERIPHERALNOTFOUND;
  1478.  
  1479.   return;
  1480. }
Advertisement
Add Comment
Please, Sign In to add comment