void main(void){ M8C_EnableGInt; M8C_EnableIntMask(INT_MSK0, INT_MSK0_GPIO); I2CHW_Start(); I2CHW_EnableSlave(); I2CHW_EnableInt(); AMUX4_Start(); PGA_1_Start(PGA_1_HIGHPOWER); ADCINC_Start(ADCINC_HIGHPOWER); TX8_Start(TX8_PARITY_NONE); LED_DBG_ON(); TX8_CPutString("I2C slave addr:0x"); TX8_PutSHexByte(I2CHW_SLAVE_ADDR); TX8_PutCRLF(); LED_DBG_OFF(); for(;;){ // I2C i2c_status = I2CHW_bReadI2CStatus(); if(i2c_status & I2CHW_WR_COMPLETE){ // master->slave I2CHW_ClrWrStatus(); I2CHW_InitWrite(buf_rx, BUF_SIZE); } if(i2c_status & I2CHW_RD_COMPLETE){ // slave->master I2CHW_ClrRdStatus(); I2CHW_InitRamRead(buf_tx, BUF_SIZE); } // ADC for(ad_pin = 0; ad_pin < 4; ad_pin++){ ad = get_adc(ad_pin); weights[ad_pin] = ad; TX8_PutChar(ad_pin+'0'); TX8_CPutString(":"); TX8_PutString(intToStr(ad,buf)); TX8_PutCRLF(); } buf_tx[0] = 'a'; buf_tx[1] = 'b'; buf_tx[2] = 'c'; buf_tx[3] = 'd'; } }
void main(void) { M8C_EnableGInt ; // Uncomment this line to enable Global Interrupts // Start the UART(with no parity), and Counter16 UART_Start(UART_PARITY_NONE); // clock for moving serial Counter16_Start(); // Start I2CHW I2CHW_Start(); I2CHW_EnableMstr(); I2CHW_EnableInt(); // This is the command usage string UART_CPutString("########################## I2C External SRAM ########################\r\n\ # W # XX T [Data]\r\n\ # W - Write command\r\n\ # # - Group Address (0 - 7)\r\n\ # XX - Memory Location in hex (00 - FF)\r\n\ # T - Data Type, either A for ASCII or H for Hexadecimal\r\n\ # Data - Either ASCII string or Hexadecimal separates by spaces\r\n\ #\t\t\tA - Mary had a little lamb\r\n\ #\t\t\tH - 01 FF A0 0F D8 C3\r\n\ #\r\n\ # R # XX T NN\r\n\ # R - Read command\r\n\ # # - Group Address (0 - 7)\r\n\ # XX - Memory Location in hex (00 - FF)\r\n\ # T - Data Type, either A for ASCII or H for Hexadecimal\r\n\ # NN - Number of bytes to read in hexadecimal\r\n\ #####################################################################\r\n"); while (1) { char *cmd; char *params; char slaveAddress = 0x50; // 010100000 R/W shifted to front GetLine(buf, 79); // Retrieves a line with a maximum length of 70 characters and put it in buf. memset(data, 0x00, 256); // Initialize all the set {data} to NULL bytes cmd = Lowercase(cstrtok(buf, " ")); // Get the first word from the entered string and lowercase it. if (strlen(cmd) == 1 && cmd[0] == 'w') // If the command is one letter and it is w, then write command { int groupAddress; // only 1 and 2 actually go to SRAM int memLoc; char dataType; int len; params = cstrtok(0x00, " "); // 0x00 indicates it will continue from last cstrtok command and get next word. This gets the next parameter // csscanf if used to parse the string into values such as hexadecimal or integers // It returns the number of parameters it parsed which should be one // If the length of the params is not right or it does not parse the right amount, it returns an error // %d gets an integer, this is the groupAddress if (strlen(params) != 1 || csscanf(params, "%d", &groupAddress) != 1) goto error; // %x gets a hexadecimal value, this can read capital or lowercase letters, this is the memory location params = cstrtok(0x00, " "); if (strlen(params) != 2 || csscanf(params, "%x", &memLoc) != 1) goto error; // %c gets a character, the data type character params = cstrtok(0x00, " "); if (strlen(params) != 1 || csscanf(params, "%c", &dataType) != 1) goto error; // This reads the rest of the string and stores it in params. // If the length is zero or if cstrtok returns 0, this means that there was no valid string/hex entered params = cstrtok(0x00, "\0"); if (strlen(params) == 0 || params == 0x00) goto error; // They did all the params but didn't write anything dataType = tolower(dataType); // Lowercase the data type if (groupAddress < 0 || groupAddress > 7) goto error; // groupAddress was not in range data[0] = memLoc; // First byte needs to be the memory location according to PCF8570 datasheet slaveAddress |= groupAddress; // ORs the group 2 address to the group 1 address to get slaveAddress if (dataType == 'a') // If the data type is ASCII { strcpy((data + 1), params); // Copy the string from params and put it right after the data[0] byte len = strlen((data + 1)) + 1; // len is the number of bytes to write, it is the length of the string and then +1 because of the memLoc byte // Cant just do strlen(data) because data[0] could be 0x00 and it would return 0 as the string length } else if (dataType == 'h') // If the data type is hex { // Take ASCII encoded hex data params and put it after data[0], returns number of bytes converted if ((len = HexConversion(params, (data + 1))) == -1) goto error; len++; // Add one to the length because of the memLoc byte at data[0] } else goto error; I2CHW_bWriteBytes(slaveAddress, data, len, I2CHW_CompleteXfer); // Write len bytes from data while (!(I2CHW_bReadI2CStatus() & I2CHW_WR_COMPLETE)); // Wait while it is writing I2CHW_ClrWrStatus(); // Clear the write bit csprintf(data, "%x bytes were written", len); // csprintf takes the string and substitutes %x for len, puts into data str UART_PutString(data); // Print the string to UART UART_PutCRLF(); } else if (strlen(cmd) == 1 && cmd[0] == 'r') // If the command is one letter and it is r, then read command { int groupAddress; int memLoc; char dataType; int numBytes; char hexStr[4]; int i; // csscanf if used to parse the string into values such as hexadecimal or integers // It returns the number of parameters it parsed which should be one // If the length of the params is not right or it does not parse the right amount, it returns an error // %d gets an integer, this is the groupAddress params = cstrtok(0x00, " "); if (strlen(params) != 1 || csscanf(params, "%d", &groupAddress) != 1) goto error; // %x gets a hexadecimal value, this can read capital or lowercase letters, this is the memory location params = cstrtok(0x00, " "); if (strlen(params) != 2 || csscanf(params, "%x", &memLoc) != 1) goto error; // %c gets a character, the data type character params = cstrtok(0x00, " "); if (strlen(params) != 1 || csscanf(params, "%c", &dataType) != 1) goto error; // %x gets a hexadecimal value, number of bytes to read params = cstrtok(0x00, " "); if (strlen(params) != 2 || csscanf(params, "%x", &numBytes) != 1) goto error; // If there is any data after the number of bytes, then the format is invalid and it should return an error if (cstrtok(0x00, " ") != 0x00) goto error; dataType = tolower(dataType); // Lowercase the data type if (groupAddress < 0 || groupAddress > 7) goto error; // groupAddress was not in range data[0] = memLoc; // First byte needs to be the memory location according to PCF8570 datasheet slaveAddress |= groupAddress; // ORs the group 2 address to the group 1 address to get slaveAddress I2CHW_bWriteBytes(slaveAddress, data, 1, I2CHW_NoStop); // Write one byte to the RAM, the slaveAddress so it knows who were talking to while (!(I2CHW_bReadI2CStatus() & I2CHW_WR_COMPLETE)); // Wait while it is writing I2CHW_ClrWrStatus(); // Clear the write bit I2CHW_fReadBytes(slaveAddress, data, numBytes, I2CHW_CompleteXfer); // Read numBytes from the RAM, put it in data while(!(I2CHW_bReadI2CStatus() & I2CHW_RD_COMPLETE)); // Wait while it is reading I2CHW_ClrRdStatus(); // Clear the read bit if (dataType == 'a') // If the data type is ASCII { for (i = 0; i < numBytes; ++i) // Loop through each byte UART_PutChar(data[i]); // Put the character in PuTTy UART_PutCRLF(); } else if (dataType == 'h') // If the data type is Hex { for (i = 0; i < numBytes; ++i) // Loop through each byte { csprintf(hexStr, "%X ", data[i]); // csprintf prints into hexStr a hexadecimal with a space UART_PutString(hexStr); // Print hexStr } UART_PutCRLF(); } else goto error; } else goto error; continue; // This is so that the error is skipped when everything goes right error: // This outputs an invalid format message and continues on to read another line UART_CPutString("Invalid format entered. Valid formats are:\r\n\tW [GroupAddress] [MemoryLocation] [h|a] Hex/ASCII\r\n\tR [GroupAddress] [MemoryLocation] [h|a] [NumBytes]\r\n"); } }
void main(void) { M8C_EnableGInt ; // Uncomment this line to enable Global Interrupts M8C_EnableIntMask(INT_MSK1, INT_MSK1_DBB01); // Enable DBB01 Interrupt for TempCounter M8C_EnableIntMask(INT_MSK1, INT_MSK1_DBB11); // Enable DBB01 Interrupt for MotorDriver M8C_EnableIntMask(INT_MSK0, INT_MSK0_GPIO); // Enable GPIO interrupt for Tout // Start the UART(with no parity), LCD, TempCounter and MotorDriver UART_Start(UART_PARITY_NONE); LCD_Start(); TempCounter_EnableInt(); // Enable interrupts for counter TempCounter_Start(); MotorDriver_EnableInt(); // Enable interrupts for counter // Start I2CHW I2CHW_Start(); I2CHW_EnableMstr(); I2CHW_EnableInt(); WriteI2C(slaveAddress, 0xAC, 1, 0x02); // Write to access config, sets mode to cooling(POL = 1), also turns 1-SHOT off, continuous conversions WriteI2C(slaveAddress, 0xA1, 2, (setTemp + tolerance), 0x00); // Sets initial high temp to be setTemp + tolerance WriteI2C(slaveAddress, 0xA2, 2, (setTemp - tolerance), 0x00); // Sets initial low temp to be setTemp - tolerance WriteI2C(slaveAddress, 0xEE, 0); // This tells the temperature IC to start converting the temperatures // Writes initial string to LCD. When LCD is updated, only the numbers will be changed LCD_Position(0,0); LCD_PrCString("CUR: 00 OFF "); LCD_Position(1,0); LCD_PrCString("SET: 00 FAN OFF "); // This is the command usage string UART_CPutString("#################### Heating/Cooling Stepper Motors ##################\r\n\ # S ##\r\n\ # S - Set the desired Temperature\r\n\ # ## - Desired temperature in celsius\r\n\ #\r\n\ # T ##\r\n\ # T - Set the desired tolerance\r\n\ # ## - Desired tolerance in celsius\r\n\ #\r\n\ # M X\r\n\ # M - Change the mode of the thermostat\r\n\ # X - C is for cool, H is for heat, F is for off\r\n\ #\r\n\ # F X S\r\n\ # F - Change the mode of the fan\r\n\ # X - A is for automatic fan control, M is for always on\r\n\ # S - Speed of the fan, H = high, M = medium, L = low\r\n\ #####################################################################\r\n"); while (1) { char *cmd; char *params; if (GetLine(buf, &strPos, 79)) // Only process the data if GetLine returns true { cmd = Lowercase(cstrtok(buf, " ")); // Lowercase the first word from the inputted string if (strlen(cmd) == 1 && cmd[0] == 's') // If the person entered s { int temp; params = cstrtok(0x00, " "); // Read next word // If next word isnt number or isnt 1 or 2 characters long, then return error if (!IsNumber(params) || strlen(params) < 1 || strlen(params) > 2 || csscanf(params, "%d", &temp) != 1) goto error; // If there is additional data at end of string or if number is not within 0-99, return error if (cstrtok(0x00, " ") != 0x00) goto error; if ( temp > 99 || temp < 0) goto error; setTemp = temp; WriteI2C(slaveAddress, 0xA1, 2, (setTemp + tolerance), 0x00); // Sets high temp to be setTemp + tolerance WriteI2C(slaveAddress, 0xA2, 2, (setTemp - tolerance), 0x00); // Sets low temp to be setTemp - tolerance updateLCD = TRUE; // Update the LCD } else if (strlen(cmd) == 1 && cmd[0] == 't') // If the person entered t { int tol; params = cstrtok(0x00, " "); // Read next word // If next word isnt number or isnt 1 or 2 characters long, then return error if (!IsNumber(params) || strlen(params) < 1 || strlen(params) > 2 || csscanf(params, "%d", &tol) != 1) goto error; // If there is additional data at end of string or if number is not within 0-10, return error if (cstrtok(0x00, " ") != 0x00) goto error; if (tol < 0 || tol > 10) goto error; tolerance = tol; WriteI2C(slaveAddress, 0xA1, 2, (setTemp + tolerance), 0x00); // Sets high temp to be setTemp + tolerance WriteI2C(slaveAddress, 0xA2, 2, (setTemp - tolerance), 0x00); // Sets low temp to be setTemp - tolerance updateLCD = TRUE; // Update the LCD } else if (strlen(cmd) == 1 && cmd[0] == 'm') // If the person entered m { char mode; params = cstrtok(0x00, " "); // Read next word // If next word isnt 1 character long, return error if (strlen(params) != 1 || csscanf(params, "%c", &mode) != 1) goto error; // If there is additional data at end of string, return error if (cstrtok(0x00, " ") != 0x00) goto error; mode = tolower(mode); // Lowercase the character switch (mode) { case 'h': thermostatMode = 1; // Set mode to heating WriteI2C(slaveAddress,0xAC, 1, 0x00); // Change access config on DS1621 to heating(POL = 0) break; case 'c': thermostatMode = 2; // Set mode to cooling WriteI2C(slaveAddress, 0xAC, 1, 0x02); // Change access config on DS1621 to cooling(POL = 1) break; case 'f': thermostatMode = 0; // Set mode to off break; default: goto error; // Invalid character entered, goto error } CheckFan(); // Check the fan to see if it should be on } else if (strlen(cmd) == 1 && cmd[0] == 'f') // If the person entered f { char mode; char speed; params = cstrtok(0x00, " "); // Read next word // If next word isnt 1 character long, then return error if (strlen(params) != 1 || csscanf(params, "%c", &mode) != 1) goto error; params = cstrtok(0x00, " "); // Read next word // If next word isnt 1 character long, then return error if (strlen(params) != 1 || csscanf(params, "%c", &speed) != 1) goto error; // If there is additional data at end of string, return error if (cstrtok(0x00, " ") != 0x00) goto error; speed = tolower(speed); // Lowercase the speed and mode characters entered mode = tolower(mode); switch (mode) { case 'm': fanMode = 0; // Set fan mode to manual break; case 'a': fanMode = 1; // Set fan mode to automatic break; default: // Otherwise go to error goto error; } MotorDriver_Stop(); // Stop the motor to change the period values switch (speed) { case 'l': fanSpeed = 0; // Set fan speed to low MotorDriver_WritePeriod(49999); // See report for where these numbers came from MotorDriver_WriteCompareValue(25000); break; case 'm': fanSpeed = 1; // Set fan speed to medium MotorDriver_WritePeriod(9999); // See report for where these numbers came from MotorDriver_WriteCompareValue(5000); break; case 'h': fanSpeed = 2; // Set fan speed to high MotorDriver_WritePeriod(1999); // See report for where these numbers came from MotorDriver_WriteCompareValue(1000); break; default: // Otherwise go to error if invalid input entered goto error; } CheckFan(); // Check the fan to see if it should be on } else goto error; } if (checkTemp) // Check the temperature { char buf[2]; ReadI2C(slaveAddress, 0xAA, 2, buf); // Read the temperature from IC, returns 2 bytes curTemp = buf[0]; // We just care about the first byte checkTemp = FALSE; // Turn flag off so it doesnt keep doing this } if (updateLCD) // Update the LCD { char buf[3]; NumToStr(buf, curTemp, 2); // Convert current temp to str LCD_Position(0, 5); LCD_PrString(buf); // Print it LCD_Position(0, 8); switch(thermostatMode) // Print thermostat mode { case 0: LCD_PrCString("OFF "); break; case 1: LCD_PrCString("HEAT"); break; case 2: LCD_PrCString("COOL"); break; } NumToStr(buf, setTemp, 2); // Convert set temp to str LCD_Position(1, 5); LCD_PrString(buf); // Print it LCD_Position(1, 12); if (fanMode == 1 && thermostatMode == 0) LCD_PrCString("OFF"); // Print current fan state else if (fanSpeed == 0) LCD_PrCString("LOW"); else if (fanSpeed == 1) LCD_PrCString("MED"); else if (fanSpeed == 2) LCD_PrCString("HI "); updateLCD = FALSE; } continue; error: UART_CPutString("# Invalid format entered. Valid formats are:\r\n\ # S ##\r\n\ # S - Set the desired Temperature\r\n\ # ## - Desired temperature in celsius\r\n\ #\r\n\ # T ##\r\n\ # T - Set the desired tolerance\r\n\ # ## - Desired tolerance in celsius\r\n\ #\r\n\ # M X\r\n\ # M - Change the mode of the thermostat\r\n\ # X - C is for cool, H is for heat, F is for off\r\n\ #\r\n\ # F X S\r\n\ # F - Change the mode of the fan\r\n\ # X - A is for automatic fan control, M is for always on\r\n\ # S - Speed of the fan, H = high, M = medium, L = low\r\n\ #####################################################################\r\n"); } }