matsstaff / stc1000p

Programmable thermostat firmware and arduino based uploader for the STC-1000 thermostat
GNU General Public License v3.0
261 stars 47 forks source link

second temperature probe inquiry #73

Closed seanmcveigh closed 8 years ago

seanmcveigh commented 8 years ago

Hi Mats, sorry if I'm being lazy and not checking out the code right now, but have you by any chance done any playing with nested control loops for 2 temperature probes (eg. for in-wort measurement while lagering but controlling refrigeration setpoint)? I was just about to get into designing my own "better" stc to do this (among other things), when I came across your project here.

matsstaff commented 8 years ago

Please don't open issues for general questions (this is not something that needs to be 'fixed' in stc-1000+). But to answer your question, the microcontroller in the STC-1000 is very constrained, so there is limited freedom in what is possible to implement. The purpose of the secondary probe, is simply to put a constraint on ambient temperature (not allowing it to wander beyond a set limit from the setpoint). This is to limit over/undershoots. Hope that answers your question. Cheers!

seanmcveigh commented 8 years ago

thanks.. (would have sent an email if I could figure out where to dig up that contact info from github :) perhaps I'll take a stab at this implementation... sounds like you're only a couple steps away from it. the idea is that the user can pick a setpoint to control to, and the outer loop adjusts the analog setpoint for ambient temperature to reach it, rather than driving a straight on/off, which as you know can lead to major overshoots. sounds like you're only a couple steps away from this actually :) cheers!

matsstaff commented 8 years ago

Well, feel free to fork the repo and play around. But, just know that already the MCU is nearly using all of the available code space. Aslo know, that doing floiting point math is simply not possibly. Whatever your control scheme is for the outer loop, it better be very simple if you're gonna make it fit (PID for example, even in fixed point, is just not feasible). Good luck!

seanmcveigh commented 8 years ago

Hey Mats, what's the best way to correspond? You weren't kidding about code space, but sdcc seems to output some pretty horrible code. Seems there's likely a lot of room for some hand optimization :) Cheers, Sean

matsstaff commented 8 years ago

Hi! I'd prefer for discussion to take place here: http://www.homebrewtalk.com/showthread.php?t=464348 This is the big STC-1000+ thread on homebrewtalk. You'd need to sign up, but it is free. That way there is just one thread (although a very big one) where most info is contained.

Yeah, the MCU is really tiny and I've tried to make as much use of it as I could :) I don't really know if it is all that horrid, but granted, I've not come in contact with PIC assembly, and after having a quick look, I'd rather keep it that way :) It seems like the architecture/instruction set is horrible. All that bank switching stuff is just... Yuck... So yeah, you might be able to trim some by hand optimizing, but then you'd lose C and your sanity :)

If you want to build your own custom FW, the easiest route would probably be to settle for a firmware to start from. Remove all the stuff that is 'if defined' for other versions (to make it more readable) and try to trim off functionality that you can do without, then add your own (or add your own and then try to trim down until it will fit again).

Cheers!

seanmcveigh commented 8 years ago

Thanks, I will consider signing up.
yah, something as simple as: LATA0 = ((ad_filter>>8) >= 248 || (ad_filter>>8) <= 8) is using up about 100 bytes, for example, and in the 2-probe variant, the same code appears again.. so 200 bytes, which could probably be reduced by using a function call instead, etc. I was reading a bit about sdcc, and, well, it's free, but this is the price you pay. Typically better compilers could use 1/2 to 1/3 as much space. Naturally, for a free project like this, it doesn't make sense to push anyone in that direction, but I think if I spend a couple days looking for some high profile chunks to optimize, you could easily reclaim a good chunk of space. Agreed, the instruction set is a bit limited, but the compiler is even more so :)

wow.. even "led_e.e_cool = !LATA4" is using like 46 bytes or so! it's implemented as a comparison and then a conditional branch to set or clear a bit. lots of extra garbage code in there :P

seanmcveigh commented 8 years ago

joined up. seems I am currently moderated.

going to work on seeing how sdcc's output can be optimized a bit tonight. my first pass is just going to be some C re-jigging. could look at some hand-coded assembler later maybe. would you be ok with me posting some tickets to the issue tracker for optimizations? I'm keeping a list in a text file right now as things come to mind :)

Hey, I noticed you're from Sweden.. cool.. I know some guys from Malmo and Gothenburg from TAT/BlackBerry. I super enjoyed visiting last year!

seanmcveigh commented 8 years ago

hey.. so I think this will be quite optimizable just sticking to C. this compiler is horrible with large compound statements, and isn't super smart about variable re-use, etc.

for example.. looking at the code here: LATA0 = ((ad_filter>>8) >= 248 || (ad_filter>>8) <= 8) || (eeprom_read_config(EEADR_MENU_ITEM(Pb)) && ((ad_filter2>>8) >= 248 || (ad_filter2>>8) <= 8))

By turning this into 4 if()s instead of one big one, it saved 30 instructions (60 bytes of 8k). By caching ad_filter>>8 in an unsigned char first, saves an additional 12 instructions. By moving this common range check check to the read_ad() function, it saved 13 more.

That one if() refactor save a total of 55 instructions, or 110 bytes of the 8k program space! The cost there was 2 bits of ram to cache the state from read_ad() and to decide whether probe2 is enabled.

I suspect changing the large nested if()s in temperature_control() would gain back a similar large number of bytes.

I'll happily tackle some of these over a few days and can push some incremental patches upstream for you to mull over. Let me know if you are interested in incorporating or not.. I can just work on my own otherwise and not worry about being tidy :)

matsstaff commented 8 years ago

Hi! You are more than welcome to open issues if you find stuff that could be improved! You are even more welcome to send pull requests, if you fix/improve stuff. If you make improvements in C code, that yield smaller code space usage (and still is correct of course), then I can pretty much guarantee I'll incorporate the changes. Please send small changes (i.e. don't lump all changes into one pull request), that way I can choose to not include something right away if I'm iffy about it. As you're a professional developer yourself, I don't really think I need to explain :) I'd be open to 'functional' changes as well, but might feel the need to discuss changes first then. I'm very glad there is a fresh set of (experienced in embedded development) eyes on the code :)

PM me on HBT, and we can exchange mail addresses, if you want to discuss stuff more privately.

Cheers and welcome!!!!