View previous topic :: View next topic |
Author |
Message |
swartz
Joined: 12 Nov 2021 Posts: 4
|
External counter seems prescaled (divided by 2) |
Posted: Fri Nov 12, 2021 8:13 pm |
|
|
Working through the sensor samples. The code below is for the magnetic sensor - digital. I can't see anything wrong in the code -- it seems quite simple -- but there must be something I am not seeing.
Code: |
void main(void)
{
int8 counter;
int8 total = 0;
setup_timer_0( T0_EXT_L_TO_H );
set_timer0( 0 );
while(1)
{
output_low( GREEN_LED );
wait_for(BUTTON_1);
output_high( GREEN_LED );
counter = get_timer0();
total += counter;
set_timer0( 0 );
printf( "current: %9d total: %9d \r\n", counter, total );
}
}
|
When counter=get_timer0(), half the value is returned. For example, if I wave the magnet in front of the device 10 times (confirmed with an LED blink) -- a value of 5 is returned. Always is half. What could be going on? Could the sensor be bad? The sensor is connected to C5 as the instructions call for. |
|
|
PrinceNai
Joined: 31 Oct 2016 Posts: 479 Location: Montenegro
|
|
Posted: Fri Nov 12, 2021 8:54 pm |
|
|
Is it possible that your sensor just toggles state every time a magnet goes by? If that is the case, you'd catch only half of transitions with your timer setup. What happens if you swing it like 7 times or any odd number of times? Does it sometimes give you one more count and sometimes one less than half? You said confirmed by LED? LED in the sensor? |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9226 Location: Greensville,Ontario
|
|
Posted: Fri Nov 12, 2021 9:11 pm |
|
|
You really need to post the make/model info of the 'magnetic sensor'. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Fri Nov 12, 2021 10:08 pm |
|
|
I found the wait_for() routine that he's calling. It's in the e3.h file
in the CCS drivers folder:
Code: |
#define BUTTON_1 PIN_C1
#define BUTTON_2 PIN_C2
// Waits until the button has been pressed and then released.
// The processor will be deadlocked waiting for button to be pressed.
// Performs very crude debouncing.
// 'pin' can be either BUTTON_1 or BUTTON_2
void wait_for(long pin)
{
while(input(pin));
delay_ms(100);
while(!input(pin));
delay_ms(100);
}
|
KY-003 Hall Magnetic Sensor Module:
https://arduinomodules.info/ky-003-hall-magnetic-sensor-module/
His posted code is totally different from the sensor code provided
by CCS with the compiler. Here are the instructions for it:
Code: |
////
//// ex_sk_hall_digital.c
////
//// Example code showing how to read the result of the
//// magnetic field recorded by the magnetic hall effect sensor.
//// Example code developed to run on the CCS E3 Mini development kit.
//// Sensor module should be inserted into the top right of the of
//// the E3 I/O header: the G pin of module inserts into the GND pin
//// of the E3 and the Y pin of the module inserts into the B5 pin of
//// the E3.
//// This module detects magnetic fields and returns a digital result
//// (LED) based on the output of the hall effect sensor. The hall
//// effect sensor only returns a YES (pin high) or NO (pin low) if
//// it's detecting a magnetic field.
//// When the example code is running, a green LED will be lit. Use a
//// magnet up close to the module. When the module senses the
//// magnetic field, a red LED will light up and the GREEN LED will
//// turn off.
//// This sensor module is sometimes called ky-003.
|
The code for the above sensor tests if it gets a high level from the
sensor. If so, it turns on the GREEN led. If it's low, it turns on the RED led. |
|
|
hmmpic
Joined: 09 Mar 2010 Posts: 314 Location: Denmark
|
|
Posted: Sat Nov 13, 2021 4:22 am |
|
|
Maybe just me but.
int8 and this
Code: | counter = get_timer0();
total += counter; |
|
|
|
swartz
Joined: 12 Nov 2021 Posts: 4
|
|
Posted: Mon Nov 15, 2021 4:17 pm |
|
|
Quote: | His posted code is totally different from the sensor code provided
by CCS with the compiler. |
You are exactly correct. This small bit of code is for the E3 board and using the hall effect sensor in the sensors experiment kit.
It is different because I am working on the "extra credit" activity, which utilizes the timer0 configured as a pulse counter.
It is a bit of a mystery to me what is going on here.
If (by the LED flash) I create ten pulses. The counter returns 5.
If I create 7 pulses, the counter returns 3.
If I had blown the sensor, I would expect no pulses.
Similarly, if I had zapped the PIC -- then -- I don't know what to expect but it would likely make even less sense.
Perhaps though the sensor is failing/failed and this is just how its failure is manifest.
For:
Quote: | Code: |
counter = get_timer0();
total += counter; |
|
This looks safe to me, except that total is overflow rather quickly. But for experimenting, this seems like a don't-care. In "real code" int16 would be better for total, I think.
It still doesn't work exactly right, but I "get the idea" -- and there does not seem to be any pre-scaler on the t0 register/counter -- or any way to control it for this kind of application.
Thanks all for your replies. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9226 Location: Greensville,Ontario
|
|
Posted: Mon Nov 15, 2021 4:25 pm |
|
|
which PIC are you using ?
You should post the complete code.
hmm...exactly half the counts...
HAVE to see the program. |
|
|
PrinceNai
Joined: 31 Oct 2016 Posts: 479 Location: Montenegro
|
|
Posted: Mon Nov 15, 2021 4:43 pm |
|
|
This one is meant as a joke. If you always get half of the count, multiply it by 2. I'll never forget one of my teachers at the university. They had to design a high power RF transmitter. Did it, too. The problem was that one corner of the antenna got white hot. The solution was simple: file that corner away. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9226 Location: Greensville,Ontario
|
|
Posted: Mon Nov 15, 2021 5:42 pm |
|
|
Be interesting to hear what happens if a properly debounced pushbutton is used as the 'sensor'.
Also the variables used should be unsigned int8, as it's an 'up count' only, though CCS may default 'int8' to unsigned (0-255).
edit....
I got curious and looked at datasheets of 4 common PICs..
16F84, 16F877, 16F648a and 18F46K22.
They ALL have a prescaler in the TIMER0 peripheral. 1st 3 are 8 bit, 46k22 is 8 or 16.
So my 'gut' says he has the prescaler set to /2. Might be a 'wizard' default ?
Course we can only confirm that once we find out which PIC he's using. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Wed Nov 17, 2021 7:33 am |
|
|
No, not a wizard default, just the way the chip behaves.
The point is that he is not defining a prescaler. Look in the defines file,
what prescaler '0' gives:
For the 877 for example:
Code: |
#define T0_DIV_1 8
#define T0_DIV_2 0
#define T0_DIV_4 1
#define T0_DIV_8 2
#define T0_DIV_16 3
#define T0_DIV_32 4
#define T0_DIV_64 5
#define T0_DIV_128 6
#define T0_DIV_256 7
|
Note that '0' is the value for a prescaler of 2....
By not setting the prescaler he is selecting the default for the chip,
which is /2.....
Lesson:
Never 'assume' what registers will be set to. If you want a particular
value, you need to set it yourself.... |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9226 Location: Greensville,Ontario
|
|
Posted: Wed Nov 17, 2021 7:57 am |
|
|
I'm still wondering WHICH PIC is involved.
One of life's mysteries....
Showing us a complete program would help.. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Wed Nov 17, 2021 9:02 am |
|
|
Absolutely.
Things that should always be included in a post:
Compiler version,
chip(s) involved.
Ideally a program we can actually compile.
'Bits' often lead to much longer threads and answers that may not be
right... |
|
|
swartz
Joined: 12 Nov 2021 Posts: 4
|
external counter seems prescaled (divided by 2) |
Posted: Fri Nov 26, 2021 6:33 pm |
|
|
Gents -- have been away from this for a bit. I appreciate all the responses. Thank you very much for this!
The response about the defines that setup the counter control register pre-scaling is noteworthy of further understanding on my part.
Here are answers to some of the questions I have been asked.
For the device: I am using the CCS E3mini development kit. The device used on this port is reported to be a PIC18F14K50.
The tool I am using is CCS PCWHD version 5.105
The complete source for the program is shown below:
Code: |
#include <e3.h>
void main(void)
{
int8 counter;
int8 total = 0;
setup_timer_0( T0_EXT_L_TO_H );
set_timer0( 0 );
while(1)
{
output_low( GREEN_LED );
wait_for(BUTTON_1);
output_high( GREEN_LED );
counter = get_timer0();
total += counter;
set_timer0( 0 );
printf( "current: %9d total: %9d \r\n", counter, total );
}
}
|
This program is a solution to the "extra credit" activity in Chapter 6 in "Magnetic Force (Binary)" of the Sensors Explorer kit from CCS. (need a bit of a refresher having been away from embedded programming for a bit whilst working on larger systems applications)
Some details of this activity are:
PIN_C5 of the PIC18F14K50 used on the E3 can be configured to be the
Timer 0 input.
When a GPIO is configured to be a timer input, any pulses
seen on the timer input are counted and can be read later in the firmware.
Rewire the hall effect sensor so it’s output is tied to the C5 pin.
Use setup_timer_0() function to configure the timer to read external pulses with T0_EXT_L_TO_H setting.
Use set_timer0(0) to clear the timer, and use get_timer0() to get current timer value.
Using these functions, display the timer value when pressing one of the E3 buttons – then experiment with placing the magnet near and far from the sensor and then pressing the button to see if the measured pulses in Timer 0 match.
This technique for measuring pulses requires no CPU power as it’s done by the Timer 0 peripheral in the background.
This approach is commonly used to measure motor movement and speed by placing a magnet on the rotating part of the motor and using the hall effect sensor to count revolutions
Cheers!
Swartz |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19515
|
|
Posted: Fri Nov 26, 2021 10:58 pm |
|
|
Code: |
#include <e3.h>
void main(void)
{
int8 counter;
int8 total = 0;
setup_timer_0( T0_EXT_L_TO_H | T0_DIV_1);
set_timer0( 0 );
while(1)
{
output_low( GREEN_LED );
wait_for(BUTTON_1);
output_high( GREEN_LED );
counter = get_timer0();
total += counter;
set_timer0( 0 );
printf( "current: %9d total: %9d \r\n", counter, total );
}
}
|
Note the single change. |
|
|
swartz
Joined: 12 Nov 2021 Posts: 4
|
|
Posted: Sat Nov 27, 2021 1:41 pm |
|
|
Ttelmah wrote: | Code: |
#include <e3.h>
void main(void)
{
int8 counter;
int8 total = 0;
setup_timer_0( T0_EXT_L_TO_H | T0_DIV_1);
set_timer0( 0 );
while(1)
{
output_low( GREEN_LED );
wait_for(BUTTON_1);
output_high( GREEN_LED );
counter = get_timer0();
total += counter;
set_timer0( 0 );
printf( "current: %9d total: %9d \r\n", counter, total );
}
}
|
Note the single change. |
fixed! Thank you. Lesson learned.
Happy Holidays.
Swartz |
|
|
|