cancel
Showing results for 
Search instead for 
Did you mean: 

Hall-effect sensor

thewizzard
Associate
Posted on May 27, 2013 at 21:04

Hello,

I'm trying to read rpm from a fan. At first I tried with EXTI and while it worked at fast speed, it started to get crazy when halted or at low speed, especially when the voltage was at undefined state ~1.5V. Is there a way interrupts trigger when actually going from <1V to >2V ? Now I'm trying with a timer in input capture mode ... looked at the reference manual (Interfacing with Hall sensors) and some googling to get this far ...

void HALL_Config(void){
GPIO_InitTypeDef GPIO_InitStructure;
NVIC_InitTypeDef NVIC_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;
GPIO_Init(GPIOA, &GPIO_InitStructure); 
TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure;
TIM_ICInitTypeDef TIM_ICInitStructure;
TIM_TimeBaseStructure.TIM_Prescaler = 840; 
TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; 
TIM_TimeBaseStructure.TIM_Period = 65535; 
TIM_TimeBaseStructure.TIM_ClockDivision = 0; 
TIM_TimeBaseStructure.TIM_RepetitionCounter = 0; 
TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);
//Enable hall sensor
TIM_SelectHallSensor(TIM2, ENABLE); 
// HallSensor event is delivered with singnal TI1F_ED
// (this is XOR of the three hall sensor lines)
// Signal TI1F_ED: falling and rising edge of the inputs is used 
TIM_SelectInputTrigger(TIM2, TIM_TS_TI1F_ED); 
// On every TI1F_ED event the counter is resetted and update is tiggered 
TIM_SelectSlaveMode(TIM2, TIM_SlaveMode_Reset); 
// Channel 1 in input capture mode 
// on every TCR edge (build from TI1F_ED which is a HallSensor edge) 
// the timervalue is copied into ccr register and a CCR1 Interrupt
// TIM_IT_CC1 is fired 
TIM_ICInitStructure.TIM_Channel = TIM_Channel_1; 
TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Rising; 
TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_TRC;
TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;
TIM_ICInitStructure.TIM_ICFilter = 0x0; 
TIM_ICInit(TIM2, &TIM_ICInitStructure); 

TIM_ITConfig(TIM2, TIM_IT_CC1, ENABLE);
//TIM_ITConfig(TIM2, TIM_IT_Trigger, ENABLE);
NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn; 
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x03; 
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3; 
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; 
NVIC_Init(&NVIC_InitStructure); 
TIM_Cmd(TIM2, ENABLE); 
}

... but the interrupt handler never triggers any help appreciated ~Matt #hall-effect-hall-timer #me-too
12 REPLIES 12
emalund
Associate III
Posted on May 27, 2013 at 21:56

Is there a way interrupts trigger when actually going from <1V to >2V ?

 

check Vih min and Vil max in the datasheet

inbetween what happen is anybodys guess

without schmitt-trigger, you can find a place where a change of a few millivolts on the input will change the output

I would not connect a Hall-effect sensor to a logical input without a schmitt trigger inbetween

your micro may have a comparator with hysteresis, if so use it
thewizzard
Associate
Posted on May 28, 2013 at 12:30

Forgot to mention, I'm using the STM32F4 Discovery, and looking into GPIO schemes, there's a schmitt trigger on inputs.

raptorhal2
Lead
Posted on May 28, 2013 at 15:41

Which Hall sensor are you using, and what is the signal source?

Cheers, Hal

emalund
Associate III
Posted on May 28, 2013 at 16:52

if you look at the signal from the Hall on a scope is it 'clean' with 'sloppy' rise and fall times or is it 'noisy'?

I know from encoders that a whole lot of noise at the transition is quite common.

If you see noise a simple RC filter should alleviate the problem

Erik
sascha2
Associate II
Posted on June 17, 2014 at 13:00

Hi I have the same problem. Did you fix the problem and how?

Sascha
Posted on June 17, 2014 at 13:37

Don't expect a poster with two posts from over a year ago to provide a useful response. State clearly YOUR situation and configuration.

Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
sascha2
Associate II
Posted on June 17, 2014 at 16:34

Hi, ok I will try my best:

I want to configuere Timer2 as a hall sensor interface for a bldc motor, but my initialization of the timer doesn't work correctly. I can't get the timer interrupt to work. I can see the hall signals with a logic analyzer and they are correct. Here's my init code:

void Init(void){

  GPIO_InitTypeDef GPIO_InitStructure;

  TIM_TimeBaseInitTypeDef TIM_InitStructure;

  TIM_ICInitTypeDef TIM_ICInitStructure;

  NVIC_InitTypeDef NVIC_InitStructure;

 

  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE);

 

  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13;

  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;

  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;

  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;

  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;

 

  GPIO_Init(GPIOC, &GPIO_InitStructure);

 

  // enable clock for GPIOA

  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);

 

  // inputs for hall sensors

  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2;

  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN;

  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;

  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;

  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;

 

  GPIO_Init(GPIOA, &GPIO_InitStructure);

 

  GPIO_PinAFConfig(GPIOA, GPIO_PinSource0, GPIO_AF_TIM2);

  GPIO_PinAFConfig(GPIOA, GPIO_PinSource1, GPIO_AF_TIM2);

  GPIO_PinAFConfig(GPIOA, GPIO_PinSource2, GPIO_AF_TIM2);

 

  // enable clock for timer2

  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);

 

  // update event every ca. 4295sec

  // resolution: 1usec

  TIM_InitStructure.TIM_Prescaler = 42;

  TIM_InitStructure.TIM_CounterMode = TIM_CounterMode_Up;

  TIM_InitStructure.TIM_Period = 0xFFFFFFFF;

  TIM_InitStructure.TIM_ClockDivision = TIM_CKD_DIV1;

 

  TIM_TimeBaseInit(TIM2, &TIM_InitStructure);

  // connect three channels to XOR in timer

  TIM_SelectHallSensor(TIM2, ENABLE);

 

  TIM_SelectInputTrigger(TIM2, TIM_TS_TI1F_ED);

  TIM_SelectSlaveMode(TIM2, TIM_SlaveMode_Reset);

 

  // initialize the cature compare function of timer2

  TIM_ICInitStructure.TIM_Channel = TIM_Channel_1;

  TIM_ICInitStructure.TIM_ICFilter = 0;

  TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_BothEdge;

  TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;

  TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_TRC;

 

  TIM_ICInit(TIM2, &TIM_ICInitStructure);

 

   // enable the interrupt for timer2

  TIM_ITConfig(TIM2, TIM_IT_CC1, ENABLE);

 

  NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn;

  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;

  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;

  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;

  NVIC_Init(&NVIC_InitStructure);

 

   // enable timer2

  TIM_Cmd(TIM2, ENABLE);

}

Hope someone can help me, thanks in advance for your replies !!!

Sascha

Posted on June 17, 2014 at 17:13

The pins need to be in AF mode in an F4 device, not IN mode

The timer on a 168 MHz F4, on APB1 (DIV4), is running at (DIV2) 84 MHz

ie Prescaler = 84 - 1;

What tool chain? Are you using C++?

Can you generate update or other interrupts on TIM2 in other situations?
Tips, Buy me a coffee, or three.. PayPal Venmo
Up vote any posts that you find helpful, it shows what's working..
sascha2
Associate II
Posted on June 18, 2014 at 11:42

Hi,

thanks for your reply. Wrong Pin configuration was the mistake.

By the way I'm using IAR embedded workbench with the c compiler. The update interrupt worked well as I tried it before.

Thanks again !!!

Sascha