DPDK patches and discussions
 help / color / mirror / Atom feed
* [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
@ 2015-06-03  6:31 Selmon Yang
  2015-06-03 12:54 ` Bruce Richardson
  0 siblings, 1 reply; 7+ messages in thread
From: Selmon Yang @ 2015-06-03  6:31 UTC (permalink / raw)
  To: dev

Hi,

I found that, in dpdk 2.0, rte_eal_alarm_set() is affected by
discontinuous jumps in the system time because eal_alarm_callback()
and rte_eal_alarm_set() use gettimeofday() to get the current time.

Here is what I encountered.
I set up a rte eal alarm as below, and I like it to be triggered every second.
        #define USE_PER_S 1000 * 1000
        void my_alarm_cb(void *arg)
        {
                /* send heartbeat signal out, etc. */

                rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
                return;
        }

        int main(void)
        {
                /* ..., do something */
                rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
                /* ... do something else */
        }

It works fine in most of time.
However, if I change system time manually, it is possible that rte alarm
function works out of my expectation.
Suppose that current time is 11:00:00 AM, and eal_alarm_callback()
is triggered because I executed
rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL) at 10:59:59 AM.
eal_alarm_callback() gets the current time (11:00:00 AM)
and calls my_alarm_cb() as below.
        while ((ap = LIST_FIRST(&alarm_list)) !=NULL &&
                      gettimeofday(&now, NULL) == 0 &&
                      (ap->time.tv_sec < now.tv_sec ||
(ap->time.tv_sec == now.tv_sec &&
                                              ap->time.tv_usec <=
now.tv_usec))){
                ap->executing = 1;
                ap->executing_id = pthread_self();
                rte_spinlock_unlock(&alarm_list_lk);

                ap->cb_fn(ap->cb_arg);

                rte_spinlock_lock(&alarm_list_lk);

                LIST_REMOVE(ap, next);
                rte_free(ap);
        }

In my_alarm_cb(), rte_eal_alarm_set() is called again.
rte_eall_alarm_set() gets the current time (11:00:00 AM), plus 1 second,
and adds the new alarm entry to alarm_list.
        /* use current time to calculate absolute time of alarm */
        gettimeofday(&now, NULL);

        new_alarm->cb_fn = cb_fn;
        new_alarm->cb_arg = cb_arg;
        new_alarm->time.tv_usec = (now.tv_usec + us) % US_PER_S;
        new_alarm->time.tv_sec = now.tv_sec + ((now.tv_usec + us) / US_PER_S);

        rte_spinlock_lock(&alarm_list_lk);
        if (!handler_registered) {
                ret |= rte_intr_callback_register(&intr_handle,
                                eal_alarm_callback, NULL);
                handler_registered = (ret == 0) ? 1 : 0;
        }

        if (LIST_EMPTY(&alarm_list))
                LIST_INSERT_HEAD(&alarm_list, new_alarm, next);
        else {
                LIST_FOREACH(ap, &alarm_list, next) {
                        if (ap->time.tv_sec > new_alarm->time.tv_sec ||
                                        (ap->time.tv_sec ==
new_alarm->time.tv_sec &&

ap->time.tv_usec > new_alarm->time.tv_usec)){
                                LIST_INSERT_BEFORE(ap, new_alarm, next);
                                break;
                        }
                        if (LIST_NEXT(ap, next) == NULL) {
                                LIST_INSERT_AFTER(ap, new_alarm, next);
                                break;
                        }
                }
        }

After the new alarm entry is added to alarm_list, if current time is
set to 8:00:00 AM manually, the current time in eal_alarm_callback()
will be updated to 8:00:00 AM, too.
Then the new alarm entry will be triggered after 3 hours and 1 second.

I think rte alarm should not be affected by discontinuous jumps in
the system time.
I tried to replace gettimeofday() with clock_gettime(CLOCK_MONOTONIC_RAW, &now),
and it looks work fine.
What do you think about this modification?
Will you consider to modify rte_alarm functions to be not affected
by discontinuous jumps in the system time?

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
  2015-06-03  6:31 [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time Selmon Yang
@ 2015-06-03 12:54 ` Bruce Richardson
  2015-06-03 13:07   ` Jay Rolette
  0 siblings, 1 reply; 7+ messages in thread
From: Bruce Richardson @ 2015-06-03 12:54 UTC (permalink / raw)
  To: Selmon Yang; +Cc: dev

On Wed, Jun 03, 2015 at 02:31:47PM +0800, Selmon Yang wrote:
> Hi,
> 
> I found that, in dpdk 2.0, rte_eal_alarm_set() is affected by
> discontinuous jumps in the system time because eal_alarm_callback()
> and rte_eal_alarm_set() use gettimeofday() to get the current time.
> 
> Here is what I encountered.
> I set up a rte eal alarm as below, and I like it to be triggered every second.
>         #define USE_PER_S 1000 * 1000
>         void my_alarm_cb(void *arg)
>         {
>                 /* send heartbeat signal out, etc. */
> 
>                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
>                 return;
>         }
> 
>         int main(void)
>         {
>                 /* ..., do something */
>                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
>                 /* ... do something else */
>         }
> 
> It works fine in most of time.
> However, if I change system time manually, it is possible that rte alarm
> function works out of my expectation.
> Suppose that current time is 11:00:00 AM, and eal_alarm_callback()
> is triggered because I executed
> rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL) at 10:59:59 AM.
> eal_alarm_callback() gets the current time (11:00:00 AM)
> and calls my_alarm_cb() as below.
>         while ((ap = LIST_FIRST(&alarm_list)) !=NULL &&
>                       gettimeofday(&now, NULL) == 0 &&
>                       (ap->time.tv_sec < now.tv_sec ||
> (ap->time.tv_sec == now.tv_sec &&
>                                               ap->time.tv_usec <=
> now.tv_usec))){
>                 ap->executing = 1;
>                 ap->executing_id = pthread_self();
>                 rte_spinlock_unlock(&alarm_list_lk);
> 
>                 ap->cb_fn(ap->cb_arg);
> 
>                 rte_spinlock_lock(&alarm_list_lk);
> 
>                 LIST_REMOVE(ap, next);
>                 rte_free(ap);
>         }
> 
> In my_alarm_cb(), rte_eal_alarm_set() is called again.
> rte_eall_alarm_set() gets the current time (11:00:00 AM), plus 1 second,
> and adds the new alarm entry to alarm_list.
>         /* use current time to calculate absolute time of alarm */
>         gettimeofday(&now, NULL);
> 
>         new_alarm->cb_fn = cb_fn;
>         new_alarm->cb_arg = cb_arg;
>         new_alarm->time.tv_usec = (now.tv_usec + us) % US_PER_S;
>         new_alarm->time.tv_sec = now.tv_sec + ((now.tv_usec + us) / US_PER_S);
> 
>         rte_spinlock_lock(&alarm_list_lk);
>         if (!handler_registered) {
>                 ret |= rte_intr_callback_register(&intr_handle,
>                                 eal_alarm_callback, NULL);
>                 handler_registered = (ret == 0) ? 1 : 0;
>         }
> 
>         if (LIST_EMPTY(&alarm_list))
>                 LIST_INSERT_HEAD(&alarm_list, new_alarm, next);
>         else {
>                 LIST_FOREACH(ap, &alarm_list, next) {
>                         if (ap->time.tv_sec > new_alarm->time.tv_sec ||
>                                         (ap->time.tv_sec ==
> new_alarm->time.tv_sec &&
> 
> ap->time.tv_usec > new_alarm->time.tv_usec)){
>                                 LIST_INSERT_BEFORE(ap, new_alarm, next);
>                                 break;
>                         }
>                         if (LIST_NEXT(ap, next) == NULL) {
>                                 LIST_INSERT_AFTER(ap, new_alarm, next);
>                                 break;
>                         }
>                 }
>         }
> 
> After the new alarm entry is added to alarm_list, if current time is
> set to 8:00:00 AM manually, the current time in eal_alarm_callback()
> will be updated to 8:00:00 AM, too.
> Then the new alarm entry will be triggered after 3 hours and 1 second.
> 
> I think rte alarm should not be affected by discontinuous jumps in
> the system time.
> I tried to replace gettimeofday() with clock_gettime(CLOCK_MONOTONIC_RAW, &now),
> and it looks work fine.
> What do you think about this modification?
> Will you consider to modify rte_alarm functions to be not affected
> by discontinuous jumps in the system time?

I agree with you that the alarm functionality should not be affected by jumps
in system time. If you have a patch that fixes this bug, it would be great if
you could upstream it here.

Thanks,
/Bruce

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
  2015-06-03 12:54 ` Bruce Richardson
@ 2015-06-03 13:07   ` Jay Rolette
  2015-06-04  2:09     ` Selmon Yang
  0 siblings, 1 reply; 7+ messages in thread
From: Jay Rolette @ 2015-06-03 13:07 UTC (permalink / raw)
  To: Bruce Richardson; +Cc: DPDK

On Wed, Jun 3, 2015 at 7:54 AM, Bruce Richardson <bruce.richardson@intel.com
> wrote:

> On Wed, Jun 03, 2015 at 02:31:47PM +0800, Selmon Yang wrote:
> > Hi,
> >
> > I found that, in dpdk 2.0, rte_eal_alarm_set() is affected by
> > discontinuous jumps in the system time because eal_alarm_callback()
> > and rte_eal_alarm_set() use gettimeofday() to get the current time.
> >
> > Here is what I encountered.
> > I set up a rte eal alarm as below, and I like it to be triggered every
> second.
> >         #define USE_PER_S 1000 * 1000
> >         void my_alarm_cb(void *arg)
> >         {
> >                 /* send heartbeat signal out, etc. */
> >
> >                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
> >                 return;
> >         }
> >
> >         int main(void)
> >         {
> >                 /* ..., do something */
> >                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
> >                 /* ... do something else */
> >         }
> >
> > It works fine in most of time.
> > However, if I change system time manually, it is possible that rte alarm
> > function works out of my expectation.
> > Suppose that current time is 11:00:00 AM, and eal_alarm_callback()
> > is triggered because I executed
> > rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL) at 10:59:59 AM.
> > eal_alarm_callback() gets the current time (11:00:00 AM)
> > and calls my_alarm_cb() as below.
> >         while ((ap = LIST_FIRST(&alarm_list)) !=NULL &&
> >                       gettimeofday(&now, NULL) == 0 &&
> >                       (ap->time.tv_sec < now.tv_sec ||
> > (ap->time.tv_sec == now.tv_sec &&
> >                                               ap->time.tv_usec <=
> > now.tv_usec))){
> >                 ap->executing = 1;
> >                 ap->executing_id = pthread_self();
> >                 rte_spinlock_unlock(&alarm_list_lk);
> >
> >                 ap->cb_fn(ap->cb_arg);
> >
> >                 rte_spinlock_lock(&alarm_list_lk);
> >
> >                 LIST_REMOVE(ap, next);
> >                 rte_free(ap);
> >         }
> >
> > In my_alarm_cb(), rte_eal_alarm_set() is called again.
> > rte_eall_alarm_set() gets the current time (11:00:00 AM), plus 1 second,
> > and adds the new alarm entry to alarm_list.
> >         /* use current time to calculate absolute time of alarm */
> >         gettimeofday(&now, NULL);
> >
> >         new_alarm->cb_fn = cb_fn;
> >         new_alarm->cb_arg = cb_arg;
> >         new_alarm->time.tv_usec = (now.tv_usec + us) % US_PER_S;
> >         new_alarm->time.tv_sec = now.tv_sec + ((now.tv_usec + us) /
> US_PER_S);
> >
> >         rte_spinlock_lock(&alarm_list_lk);
> >         if (!handler_registered) {
> >                 ret |= rte_intr_callback_register(&intr_handle,
> >                                 eal_alarm_callback, NULL);
> >                 handler_registered = (ret == 0) ? 1 : 0;
> >         }
> >
> >         if (LIST_EMPTY(&alarm_list))
> >                 LIST_INSERT_HEAD(&alarm_list, new_alarm, next);
> >         else {
> >                 LIST_FOREACH(ap, &alarm_list, next) {
> >                         if (ap->time.tv_sec > new_alarm->time.tv_sec ||
> >                                         (ap->time.tv_sec ==
> > new_alarm->time.tv_sec &&
> >
> > ap->time.tv_usec > new_alarm->time.tv_usec)){
> >                                 LIST_INSERT_BEFORE(ap, new_alarm, next);
> >                                 break;
> >                         }
> >                         if (LIST_NEXT(ap, next) == NULL) {
> >                                 LIST_INSERT_AFTER(ap, new_alarm, next);
> >                                 break;
> >                         }
> >                 }
> >         }
> >
> > After the new alarm entry is added to alarm_list, if current time is
> > set to 8:00:00 AM manually, the current time in eal_alarm_callback()
> > will be updated to 8:00:00 AM, too.
> > Then the new alarm entry will be triggered after 3 hours and 1 second.
> >
> > I think rte alarm should not be affected by discontinuous jumps in
> > the system time.
> > I tried to replace gettimeofday() with
> clock_gettime(CLOCK_MONOTONIC_RAW, &now),
> > and it looks work fine.
> > What do you think about this modification?
> > Will you consider to modify rte_alarm functions to be not affected
> > by discontinuous jumps in the system time?
>
> I agree with you that the alarm functionality should not be affected by
> jumps
> in system time. If you have a patch that fixes this bug, it would be great
> if
> you could upstream it here.
>
> Thanks,
> /Bruce
>

I haven't looked through the RTE alarm code, but one thing to consider is
whether you want to use CLOCK_MONOTONIC_RAW or just CLOCK_MONOTONIC. The
RAW version is ~10x slower than the CLOCK_MONOTONIC.

CLOCK_MONOTONIC isn't completely protected from NTP frequency adjustments,
but it won't have discontinuities.

We've found the rte_eal_alarm calls to be surprisingly (ie., we hadn't
bothered to look at the implementation yet) variable and intermittently
slow, so the 10x difference on the call to clock_gettime() may be relevant.

Jay

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
  2015-06-03 13:07   ` Jay Rolette
@ 2015-06-04  2:09     ` Selmon Yang
  2015-06-04  2:29       ` Selmon Yang
  0 siblings, 1 reply; 7+ messages in thread
From: Selmon Yang @ 2015-06-04  2:09 UTC (permalink / raw)
  To: Jay Rolette; +Cc: DPDK

Hi, Bruce,

Thank you very much for your positive response.
The attachment is the patch.
Please have a look.

Hi, Jay,

Thank you so much for your kindly reminding.
However, due to I really like the alarm functionalities not to be affected.
I guess I need to replace CLOCK_MONOTONIC_RAW with CLOCK_MONOTONIC
and do more tests to see if it also works for me.


2015-06-03 21:07 GMT+08:00 Jay Rolette <rolette@infiniteio.com>:
>
> On Wed, Jun 3, 2015 at 7:54 AM, Bruce Richardson
> <bruce.richardson@intel.com> wrote:
>>
>> On Wed, Jun 03, 2015 at 02:31:47PM +0800, Selmon Yang wrote:
>> > Hi,
>> >
>> > I found that, in dpdk 2.0, rte_eal_alarm_set() is affected by
>> > discontinuous jumps in the system time because eal_alarm_callback()
>> > and rte_eal_alarm_set() use gettimeofday() to get the current time.
>> >
>> > Here is what I encountered.
>> > I set up a rte eal alarm as below, and I like it to be triggered every
>> > second.
>> >         #define USE_PER_S 1000 * 1000
>> >         void my_alarm_cb(void *arg)
>> >         {
>> >                 /* send heartbeat signal out, etc. */
>> >
>> >                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
>> >                 return;
>> >         }
>> >
>> >         int main(void)
>> >         {
>> >                 /* ..., do something */
>> >                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
>> >                 /* ... do something else */
>> >         }
>> >
>> > It works fine in most of time.
>> > However, if I change system time manually, it is possible that rte alarm
>> > function works out of my expectation.
>> > Suppose that current time is 11:00:00 AM, and eal_alarm_callback()
>> > is triggered because I executed
>> > rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL) at 10:59:59 AM.
>> > eal_alarm_callback() gets the current time (11:00:00 AM)
>> > and calls my_alarm_cb() as below.
>> >         while ((ap = LIST_FIRST(&alarm_list)) !=NULL &&
>> >                       gettimeofday(&now, NULL) == 0 &&
>> >                       (ap->time.tv_sec < now.tv_sec ||
>> > (ap->time.tv_sec == now.tv_sec &&
>> >                                               ap->time.tv_usec <=
>> > now.tv_usec))){
>> >                 ap->executing = 1;
>> >                 ap->executing_id = pthread_self();
>> >                 rte_spinlock_unlock(&alarm_list_lk);
>> >
>> >                 ap->cb_fn(ap->cb_arg);
>> >
>> >                 rte_spinlock_lock(&alarm_list_lk);
>> >
>> >                 LIST_REMOVE(ap, next);
>> >                 rte_free(ap);
>> >         }
>> >
>> > In my_alarm_cb(), rte_eal_alarm_set() is called again.
>> > rte_eall_alarm_set() gets the current time (11:00:00 AM), plus 1 second,
>> > and adds the new alarm entry to alarm_list.
>> >         /* use current time to calculate absolute time of alarm */
>> >         gettimeofday(&now, NULL);
>> >
>> >         new_alarm->cb_fn = cb_fn;
>> >         new_alarm->cb_arg = cb_arg;
>> >         new_alarm->time.tv_usec = (now.tv_usec + us) % US_PER_S;
>> >         new_alarm->time.tv_sec = now.tv_sec + ((now.tv_usec + us) /
>> > US_PER_S);
>> >
>> >         rte_spinlock_lock(&alarm_list_lk);
>> >         if (!handler_registered) {
>> >                 ret |= rte_intr_callback_register(&intr_handle,
>> >                                 eal_alarm_callback, NULL);
>> >                 handler_registered = (ret == 0) ? 1 : 0;
>> >         }
>> >
>> >         if (LIST_EMPTY(&alarm_list))
>> >                 LIST_INSERT_HEAD(&alarm_list, new_alarm, next);
>> >         else {
>> >                 LIST_FOREACH(ap, &alarm_list, next) {
>> >                         if (ap->time.tv_sec > new_alarm->time.tv_sec ||
>> >                                         (ap->time.tv_sec ==
>> > new_alarm->time.tv_sec &&
>> >
>> > ap->time.tv_usec > new_alarm->time.tv_usec)){
>> >                                 LIST_INSERT_BEFORE(ap, new_alarm, next);
>> >                                 break;
>> >                         }
>> >                         if (LIST_NEXT(ap, next) == NULL) {
>> >                                 LIST_INSERT_AFTER(ap, new_alarm, next);
>> >                                 break;
>> >                         }
>> >                 }
>> >         }
>> >
>> > After the new alarm entry is added to alarm_list, if current time is
>> > set to 8:00:00 AM manually, the current time in eal_alarm_callback()
>> > will be updated to 8:00:00 AM, too.
>> > Then the new alarm entry will be triggered after 3 hours and 1 second.
>> >
>> > I think rte alarm should not be affected by discontinuous jumps in
>> > the system time.
>> > I tried to replace gettimeofday() with
>> > clock_gettime(CLOCK_MONOTONIC_RAW, &now),
>> > and it looks work fine.
>> > What do you think about this modification?
>> > Will you consider to modify rte_alarm functions to be not affected
>> > by discontinuous jumps in the system time?
>>
>> I agree with you that the alarm functionality should not be affected by
>> jumps
>> in system time. If you have a patch that fixes this bug, it would be great
>> if
>> you could upstream it here.
>>
>> Thanks,
>> /Bruce
>
>
> I haven't looked through the RTE alarm code, but one thing to consider is
> whether you want to use CLOCK_MONOTONIC_RAW or just CLOCK_MONOTONIC. The RAW
> version is ~10x slower than the CLOCK_MONOTONIC.
>
> CLOCK_MONOTONIC isn't completely protected from NTP frequency adjustments,
> but it won't have discontinuities.
>
> We've found the rte_eal_alarm calls to be surprisingly (ie., we hadn't
> bothered to look at the implementation yet) variable and intermittently
> slow, so the 10x difference on the call to clock_gettime() may be relevant.
>
> Jay

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
  2015-06-04  2:09     ` Selmon Yang
@ 2015-06-04  2:29       ` Selmon Yang
  2015-06-04  9:39         ` Bruce Richardson
  0 siblings, 1 reply; 7+ messages in thread
From: Selmon Yang @ 2015-06-04  2:29 UTC (permalink / raw)
  To: Jay Rolette; +Cc: DPDK

Hi, Bruce, Jay,

I am sorry that the patch in last mail is the wrong one,
please replace it with the attached one in this mail.

2015-06-04 10:09 GMT+08:00 Selmon Yang <wolkayang@gmail.com>:
> Hi, Bruce,
>
> Thank you very much for your positive response.
> The attachment is the patch.
> Please have a look.
>
> Hi, Jay,
>
> Thank you so much for your kindly reminding.
> However, due to I really like the alarm functionalities not to be affected.
> I guess I need to replace CLOCK_MONOTONIC_RAW with CLOCK_MONOTONIC
> and do more tests to see if it also works for me.
>
>
> 2015-06-03 21:07 GMT+08:00 Jay Rolette <rolette@infiniteio.com>:
>>
>> On Wed, Jun 3, 2015 at 7:54 AM, Bruce Richardson
>> <bruce.richardson@intel.com> wrote:
>>>
>>> On Wed, Jun 03, 2015 at 02:31:47PM +0800, Selmon Yang wrote:
>>> > Hi,
>>> >
>>> > I found that, in dpdk 2.0, rte_eal_alarm_set() is affected by
>>> > discontinuous jumps in the system time because eal_alarm_callback()
>>> > and rte_eal_alarm_set() use gettimeofday() to get the current time.
>>> >
>>> > Here is what I encountered.
>>> > I set up a rte eal alarm as below, and I like it to be triggered every
>>> > second.
>>> >         #define USE_PER_S 1000 * 1000
>>> >         void my_alarm_cb(void *arg)
>>> >         {
>>> >                 /* send heartbeat signal out, etc. */
>>> >
>>> >                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
>>> >                 return;
>>> >         }
>>> >
>>> >         int main(void)
>>> >         {
>>> >                 /* ..., do something */
>>> >                 rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL);
>>> >                 /* ... do something else */
>>> >         }
>>> >
>>> > It works fine in most of time.
>>> > However, if I change system time manually, it is possible that rte alarm
>>> > function works out of my expectation.
>>> > Suppose that current time is 11:00:00 AM, and eal_alarm_callback()
>>> > is triggered because I executed
>>> > rte_eal_alarm_set(1 * US_PER_S, my_alarm_cb, NULL) at 10:59:59 AM.
>>> > eal_alarm_callback() gets the current time (11:00:00 AM)
>>> > and calls my_alarm_cb() as below.
>>> >         while ((ap = LIST_FIRST(&alarm_list)) !=NULL &&
>>> >                       gettimeofday(&now, NULL) == 0 &&
>>> >                       (ap->time.tv_sec < now.tv_sec ||
>>> > (ap->time.tv_sec == now.tv_sec &&
>>> >                                               ap->time.tv_usec <=
>>> > now.tv_usec))){
>>> >                 ap->executing = 1;
>>> >                 ap->executing_id = pthread_self();
>>> >                 rte_spinlock_unlock(&alarm_list_lk);
>>> >
>>> >                 ap->cb_fn(ap->cb_arg);
>>> >
>>> >                 rte_spinlock_lock(&alarm_list_lk);
>>> >
>>> >                 LIST_REMOVE(ap, next);
>>> >                 rte_free(ap);
>>> >         }
>>> >
>>> > In my_alarm_cb(), rte_eal_alarm_set() is called again.
>>> > rte_eall_alarm_set() gets the current time (11:00:00 AM), plus 1 second,
>>> > and adds the new alarm entry to alarm_list.
>>> >         /* use current time to calculate absolute time of alarm */
>>> >         gettimeofday(&now, NULL);
>>> >
>>> >         new_alarm->cb_fn = cb_fn;
>>> >         new_alarm->cb_arg = cb_arg;
>>> >         new_alarm->time.tv_usec = (now.tv_usec + us) % US_PER_S;
>>> >         new_alarm->time.tv_sec = now.tv_sec + ((now.tv_usec + us) /
>>> > US_PER_S);
>>> >
>>> >         rte_spinlock_lock(&alarm_list_lk);
>>> >         if (!handler_registered) {
>>> >                 ret |= rte_intr_callback_register(&intr_handle,
>>> >                                 eal_alarm_callback, NULL);
>>> >                 handler_registered = (ret == 0) ? 1 : 0;
>>> >         }
>>> >
>>> >         if (LIST_EMPTY(&alarm_list))
>>> >                 LIST_INSERT_HEAD(&alarm_list, new_alarm, next);
>>> >         else {
>>> >                 LIST_FOREACH(ap, &alarm_list, next) {
>>> >                         if (ap->time.tv_sec > new_alarm->time.tv_sec ||
>>> >                                         (ap->time.tv_sec ==
>>> > new_alarm->time.tv_sec &&
>>> >
>>> > ap->time.tv_usec > new_alarm->time.tv_usec)){
>>> >                                 LIST_INSERT_BEFORE(ap, new_alarm, next);
>>> >                                 break;
>>> >                         }
>>> >                         if (LIST_NEXT(ap, next) == NULL) {
>>> >                                 LIST_INSERT_AFTER(ap, new_alarm, next);
>>> >                                 break;
>>> >                         }
>>> >                 }
>>> >         }
>>> >
>>> > After the new alarm entry is added to alarm_list, if current time is
>>> > set to 8:00:00 AM manually, the current time in eal_alarm_callback()
>>> > will be updated to 8:00:00 AM, too.
>>> > Then the new alarm entry will be triggered after 3 hours and 1 second.
>>> >
>>> > I think rte alarm should not be affected by discontinuous jumps in
>>> > the system time.
>>> > I tried to replace gettimeofday() with
>>> > clock_gettime(CLOCK_MONOTONIC_RAW, &now),
>>> > and it looks work fine.
>>> > What do you think about this modification?
>>> > Will you consider to modify rte_alarm functions to be not affected
>>> > by discontinuous jumps in the system time?
>>>
>>> I agree with you that the alarm functionality should not be affected by
>>> jumps
>>> in system time. If you have a patch that fixes this bug, it would be great
>>> if
>>> you could upstream it here.
>>>
>>> Thanks,
>>> /Bruce
>>
>>
>> I haven't looked through the RTE alarm code, but one thing to consider is
>> whether you want to use CLOCK_MONOTONIC_RAW or just CLOCK_MONOTONIC. The RAW
>> version is ~10x slower than the CLOCK_MONOTONIC.
>>
>> CLOCK_MONOTONIC isn't completely protected from NTP frequency adjustments,
>> but it won't have discontinuities.
>>
>> We've found the rte_eal_alarm calls to be surprisingly (ie., we hadn't
>> bothered to look at the implementation yet) variable and intermittently
>> slow, so the 10x difference on the call to clock_gettime() may be relevant.
>>
>> Jay

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
  2015-06-04  2:29       ` Selmon Yang
@ 2015-06-04  9:39         ` Bruce Richardson
  2015-06-05  2:48           ` Selmon Yang
  0 siblings, 1 reply; 7+ messages in thread
From: Bruce Richardson @ 2015-06-04  9:39 UTC (permalink / raw)
  To: Selmon Yang; +Cc: DPDK

On Thu, Jun 04, 2015 at 10:29:48AM +0800, Selmon Yang wrote:
> Hi, Bruce, Jay,
> 
> I am sorry that the patch in last mail is the wrong one,
> please replace it with the attached one in this mail.
> 

Thanks for the patch. Could you perhaps submit this using git send-email as an official 
patch, with appropriate signoff to the mailing list. It will make reviewing
it easier, and allow us to consider it for integration. See http://dpdk.org/dev
for more details on how to submit patches.

	Regards,
	/Bruce

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time
  2015-06-04  9:39         ` Bruce Richardson
@ 2015-06-05  2:48           ` Selmon Yang
  0 siblings, 0 replies; 7+ messages in thread
From: Selmon Yang @ 2015-06-05  2:48 UTC (permalink / raw)
  To: Bruce Richardson; +Cc: DPDK

Hi, Bruce,

Thank you very much for your explanation.
I will send my patch in that way.
I am so sorry for any inconvenience causes you.


2015-06-04 17:39 GMT+08:00 Bruce Richardson <bruce.richardson@intel.com>:
> On Thu, Jun 04, 2015 at 10:29:48AM +0800, Selmon Yang wrote:
>> Hi, Bruce, Jay,
>>
>> I am sorry that the patch in last mail is the wrong one,
>> please replace it with the attached one in this mail.
>>
>
> Thanks for the patch. Could you perhaps submit this using git send-email as an official
> patch, with appropriate signoff to the mailing list. It will make reviewing
> it easier, and allow us to consider it for integration. See http://dpdk.org/dev
> for more details on how to submit patches.
>
>         Regards,
>         /Bruce
>

^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2015-06-05  2:48 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-06-03  6:31 [dpdk-dev] rte_eal_alarm_set() is affected by discontinuous jumps in the system time Selmon Yang
2015-06-03 12:54 ` Bruce Richardson
2015-06-03 13:07   ` Jay Rolette
2015-06-04  2:09     ` Selmon Yang
2015-06-04  2:29       ` Selmon Yang
2015-06-04  9:39         ` Bruce Richardson
2015-06-05  2:48           ` Selmon Yang

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).