找回密码
 加入计匠网
搜索
热搜: BIOS ACPI CPU Windows
查看: 5399|回复: 0

Smart Timing Mechanism

[复制链接]
发表于 2009-4-20 09:50:13 | 显示全部楼层 |阅读模式
Smart Timing Mechanism

) ~1 m0 g# I( l1 q

+ @* U' D8 R1 l4 g) {3 Y2 m1. Why need this mechanism" B$ N& a: P  m: p9 n5 K
: D# C9 w  n% R' S& ?
   最近在跑一个超薄NB专案,这个专案的power sequence比较奇怪,很多地方需要很多的定时一段时间然后再去调整某一部分的时序。我真是受够了code base中的定时方式。每次定时都要定义一个变量,需要使用时给它赋值,然后再8051的定时器中断到来时,再计数累加。一个函数非常的长,而且充斥着乱七八糟的变量。经过这么多年的发展,代码里到处都是坏味道,看的我非常不爽,于是就产生了改造这个机制的想法。
' |8 l5 u7 a* m, `5 D

( j. W; S5 o' c, H2. How to improve it?
2 `8 e/ o) G; I* i8 H+ Y7 B% C+ {( K* v7 q- ^( b, w
  既然决定了那么就行动吧! 打开google 大神进入code search,看看有没有什么好东西(J我不想重新造轮子,如果有好的代码那么就拿来参考)搜来搜去,发现linux 2.6内核中的定时机制很酷,可是不适合我的环境,它太大了,光这个机制就能把我的EC搞爆了L。然后再狂搜!果然不负我一番苦心,我发现linux 0.95内核中的定时机制挺适合。可是仔细阅读之后发现这个机制有些缺陷,它只处理了插入结点时间比头结点时间长的情况,而没有处理插入结点时间比链表头结点短的状况。下面就是我修改后的source code
$ g3 e$ `6 Z: z& E$ W) ^% x
* p4 l" A6 z/ y+ ~1 `//header file
, M" [0 d5 Z  {8 G& }# J; F/////////////////////////////////////////////////
4 Z. a* u* @$ p#ifndef
; z, @" N7 G1 t, I- W% h! nOEM_TIMER_SERVICE__H
7 \+ Q. X) Z7 G5 a- N
#define: R7 z0 u; H  G$ V  m1 z) t2 Q8 |
OEM_TIMER_SERVIEC__H
& N: f9 ?( L8 _- b2 `4 X0 f$ E( w
* P1 M  W: p& j8 m
% J4 }& P" M% R" k. N  @
void add_timer(unsigned short
2 s# l, t; V+ S' jjiffies,void (*callback)());

, Z4 J) J$ S% ~
9 I" y# K, K( S' R) Rvoid do_timer(void);& q0 Y( J, Q: V8 [: f. n
9 R6 s8 L1 u. N0 O7 M
#endif4 ^4 [* k6 Y* Y, D& p0 C
/////////////////////////////////////////////////
, r0 w% U! P# F( m- _% f8 A3 N2 U/////////////////////////////////////////////////, H( |- h1 ?. O( j% q
//impl file" n% M8 t0 r+ A% O4 `
#include <stdio.h>5 x! g1 a% `0 R6 m* u- B* U
#include "OEMTimerService.H"
0 t6 r! x- U, r- W8 O( N  [
  d) o# P) ~- T. H3 |  H8 R" N# b& L) X; I* b$ x
#define1 M  Y! L) a5 G! x) B4 z0 h# m
TIMER_REQUESTS' a- ^& Y" C' A- M/ r! g
0x30
1 v* _, G% r3 g4 r8 p) A& [: w" _
4 B5 X! I; h! e
struct timer_list ' x2 f/ Y% n1 Z
{9 z. t$ {$ v! j) i  P3 D

  F2 C% m5 c& z5 o6 Tstruct timer_list *next;
! V; a& L0 ^) c' _* @% n9 J6 s
; U( R8 N6 c0 V4 `6 I& ^# N( R
unsigned short jiffies;

" C& `6 `" H5 ]  s
, d1 U2 R) V; h  O7 o& @3 nvoid (*callback)(void);
' d' ?2 c9 V! X3 h1 n  Q5 ?
};
, V& D8 E. I) `
7 Q* @, C- p; h; O5 G1 u& c
9 s: {" g0 c4 z" u( gstruct timer_list timer_list[TIMER_REQUESTS] = {NULL};% k$ L* M% K- E% t1 h0 G; H2 t
; g0 @, m0 _3 H, o
struct timer_list *timer_header = NULL;" U* t, y! B, J; @: k4 \$ u$ {. k
+ D. {2 O1 U6 Y! S& s, H6 H0 F3 O

) I  D3 h5 k( V) x* Ovoid add_timer(unsigned short+ v  w: e2 ^4 C1 U7 Q
jiffies,void (*callback)())

+ |- S( p- k: g/ D' F, t{
* f& j" E) c6 |
( [* r. N, n3 @5 Q) `, c8 L  Ustruct timer_list *ptmp;

& q# p, Z, s% n3 P2 _; U3 W, P0 H" w- _: b. e

; }' v. F- l8 Q! l/ n+ r9 y6 `, Rif(!callback)

( [* [2 z# Z- x1 \$ e( j. t& s/ j) ]4 r
return ;

; j8 D. B5 q  Q) H+ }% r' w, `6 A8 q+ u) h

  h9 v  o. I! ~/ _8 Y8 w8 e) P' l: l4 E, H/ H
EA = 0;

. k4 \9 W( M3 e( h# h, |" X6 b- C
7 _5 Y" v; V# x! T& m- v4 F8 B  p- V9 a. v* @: Y& Z; M* Q
if(jiffies <= 0)

4 f1 @9 n6 Z' V+ u* j" y7 @5 }4 V  p3 F% K" n4 j+ b. Q# z) y# I& J& y
(*callback)();
/ N: L0 f  p  l  r# ^1 l  Q: q

9 W8 t6 L# Z9 ^
9 f1 \5 g6 s: {& Y+ A2 z! c
, N: r; z+ t9 p2 [( h5 ^
for(ptmp = timer_list; ptmp < timer_list + TIMER_REQUESTS; ptmp++)

1 V, c7 ]8 {+ l1 k' C/ n. D- d) W$ n4 {4 s' q- S
if(ptmp->callback == NULL)
+ P1 @: \. n' K
" g( m/ v# W5 Q8 z! n2 v6 l
break;

, E. l+ A" j. ~3 m% R& `7 |, b  y+ S9 m# e+ N2 l3 w

9 W/ {- v  t3 Z, f3 F/ f1 v. D1 i6 d2 J+ q" B6 ^
if(ptmp >= timer_list + TIMER_REQUESTS)
; z, B. \" E9 G; J

$ V8 j$ f9 w1 G; W  k5 H{
, `) B1 E9 V) I
' l; c3 i4 \3 @% b
goto EXIT;
& T2 b8 r) i# u  f
, ]" P; q9 L0 |! _8 N" w
}
8 M. b) U4 v- x
  V: V. f6 V9 Z- r; n# Y
( X* Y8 h4 C+ ~3 n
ptmp->jiffies = jiffies;
0 E! o0 a' U- q) [( I
" F+ k: U' h/ I9 a% Q8 S  c. X
ptmp->callback = callback;

2 _6 ]3 C% p7 n6 a0 ?* r" j' K- C7 |, l' e* y
7 V5 k5 x9 O0 @/ L6 D0 _' h# ^% @: [

/ O6 S9 X/ j0 t: Yptmp->next = timer_header;
2 n0 C+ A3 Z  j; [

1 z9 O: G6 B/ w5 Wtimer_header = ptmp;
7 q" j" m( ]2 @; h2 a+ e! d9 V
) b! C5 s0 ], ?6 w* {9 I
9 U0 w' D7 G9 v  \+ v. [
//add bellow code to fix linux on timer’s bugs ++

' W7 `+ A  X- s- N1 ^$ K- R& A5 D0 r4 T9 B
if(ptmp->next && ptmp->next->jiffies > ptmp->jiffies)
  O2 j' V+ m' f: J/ R& Y$ G
  Z% l4 B! z% \3 R
{

8 H; t6 K. C2 h( O8 c" g" x4 g( J5 q+ u# y+ Y6 m
ptmp->next->jiffies -= ptmp->jiffies;

: I, Q0 I  p/ r- \. O1 b: g* g. u: G
}//end ++
/ e1 t8 S1 E8 G7 H! N0 w8 W

' O9 J6 ~7 [1 X4 j. Felse
$ H8 K2 t- b  V& a3 c: m, t

. l" b3 l. f3 ^9 a# X7 Q% g{
( U1 L( H0 _1 b' Q9 J0 {

0 o  o# i6 j$ {( d8 m3 `. G8 kwhile(ptmp->next && (ptmp->next->jiffies < ptmp->jiffies))
8 \6 @$ u% T& q) N

7 D# W$ K+ k/ Y
& K6 `' Q6 c. ]! e7 a# Y{
/ c! M- ^# A/ G
' ^6 z" |, _- Q# G! D0 u8 V
ptmp->jiffies -= ptmp->next->jiffies;

1 T1 g& z+ Z( r7 x+ H& h
1 k" N- _0 }  Y( |callback = ptmp->callback;
! b$ O; ]" y" o& ]

, w; F' A$ @/ h4 |3 z, Jptmp->callback = ptmp->next->callback;
  m6 \, E# G# H- q# G2 T
$ @( C+ c  V. E3 @
ptmp->next->callback = callback;
- P; f/ R- k2 N: E% \
( K  u! a7 h5 F5 F5 A+ k( L
jiffies = ptmp->jiffies;
% r. K/ l# ?) l) |  J, K) T. x
2 c4 L, I/ n, L. M6 V
ptmp->jiffies = ptmp->next->jiffies;
* c/ [0 J5 I; W% p- M* T3 v
0 D8 E, M/ M& N9 r2 A
ptmp->next->jiffies = jiffies;
0 k' `- w$ g2 O8 K( O4 Q8 z7 g

; D5 P$ c* W: c- u( E" B* |ptmp = ptmp->next;
) W! u7 P9 N* h: p
9 N) P5 v$ S& a6 K
}
( m( h% D8 Z1 D& {5 `' v
" P; f! q) `& C$ x
}

+ H5 u# X9 Q( }/ t7 c, H
4 D, w+ W0 W7 O1 a8 MEXIT:* c# }" `8 d: U9 I/ g7 ?, {0 a0 {
, @% m; z, _) c( q. E
EA = 1;
, W/ ]& T# L- z7 f3 G. G' q* o

2 p. [3 z7 s) Z( _return;

6 r( ^5 z# F2 g1 Y2 z: N}, M6 y; t! {( u

: ~! t1 y# ~0 R5 A- [4 F" Tvoid do_timer(void)' }, x% ^7 X- D% N
{+ Z9 `  O+ H( U; w1 t* n) _3 v
' O& |' B7 t: R) p% _

5 j; ~& w% u' D3 N# Pwhile((timer_header != NULL)

* {7 M! [+ B. ~3 E# T
# f6 S/ c( M4 N" A2 `" N, Q
8 }- u3 |; l; l! e5 }&&(timer_header->callback != NULL)

3 }! k/ _# q' x$ f, F) M, ]8 {+ f
- w2 ]8 \/ b. X4 ?- z! W
/ j% u3 r, @! Y1 `* |&&(--timer_header->jiffies <= 0))
4 a, B* ^7 W, x9 S4 a0 ]

$ C* U; B7 b* n/ O4 A  ]) W{
5 q' k4 Y$ _0 A' t2 p& u
0 q# O1 }  D5 \  H1 D
void (*callback_fptr)(void);

, a5 b  y; v. l0 v6 `
8 z# z; H/ m3 ~8 s5 `( w. ?+ @9 ~
callback_fptr = timer_header->callback;
% N8 K2 ]. \; U- A; A3 \
- @0 i8 ?* W( N3 y& C
timer_header->callback = NULL;
3 L* t7 h! H! R) [
$ B, s6 [1 j4 h; i; _3 N: f8 O9 C
timer_header = timer_header->next;
. u7 C) L7 \/ P# v0 }) Z; r; f: Z+ k

# e/ A0 Z# ]; w(*callback_fptr)();
: @5 d; I$ n, ]2 i* Z
3 @6 D) e' y# E
}

$ k0 m3 `3 Z5 t7 `. ]
, h+ O5 f8 `- }% E4 E5 H
: V- w- ], B* A2 v+ _; k
}
7 y2 H+ [; _% M///////////////////////////////////////////////////
  t# w  H* H# b  P9 D6 m+ q5 g) E0 O$ r# f: h
7 J& u' i5 o7 ~6 N8 D! k
上述code,我已经导入并开始测试了,短短几十行代码大大改善了我的code base的感官,降低了代码的耦合度,现在看上去清爽多了J!* |$ O, n/ p( c( _! t& Y$ ]. D8 K6 Z% ]

1 L) h% K2 ]1 V; ]1 L' ^' q野人献曝,博君一笑6 z! {2 y" s, K2 d# j$ Y$ r" W6 R" n3 t
6 [6 V$ A4 H# ?, \6 l$ a, {
Peter
3 m, Z  }( v/ k- g1 S  
7 x. Z% r1 z9 A+ S5 F8 Y4 U& I; A1 T& P7 [& G
[ 本帖最后由 peterhu 于 2009-4-20 09:51 编辑 ]
您需要登录后才可以回帖 登录 | 加入计匠网

本版积分规则

Archiver|手机版|小黑屋|计匠网

GMT+8, 2025-2-19 07:16 , Processed in 0.029459 second(s), 16 queries .

Powered by Discuz! X3.5

© 2001-2023 Discuz! Team.

快速回复 返回顶部 返回列表