Central Heating controller using the real time clock, PHY module for internet, 1-wire interface for temperature sensors, a system log and a configuration file
Dependencies: net 1-wire lpc1768 crypto clock web fram log
/media/uploads/andrewboyson/heating.sch
/media/uploads/andrewboyson/heating.brd
/media/uploads/andrewboyson/eagle.epf
heating/boiler.c@1:ccc66fdf858d, 2018-01-28 (annotated)
- Committer:
- andrewboyson
- Date:
- Sun Jan 28 14:41:12 2018 +0000
- Revision:
- 1:ccc66fdf858d
- Parent:
- 0:3c04f4b47041
- Child:
- 5:82197a6997fd
Updated libraries
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
andrewboyson | 0:3c04f4b47041 | 1 | #include <string.h> |
andrewboyson | 0:3c04f4b47041 | 2 | #include <stdint.h> |
andrewboyson | 0:3c04f4b47041 | 3 | #include <stdbool.h> |
andrewboyson | 0:3c04f4b47041 | 4 | |
andrewboyson | 1:ccc66fdf858d | 5 | #include "defs.h" |
andrewboyson | 1:ccc66fdf858d | 6 | #include "tick.h" |
andrewboyson | 1:ccc66fdf858d | 7 | #include "ds18b20.h" |
andrewboyson | 1:ccc66fdf858d | 8 | #include "fram.h" |
andrewboyson | 0:3c04f4b47041 | 9 | |
andrewboyson | 0:3c04f4b47041 | 10 | #define BOILER_PUMP_MASK 1UL << 4 // P2.4 == p22 |
andrewboyson | 0:3c04f4b47041 | 11 | #define BOILER_CALL_MASK 1UL << 5 // P2.5 == p21 |
andrewboyson | 0:3c04f4b47041 | 12 | |
andrewboyson | 0:3c04f4b47041 | 13 | static char tankRom[8]; static int iTankRom; |
andrewboyson | 0:3c04f4b47041 | 14 | static char outputRom[8]; static int iOutputRom; |
andrewboyson | 0:3c04f4b47041 | 15 | static char returnRom[8]; static int iReturnRom; |
andrewboyson | 0:3c04f4b47041 | 16 | |
andrewboyson | 0:3c04f4b47041 | 17 | |
andrewboyson | 0:3c04f4b47041 | 18 | static int32_t tankSetPoint; static int iTankSetPoint; |
andrewboyson | 0:3c04f4b47041 | 19 | static int32_t tankHysteresis; static int iTankHysteresis; |
andrewboyson | 0:3c04f4b47041 | 20 | static int32_t runOnResidual; static int iRunOnResidual; |
andrewboyson | 0:3c04f4b47041 | 21 | static int32_t runOnTime; static int iRunOnTime; |
andrewboyson | 0:3c04f4b47041 | 22 | |
andrewboyson | 0:3c04f4b47041 | 23 | char* BoilerGetTankRom () { return tankRom; } |
andrewboyson | 0:3c04f4b47041 | 24 | char* BoilerGetOutputRom () { return outputRom; } |
andrewboyson | 0:3c04f4b47041 | 25 | char* BoilerGetReturnRom () { return returnRom; } |
andrewboyson | 0:3c04f4b47041 | 26 | int BoilerGetTankSetPoint () { return (int) tankSetPoint; } |
andrewboyson | 0:3c04f4b47041 | 27 | int BoilerGetTankHysteresis() { return (int) tankHysteresis; } |
andrewboyson | 0:3c04f4b47041 | 28 | int BoilerGetRunOnResidual () { return (int) runOnResidual; } |
andrewboyson | 0:3c04f4b47041 | 29 | int BoilerGetRunOnTime () { return (int) runOnTime; } |
andrewboyson | 0:3c04f4b47041 | 30 | |
andrewboyson | 0:3c04f4b47041 | 31 | void BoilerSetTankRom (char* value) { memcpy(tankRom, value, 8); FramWrite(iTankRom, 8, tankRom ); } |
andrewboyson | 0:3c04f4b47041 | 32 | void BoilerSetOutputRom (char* value) { memcpy(outputRom, value, 8); FramWrite(iOutputRom, 8, outputRom ); } |
andrewboyson | 0:3c04f4b47041 | 33 | void BoilerSetReturnRom (char* value) { memcpy(returnRom, value, 8); FramWrite(iReturnRom, 8, returnRom ); } |
andrewboyson | 0:3c04f4b47041 | 34 | void BoilerSetTankSetPoint (int value) { tankSetPoint = (int32_t)value; FramWrite(iTankSetPoint, 4, &tankSetPoint ); } |
andrewboyson | 0:3c04f4b47041 | 35 | void BoilerSetTankHysteresis (int value) { tankHysteresis = (int32_t)value; FramWrite(iTankHysteresis, 4, &tankHysteresis ); } |
andrewboyson | 0:3c04f4b47041 | 36 | void BoilerSetRunOnResidual (int value) { runOnResidual = (int32_t)value; FramWrite(iRunOnResidual, 4, &runOnResidual ); } |
andrewboyson | 0:3c04f4b47041 | 37 | void BoilerSetRunOnTime (int value) { runOnTime = (int32_t)value; FramWrite(iRunOnTime, 4, &runOnTime ); } |
andrewboyson | 0:3c04f4b47041 | 38 | |
andrewboyson | 0:3c04f4b47041 | 39 | |
andrewboyson | 0:3c04f4b47041 | 40 | int BoilerInit() |
andrewboyson | 0:3c04f4b47041 | 41 | { |
andrewboyson | 0:3c04f4b47041 | 42 | int address; |
andrewboyson | 0:3c04f4b47041 | 43 | int32_t def4; |
andrewboyson | 0:3c04f4b47041 | 44 | address = FramLoad( 8, tankRom, 0); if (address < 0) return -1; iTankRom = address; |
andrewboyson | 0:3c04f4b47041 | 45 | address = FramLoad( 8, outputRom, 0); if (address < 0) return -1; iOutputRom = address; |
andrewboyson | 0:3c04f4b47041 | 46 | address = FramLoad( 8, returnRom, 0); if (address < 0) return -1; iReturnRom = address; |
andrewboyson | 0:3c04f4b47041 | 47 | def4 = 80; address = FramLoad( 4, &tankSetPoint, &def4); if (address < 0) return -1; iTankSetPoint = address; |
andrewboyson | 0:3c04f4b47041 | 48 | def4 = 5; address = FramLoad( 4, &tankHysteresis, &def4); if (address < 0) return -1; iTankHysteresis = address; |
andrewboyson | 0:3c04f4b47041 | 49 | def4 = 2; address = FramLoad( 4, &runOnResidual, &def4); if (address < 0) return -1; iRunOnResidual = address; |
andrewboyson | 0:3c04f4b47041 | 50 | def4 = 360; address = FramLoad( 4, &runOnTime, &def4); if (address < 0) return -1; iRunOnTime = address; |
andrewboyson | 0:3c04f4b47041 | 51 | |
andrewboyson | 0:3c04f4b47041 | 52 | LPC_GPIO2->FIODIR |= BOILER_PUMP_MASK; //Set the direction to 1 == output |
andrewboyson | 0:3c04f4b47041 | 53 | LPC_GPIO2->FIODIR |= BOILER_CALL_MASK; //Set the direction to 1 == output |
andrewboyson | 0:3c04f4b47041 | 54 | |
andrewboyson | 0:3c04f4b47041 | 55 | return 0; |
andrewboyson | 0:3c04f4b47041 | 56 | } |
andrewboyson | 0:3c04f4b47041 | 57 | bool BoilerPump = false; |
andrewboyson | 0:3c04f4b47041 | 58 | bool BoilerCall = false; |
andrewboyson | 0:3c04f4b47041 | 59 | |
andrewboyson | 0:3c04f4b47041 | 60 | void BoilerMain() |
andrewboyson | 0:3c04f4b47041 | 61 | { |
andrewboyson | 0:3c04f4b47041 | 62 | //Control boiler call |
andrewboyson | 0:3c04f4b47041 | 63 | int tankTemp16ths = DS18B20ValueFromRom(tankRom); |
andrewboyson | 0:3c04f4b47041 | 64 | if (DS18B20IsValidValue(tankTemp16ths)) //Ignore values which are likely to be wrong |
andrewboyson | 0:3c04f4b47041 | 65 | { |
andrewboyson | 0:3c04f4b47041 | 66 | int tankUpper16ths = tankSetPoint << 4; |
andrewboyson | 0:3c04f4b47041 | 67 | int hysteresis16ths = tankHysteresis << 4; |
andrewboyson | 0:3c04f4b47041 | 68 | int tankLower16ths = tankUpper16ths - hysteresis16ths; |
andrewboyson | 0:3c04f4b47041 | 69 | |
andrewboyson | 0:3c04f4b47041 | 70 | if (tankTemp16ths >= tankUpper16ths) BoilerCall = false; |
andrewboyson | 0:3c04f4b47041 | 71 | if (tankTemp16ths <= tankLower16ths) BoilerCall = true; |
andrewboyson | 0:3c04f4b47041 | 72 | } |
andrewboyson | 0:3c04f4b47041 | 73 | if (BoilerCall) LPC_GPIO2->FIOSET = BOILER_CALL_MASK; |
andrewboyson | 0:3c04f4b47041 | 74 | else LPC_GPIO2->FIOCLR = BOILER_CALL_MASK; |
andrewboyson | 0:3c04f4b47041 | 75 | |
andrewboyson | 0:3c04f4b47041 | 76 | //Control boiler circulation pump |
andrewboyson | 0:3c04f4b47041 | 77 | int boilerOutput16ths = DS18B20ValueFromRom(outputRom); |
andrewboyson | 0:3c04f4b47041 | 78 | int boilerReturn16ths = DS18B20ValueFromRom(returnRom); |
andrewboyson | 0:3c04f4b47041 | 79 | int boilerResidual16ths = boilerOutput16ths - boilerReturn16ths; |
andrewboyson | 0:3c04f4b47041 | 80 | int boilerTempsAreValid = DS18B20IsValidValue(boilerOutput16ths) && DS18B20IsValidValue(boilerReturn16ths); |
andrewboyson | 0:3c04f4b47041 | 81 | |
andrewboyson | 1:ccc66fdf858d | 82 | static int64_t offTicks; |
andrewboyson | 0:3c04f4b47041 | 83 | if (BoilerCall) |
andrewboyson | 0:3c04f4b47041 | 84 | { |
andrewboyson | 0:3c04f4b47041 | 85 | BoilerPump = true; |
andrewboyson | 1:ccc66fdf858d | 86 | offTicks = Ticks(); |
andrewboyson | 0:3c04f4b47041 | 87 | } |
andrewboyson | 0:3c04f4b47041 | 88 | else |
andrewboyson | 0:3c04f4b47041 | 89 | { |
andrewboyson | 1:ccc66fdf858d | 90 | int secondsSinceBoilerOff = (Ticks() - offTicks) >> TICK_ONE_SECOND_SHIFT; |
andrewboyson | 0:3c04f4b47041 | 91 | if (secondsSinceBoilerOff > runOnTime) BoilerPump = false; |
andrewboyson | 0:3c04f4b47041 | 92 | if (boilerTempsAreValid) |
andrewboyson | 0:3c04f4b47041 | 93 | { |
andrewboyson | 0:3c04f4b47041 | 94 | int boilerStillSupplyingHeat = boilerResidual16ths > runOnResidual; |
andrewboyson | 0:3c04f4b47041 | 95 | if (!boilerStillSupplyingHeat) BoilerPump = false; |
andrewboyson | 0:3c04f4b47041 | 96 | } |
andrewboyson | 0:3c04f4b47041 | 97 | } |
andrewboyson | 0:3c04f4b47041 | 98 | |
andrewboyson | 0:3c04f4b47041 | 99 | if (BoilerPump) LPC_GPIO2->FIOSET = BOILER_PUMP_MASK; |
andrewboyson | 0:3c04f4b47041 | 100 | else LPC_GPIO2->FIOCLR = BOILER_PUMP_MASK; |
andrewboyson | 0:3c04f4b47041 | 101 | |
andrewboyson | 0:3c04f4b47041 | 102 | } |