Datalogging interrupts

rmeldo

Senior Member
Hi there,

I am doing a project to log the gas consumption in my house using a hall effect sensor switch and an AXE110 datalogger.

I have sorted out the hardware side, with some help and I now have turned to the software.

The idea is, rather than logging the status of the hall switch at regular intervals, to log the time at which a pulse comes around (the gas meter wheel has a magnet on it). To do this I plan to use interrupts on one of the input pins of the Picaxe 18X.

I have searched for examples on the various forums but I haven't found examples of this approach. Maybe this project will be useful to others, once I get it done.

Anyway...

I am quite rusty (not that I was ever proficient) on the coding side. I have written the code attached and started debugging it with the Picaxe simulator, but the debugger gets gets stuck at line 86: "hi2cout address, (w2,w3,w4)"

View attachment RM_program_v2.bas

Could someone take a look at it for me? Hopefully it is something very simple to fix.

The specifics of the hardware are:

1) AXE110 datalogger, with 18X chip, RTC1307 and 24LC256/P I2C EEPROM

Many Thanks
Riccardo
 

hippy

Technical Support
Staff member
Not sure what the problem may be there, and other test code which does similar seems to be working, so we will have to investigate that issue further.
 

Technical

Technical Support
Staff member
You can only write bytes on the i2c bus, so using a word variable may overflow.

"hi2cout address, (w2,w3,w4)"

So use this instead, low byte of each word used (ie b4 is low byte of w2):

"hi2cout address, (b4,b6,b8)"

We have modified the simulation so that it now behaves like a real chip (ANDs the word variable value with 255, so effectively only giving you the value of the least significant byte in the word)
 
Last edited:

rmeldo

Senior Member
Can I use "hi2cout address, (b4,b5,b6,b7,b8)" then?

It was my intention all along to write 6 variables.

Many Thanks
Riccardo
 

Technical

Technical Support
Staff member
Yes, this is exactly what you should do in this situation. Remember address will increase by 6 each time.
 

rmeldo

Senior Member
Code attached

Hi,

I thought I would share the code so far, as I wasn't able to find anything similar on the forum (probably I didn't look hard enough).

View attachment RM_program_v2.bas

I tested it last night and it seems to work. The only thing I am still working on is the ability to download the data BEFORE the memory is full. I am trying to sense a high value for the input 2 pin of the AXE110 but I am getting spurious results. Hopefully I haven't burnt the chip.

Comments welcome
Riccardo
 

rmeldo

Senior Member
Software or hardware problem?

Hi,

I have a problem with the datalogger and I cannot decide whether it is hardware or software.

I have modified the code above to include a check of pin7 being high (the input from connector C5 in the AXE110, the one which is used for the temperature sensor) to stop logging and go straight to the downloading subroutine. The new code is attached below.

View attachment RM_program_v3.bas

I have checked the code with the simulator and it works, but when I try it on the AXE110 (with a 18X chip on it) itself the check of pin7 seems to be ignored.

I have wired up the input pin as follows:

1) I have a 400 kohm resistor between the pin and ground
2) I pull the input high by using a pushbutton in series with a 4k7 resistor to connect it to V+

Could someone please take a look at the code to see what I have done wrong or tell me if my wiring is incorrect?

Many Thanks
Riccardo
 

westaust55

Moderator
There is by default a 4k7 pull up resistor on the input associate with connector CT5. This is the require data line pull up resistor for the DS18B20 temp sensor.

When you add a400k pull-down resistor, if the 4k7 resistor is still present the PICAXE input will always appear high due to the potential divider voltage between to the two resistors.

Why not remove your 400k resistor and use the switch between the PICAXE input and ground instead.
 

rmeldo

Senior Member
Thanks westaus55,

it makes sense.

I have tried however and it doesn't work. Using pin7 was my attempt to change something, having tried pin2 before.

When wiring pin2 I used the pull down resistor as well, but initially I didn't use a 4k7 resistor in series with the switch to Vdd. I wonder whether I burnt the PIC and what I am seeing are the consequences.....

Is the code above correct? Is there an interaction with the interrupt mask which I am not considering?

Many Thanks
Riccardo
 

rmeldo

Senior Member
I need some help please.

I would like to the value of input 2 of the AXE110 datalogger to jump to the subroutine which tranmit the logs to the PC BEFORE I have reached the maximum number of logs the EEPROM can store.
.
the problem is that pin2 doesn't seem to be recognised. Code attached below:

View attachment RM_program_v4.bas

I did some investigations:

1) I replaced the Picaxe 18X with a brand new 18M2 => no change
2) I replaced the EEprom => no change
3) I replaced the DS1307 => no change
4) I tried to use the readadc command in place of checking the logical value of pin2, as done at line 63 of the attached code => no change

5) The only success I had was to remove (comment) the interrupt setup (line 60 of the code). If I od this then the pin2 logic level gets recognised.

The problem seems to be that the hintsetup command deactivates checks on other pins. So I am left in the situation that I can either trigger a log based on the interrupt OR call the subroutine to communicate with the PC BEFORE I have reached the maximum number of logs.

Is this really the case? It seems very strange that the interrupt prevents the sensing of any other input pin.

Is there a workaround?

Many Thanks
Riccardo
 

hippy

Technical Support
Staff member
5) The only success I had was to remove (comment) the interrupt setup (line 60 of the code). If I od this then the pin2 logic level gets recognised.
Is this when simulating or running on a physical chip ?

Your command "setint %11111111,%00000010" appears to be flawed, should be functioning as if -

Whenever ( pinsC & %00000010 ) = %11111111 Call Interrput

That condition should never be met so interrupt should never be called. It also should not be preventing pinC.2 from being read separately. We may need to investigate what is happening if it is not behaving as expected.
 

rmeldo

Senior Member
Thanks hippy.

I originally had "setint %00000010,%00000010" but I thought that perhaps the mask would deactivate pin2, so I modified the code to the one I posted. There was no effect in the behaviour of the interrupt, but also no effect on the reading of pin2. I also double checked by putting the mask back to %00000010.

That is in the physical parts. In the simulator things worked straight away, and that is why I thought that I had broken something, but even after swapping parts I get the same behaviour.

One more thing to note is that LED2 blips very faintly with (about) a 1Hz frequency, irrespective of how I set the control byte in the DS1307 ($00, $20 or $80).

Many Thanks
Riccardo
 

hippy

Technical Support
Staff member
It sounds like there may be some issues with your hardware but perhaps not.

There is no reason a correct 'setint' command should inhibit another pin but perhaps it is the interrupt behaviour itself which is causing the problem. If an interrupt event were permanently asserted it could be that the interrupt never returns control to the rest of the program and this could also lead to unexpected behaviour which could perhaps affect other things including the LED.

I am not sure why interrupts are being used because it would seem polling would be just as appropriate. In fact, having interrupts could be causing the problem. Perhaps pin2 is being seen but an interrupt is then screwing things up.

The best way to find out what is going on is to add SERTXD commands in the program so you can follow program execution. Though it would probably be easier to rewrite to use polling where you can more easily predict what that execution would be.
 

rmeldo

Senior Member
Thanks for the reply,

I will do some further investigation with the SERTXD and with a stripped down program.

The idea was to send the Picaxe to sleep between interrupts and save the battery, since there are large parts of the day when the gas consumption is zero. That and learning about interrupts...

Thanks for the pointers

Riccardo
 

rmeldo

Senior Member
Are parallel interrupts on 18M2 possible?

A Quick update and a question.

First of hall Hippy was right: I was setting the interrupt to detect a high value of a pin when the pin is high all the time, screwing up the whole logic. Once set the interrupt to detect the low value everything started working.


Now the question:


Currently my code use interrupts to detect the magnet coming into range and then going out of range. I am using polling to detect pressing push buttons to drive the GUI on the LCD display.

It occurred to me that if only I could use the parallel execution paths possible in the 18M2 chip and have separate interrupts for the two paths I could use one execution path with an interrupt for the pulse counting and the other path with interrupts to implement the user interface.

Is this at all possible or only one interrupt can be active at a time?

Many thanks
Riccardo
 

BeanieBots

Moderator
It is possible but not the way you are thinking. (you can have only ONE interrupt routine)
All you need to do in your interrupt routine is detect which pin(s) caused the interrupt and branch accordingly.
If for example your interrupting bits are 0,1,2 you only need to mask off those three bits to create a 'number' that represents the cause of the interrupt.
A SELECT/CASE structure can then process as required.
Alternatively, use an 'if bit0 = x then... if bit1 = x then... etc.' type structure.
 

rmeldo

Senior Member
Thanks BeanieBots.

So if I understand correctly I need to use the instruction
Code:
SETINT OR input,mask
so that the interrupt is detected when any of the pins I am interested in matches the mask.

Is that correct?

Many Thanks
Riccardo
 

BeanieBots

Moderator
Yes, that should work.
The last time I did something similar there was no "OR" function and I had to use setint NOT which worked fine but needed a lot of head scratching to get right because all the logic is inverted.

Another method (used before the expanded settint functions were available) was to have all the inputs diode OR'd to one interrupt pin.
 
Top