QQ登录

只需要一步,快速开始

 注册地址  找回密码
查看: 2837|回复: 0
打印 上一主题 下一主题

malloc(内存分配)在嵌入式下的一种实现

[复制链接]
字体大小: 正常 放大

937

主题

117

听众

3万

积分

升级  0%

  • TA的每日心情

    2020-10-25 11:55
  • 签到天数: 264 天

    [LV.8]以坛为家I

    自我介绍
    内蒙古大学计算机学院

    社区QQ达人 金点子奖 助人为乐奖 风雨历程奖

    群组2013年数学建模国赛备

    跳转到指定楼层
    1#
    发表于 2013-7-26 10:17 |只看该作者 |正序浏览
    |招呼Ta 关注Ta
    想知道malloc是如何实现的吗?这里是一个简单版本,所有的功能都在这个文件实现了。如果你对malloc的原理有兴趣,可以通过这个代码窥视一二。实际上这个实现是著名的嵌入式操作系统vxworks5.5以前的内存分配版本。这里我已经把它实现的更简单易懂了。当然我还有移植到vc++下的版本,更方便调试。有需要请留言! u1 t9 q' f* o3 ]8 N1 M. T

    2 ]9 M8 F; }) l/ o3 X* f( w8 q( D  f& s. U. k' g, `7 H7 O
    $ Y, w2 J+ N9 y& @' |1 k
    *\file
    9 p4 \! g& b; _: A& f1 X( y/ I *\brief                ; b* n4 O1 E6 e7 F$ `! _
    *\details       
    1 J) h8 E8 n$ w6 n  d/ N *" l8 L9 Z: G3 W2 A% M
    *\author        Janson7 @/ |' E; c2 y1 g1 B
    *\version        * v& w9 S( D4 a* v  W' i3 A# k, N
    *\date                04Jan12
    + r. v% r1 t4 b( c: S" g7 [ *
    9 ]( K  I, _) {9 w4 P  @4 s7 O *\warning        9 k- a) c& r2 X" {6 I
    *- }( J2 o0 g3 z
    *\history \arg        30Jan12, Janson, Create the file5 F2 g4 ~3 V4 V; D: u) Q
    *        modify from VxWorks source
    " R/ @8 c+ T, s5 R  g9 X *  Legal Declaration: it is for studying VxWorks only.5 n: {" A2 h7 [9 y2 G
    */
    / a- n2 M1 \, x! S0 w5 X# {$ b9 U#include "includes.h"
    6 F) ?  \+ z( h, o
    1 i# S9 {" x3 [" z/ y5 k/* The memParLib.h file is hear:
    : a% y3 `2 R, m* A- q1 G; Khttps://code.google.com/p/vxwork ... rivate/memPartLib.h
    0 k# m  n) i9 \6 S*// c; Y0 `& k# g$ O, J+ ?
    7 }1 u4 S) Q! E2 U2 u
    /* optional check for bad blocks */+ R- O2 h# W% `- l. Y

    5 D# `$ r' r2 \5 S1 h#define MEM_BLOCK_CHECK                        0x10% J  o2 K* v$ R% z% O8 ^* A& E& }8 M
    3 I* P$ w6 I% J* y9 d! J8 m
    /* response to errors when allocating memory */3 _' n$ d3 _5 [

    % }$ Y: d- ?  [5 n6 {4 \" U#define MEM_ALLOC_ERROR_LOG_FLAG        0x205 ^/ ?. p7 y) @, C* x, W5 w
    #define MEM_ALLOC_ERROR_SUSPEND_FLAG        0x40
    / n6 L" E1 {' y+ ^- h8 G
    , b# ]' o( w1 L/ B( O/* response to errors when freeing memory */
    ) F' [6 t# l0 p) M3 P5 s
    + x* i" B0 C. ^6 U8 @  w#define MEM_BLOCK_ERROR_LOG_FLAG        0x80" C3 y( I$ X6 ?' y4 i
    #define MEM_BLOCK_ERROR_SUSPEND_FLAG        0x100- z% b0 O3 G+ [8 D

      k0 Z! z, K7 Q$ T#define NEXT_HDR(pHdr)  ((BLOCK_HDR *) ((char *) (pHdr) + (2 * (pHdr)->nWords)))+ z6 _" m$ B; |6 A8 ^4 Q
    #define PREV_HDR(pHdr)        ((pHdr)->prevHdr)+ }' u; i5 {- i4 ?# w

    % P) u4 V. g. n% ]#define HDR_TO_BLOCK(pHdr)        ((char *) ((int) pHdr + sizeof (BLOCK_HDR)))
    ( U# i) A- _2 }6 |+ `#define BLOCK_TO_HDR(pBlock)        ((BLOCK_HDR *) ((int) pBlock - \! M1 B' D* G/ a% r8 j& [4 u) s
                                                    sizeof(BLOCK_HDR)))
    0 Q: ~) W2 s. f6 g
    8 V1 m7 s+ s" ~8 S6 v#define HDR_TO_NODE(pHdr)        (& ((FREE_BLOCK *) pHdr)->node)! H. T9 N; C  ~7 c" I" E
    #define NODE_TO_HDR(pNode)        ((BLOCK_HDR *) ((int) pNode - \4 H3 Z! O+ q; F/ J5 v
                                                    OFFSET (FREE_BLOCK, node)))
    . D' T* A  V. u: p7 {
    . K& C3 P7 n" P- zstatic BOOL memPartLibInstalled = FALSE;
    2 n9 N' u. Q! K5 Q
    + y- a) ?6 q; m$ j0 Q4 bstatic OBJ_CLASS memPartClass;+ g' ^. @5 b0 j- a5 u1 {. L  x: i
    CLASS_ID memPartClassId = &memPartClass;# I( C* m) t" D0 U( j, T$ k. w
    7 J* x9 t( b" O: d0 Q
    static PARTITION memSysPartition;
    % t+ q# u2 O: x0 B: QPART_ID memSysPartId = &memSysPartition;1 E1 i: p+ |+ f+ k# s
    U32 memDefaultAlign = _ALLOC_ALIGN_SIZE;
    " H! {- Q2 P  Z/ ~5 c# B! ?
    ! B- h& {/ F7 q: H" j! V5 G4 Astatic SEMAPHORE semMemSysPartition;
    ' O/ D' G2 J6 O( I
      Q+ ^7 S; O+ rstatic void memPartSemInit(PART_ID partId);
      ?; N4 D/ h/ W$ i, ~& e% Z+ ^* U  s  x" @/ ~0 b6 z0 ?; s
    FUNCTION  memPartSemInitRtn        = (FUNCTION) memPartSemInit;
    $ f# D8 x2 O# ]6 g) e) ~; D: T9 A% F% s, J
    unsigned memPartDefaultOption = MEM_BLOCK_ERROR_SUSPEND_FLAG | MEM_BLOCK_CHECK;3 u0 W* }, r- h9 M1 K. S; q
    ; i" l6 y# v) Q# t: J& v
    static BOOL memPartBlockIsValid(PART_ID partId, FAST BLOCK_HDR* pHdr, BOOL isFree);1 y! `8 }0 C' [3 {* o2 w) h
    static BLOCK_HDR* memAlignedBlockSplit(PART_ID partId
      ?# k8 @# G- l2 R. ]        , FAST BLOCK_HDR* pHdr
    % j% K5 Z4 k, }( b7 ]# J        , FAST unsigned nWords: F( w, A, e9 W
            , unsigned minWords
    1 l5 \$ V& F( i0 ^        , unsigned align);
    : h& I) X) I( b6 E+ F. i
    2 @) ^' I; M' f- Q" T* Lstatic STATUS memPartAddToPool(PART_ID partId, char* pPool, unsigned poolSize);: o- |7 q+ J6 [+ _* M* w9 ]6 I4 I5 I

    & e. ?: }+ h. V  c, j2 uSTATUS memPartLibInit(char* pPool, unsigned poolSize)
    ) v$ D" s8 V# ]+ i/ h9 s{/ }' @; J2 M4 c. o+ e, W" I
            if((!memPartLibInstalled) && & x6 Q8 [; Q% g" {
                    (OK == classInit(memPartClassId, sizeof(PARTITION), OFFSET(PARTITION, objCore)
    , O! C/ y3 g$ j$ F7 B0 q                , (FUNCTION)memPartCreate, (FUNCTION)memPartInit, (FUNCTION)memPartDestroy)))6 J3 j! F6 a) m
            {  P$ s3 @$ R3 M; p+ Z& C
                    memPartInit(&memSysPartition, pPool, poolSize);
      s: [0 T4 B# j. t                memPartLibInstalled = TRUE;. w  E- r2 @# r
            }& ?$ X. q. x5 \; L8 D+ u% r/ t. i

    ; H& I* v' T% Z3 B6 [5 \: p        return ((memPartLibInstalled)? OK : ERROR);
    $ _  q) L4 ]9 t. _0 H. M/ M}
    , |/ m$ _1 [+ U- `+ f$ _) z9 Z( K& |  \# x, R
    PART_ID memPartCreate(char* pPool, unsigned poolSize)
      I, t$ e; v& J6 [) _{
    / \' f; }1 H0 l( E* H, H        PART_ID pPart = (PART_ID)objAlloc(memPartClassId);) W* W% P1 I' m$ n

    % N/ g! i3 @# I1 u        if(NULL != pPart). x' J: |/ ^  E; [5 y
            {
    * z8 u- n' v6 n; p; h  i/ u* p                memPartInit(pPart, pPool, poolSize);9 R! r: b5 y0 c! O0 {8 w0 \. B
            }' l9 y7 ?- g( o% h& p% F
    8 `; F7 O& G- Q( u7 y2 G  l. [
            return pPart;
    - }" Z2 l0 R% `$ _}: ~7 N! v# {9 _* m9 O* m% V% O" g

    % L! d9 e7 j* O0 L4 H2 ~: ovoid memPartInit(PART_ID partId, char* pPool, unsigned poolSize)  P3 C2 m9 b- p2 q' Q' Q5 \3 |: c
    {
    ) s4 {9 K8 l' h+ X1 G& [        memset((void*)partId, 0, sizeof(*partId));
    : X; d, L, K4 E3 x/ E# V- o- H8 W0 ]' ?+ A" X6 ?& p8 ~2 h) B
            partId->options = memPartDefaultOption;
    ( p$ P5 n) ~, N+ L0 r; b3 ^: [/ T  |        partId->minBlockWords = sizeof (FREE_BLOCK) >> 1;        /* word not byte */
    4 X0 L+ y+ e) ~+ B% t
    2 I# T1 ]; ]3 m& r# o* z$ Y        (* memPartSemInitRtn) (partId);
    ( }: e5 N7 @" ?% L' U/ x( q4 `9 {       
    2 t. N, U8 f0 x- |8 R" T        dllInit(&partId->freeList);
    1 ~3 E# O2 i9 l       
    9 V) S5 m$ _, x! L        objCoreInit(&partId->objCore, memPartClassId);6 S! u) ?/ n1 l3 F9 b
           
    6 o; _! T2 z, w, C: V        memPartAddToPool(partId, pPool, poolSize);
    0 d2 x$ F9 l  g; o2 h! X5 }, _}# `3 G- E7 o) \* L0 U# t

    2 a$ g7 q5 y$ Y' T" p2 }2 TSTATUS memPartDestroy(PART_ID partId)
    & h  ]0 V" y  I! G" T6 c; {{
    3 K9 ]. i  s3 K. W( ?$ Q; O! R        return (ERROR);
    # K( m, {& ^: h6 e6 H/ F}
    . |; w* B& {0 o7 O$ `. A7 L1 C$ W4 c5 H5 }5 u6 ?# l2 [+ {5 C
    void memAddToPool(FAST char *pPool, FAST unsigned poolSize)" c' N0 ?+ y1 p3 }( r0 }& f, P
    {
    : |: x% j" K4 ?9 b& t! ~    (void)memPartAddToPool(&memSysPartition, pPool, poolSize);5 }, [: c" b0 y: z
    }% G) p6 y' l; U3 C  `# `/ x

    - k( o2 T# o# |1 r4 C/ a3 Y) C! h9 h
    6 C4 j7 K2 f. A* m) lstatic STATUS memPartAddToPool(PART_ID partId, char* pPool, unsigned poolSize)
    9 T/ p% e6 Q, W- x! v1 P{0 c! d) U4 s' T& F
            BLOCK_HDR* pHdrStart;+ r& I( k4 Y/ ^3 q; B
            BLOCK_HDR* pHdrMid;, D" t; S! Q6 w. U) Y, N
            BLOCK_HDR* pHdrEnd;, r: [1 i4 }2 j# {8 P- s: @6 i
            char* tmp;% }! B4 ^8 ]; J& o6 K
            int reducePool;
    " w: F+ c2 v" d+ m& q, W5 r7 o  U1 H5 j  {
            if(!(IS_CLASS(partId, memPartClassId)))        /* only memPartClass can call this function */
    8 |+ v+ e: s$ s8 v# I/ V        {* o1 k" |0 l7 a, T% V
                    return (ERROR);
    1 a- Z3 l6 W: e        }
      Z' t/ n9 l8 N  D+ ^% E6 v% h1 |1 k
            tmp = (char*) MEM_ROUND_UP(pPool);  c# H1 y' Y; x: q& W& [3 I3 u
            reducePool = tmp - pPool;
    9 _1 u+ d' n1 O/ x2 {' t, p5 K- {+ l( l- k/ [3 E- v2 `
            /* adjust the lenght */
    6 {2 S+ p: l( m' J. P        if(poolSize >= reducePool)
    * R2 ]3 o( G  o; S* B        {
    ! ^. i" T/ B8 p2 z, _                poolSize -= reducePool;
    9 `7 G# I$ i: H! H! L8 s0 K' Q) b) p        }4 f& n2 I' ^7 B( C
            else
    1 A, C  ]& G0 r" s        {9 n5 s2 A" z! n- ~' T
                    poolSize = 0;
    7 q( |: M/ {" N5 T8 _) K5 t) o        }: c8 B: i' N: G& y! `0 \
            pPool = tmp;
    1 |" \" j( ?. b/ c( D/ ?       
    . h. t+ T2 U5 F( ]: q        poolSize = MEM_ROUND_DOWN(poolSize);$ M: ~" [& g+ u
           
    ; _9 K$ K+ X& \$ Z: R3 \, F        /* at least one valid free block and three header blocks */
    7 @, f) C& s1 U! w! x        if((sizeof(BLOCK_HDR)*3 + (partId->minBlockWords*2)) > poolSize)
    4 }, A( A1 ?% @        {' q5 l- Q* o4 o0 t+ q; ]1 i: d5 S
                    return (ERROR);' s+ p. W6 G3 e* L
            }
    & g' }: f" {/ P7 u% f) u5 Y
    0 ^/ P) o+ P& \& l$ W        /* initialize three blocks */
    * a6 @1 P' ~- R9 T; M. u        pHdrStart = (BLOCK_HDR*)pPool;
    3 d  u8 r5 D$ S( [) P5 d        pHdrStart->prevHdr = NULL;
    1 z, {; f$ ~0 `        pHdrStart->free = FALSE;                /* never in use */$ O; l1 k0 L; i2 T- N% |
            pHdrStart->nWords = sizeof(BLOCK_HDR) >> 1;
    ' q/ Z& f( E* J9 O/ |, ?7 z+ `7 s2 h$ T# o+ L
            pHdrMid = NEXT_HDR(pHdrStart);
    4 P  [% o  J% U$ X6 k; U# V5 {! q        pHdrMid->prevHdr = pHdrStart;
    1 l+ R7 O5 h, k& ^1 B        pHdrMid->free = TRUE;                        /* the main block */
    * |: P1 X: D" t3 Q* X2 \# [        pHdrMid->nWords = (poolSize - 2*sizeof(BLOCK_HDR)) >> 1;, q2 A) Z* X  L* d% ^; s, L8 v

    , R- P3 k$ U# f: ^' P& [2 Z% }, h        pHdrEnd = NEXT_HDR(pHdrMid);
    - y/ @; O# x+ K" i: d5 b        pHdrEnd->prevHdr = pHdrMid;
    : W( b/ s. p! O2 u# x6 a# A3 B0 M1 ^        pHdrEnd->free = FALSE;# a* L* j1 y! W) v% c  ~' a# K
            pHdrEnd->nWords = sizeof (BLOCK_HDR) >> 1;
    ' V6 `0 G  [4 }( d9 s% Y( ^& r6 G3 t. [7 x% [5 a# e7 T
            /* TODO take sem hear */! |- c! y: N! |% B; F/ N% n
            semTake(partId->semPartId, WAIT_FOREVER);5 L" C, r6 y' h5 T' G) L
            * k2 x9 U/ ^: `, F$ J8 v
            dllInsert(&partId->freeList, (DL_NODE*)NULL, HDR_TO_NODE(pHdrMid));
    3 B! H" m" H* |9 @# f- O        partId->totalWords += (poolSize >> 1);
    & j4 D: R: X4 o0 q' L3 [3 ^" v$ J& W! S; D. ~& y
            /* TODO give sem hear */! \! W' ]! ]0 j4 Z( P2 y
            semGive(partId->semPartId);
    ! f5 V; o1 p( j2 W" g4 r0 R& C/ H+ n& \8 h" f
    7 r; P8 L8 v% }% \
            return (OK);0 ^5 B3 W5 s- N9 v8 c
    }5 f8 U" Y7 }% E% q
    - o3 G" c4 C2 P& ?$ O; p7 M" q
    void* memPartAllignedAlloc(FAST PART_ID partId, unsigned nBytes, unsigned align)
    : v# t7 `* n2 @# F; q& m  `{# t) D; W% Y4 D8 r3 m
            FAST unsigned nWords;
    ) N' w6 U9 V3 V- n; q4 p, ]        FAST unsigned nWordsExtra;
    1 l  Q, s1 e1 R        FAST DL_NODE* pNode;
    6 x! `4 Z7 j! E9 ?! j! x& K. R        FAST BLOCK_HDR* pHdr;
    3 V4 Q3 O* p  f2 z* _/ t8 ~        BLOCK_HDR* pNewHdr;; @  x% k- w1 T! G
            BLOCK_HDR* origpHdr;6 Z  B/ I% _6 G2 O

    5 [& s' n. u" O! ]2 f7 K0 e        if(!(IS_CLASS(partId, memPartClassId)))        /* only memPartClass can call this function */! _* Q/ e4 U8 Q# T  D0 r
            {( b  {0 c5 _$ [- s8 Q6 K9 @
                    return (NULL);
      }: A) {+ ~" U$ J4 ]) @- d$ I) H2 a        }
    1 m2 l+ i4 v0 j# _2 x3 W% D* x, i7 }0 E5 s1 p$ C
            nWords = (MEM_ROUND_UP(nBytes)+sizeof(BLOCK_HDR)) >>1;
    6 v& ]4 T5 Q8 B% f/ \" S- o" O! X* _* M, e2 Q
            if((nWords<<1) < nBytes)
    * q9 w  c. o. c        {
    $ s0 o4 V' l( q8 _$ I( R3 z. {4 m9 o                /* TODO suspend the task */
      `; n6 G: m! E* X                return (NULL);
    - J) F% g: r& {8 p0 P8 I, ]        }: y- K/ N# X$ m1 D

    ' N' y2 e3 r- i$ S6 N0 h0 E        if(nWords < partId->minBlockWords)  ~; C. X  d2 k# u* ?9 q6 R1 l
            {2 s+ C4 o; q4 e7 a- a
                    nWords = partId->minBlockWords;' G, w) ]7 T3 t/ ~( o& V% X
            }
    2 a! t' u8 F& g* t5 K" d3 ]! H! k+ E" f' D# }6 I
            /* TODO task the semaphore hear */, @" M& o) y* d  O% g5 W+ l- y8 S. I
            semTake(partId->semPartId, WAIT_FOREVER);
    : \. o0 _* @- ^/ Z- J6 R3 B; I        pNode = DLL_FIRST(&partId->freeList);
    & V% X% {+ ]$ \        nWordsExtra = nWords + align/2; /* why? */
    1 _% m* Q3 ]1 |9 [3 X/ e  ^2 d6 D  B* v2 d5 a" _' m+ B
            for(;;)4 N5 ~, ^6 l6 j- h$ h  L+ ?. E
            {
    # B, @4 M% D7 N5 X2 ~3 ^, f" H( y                while(NULL != pNode)9 p; q. p' M, }' L5 J- V0 Z0 r& Y
                    {
    5 u, t7 Z" {( L  |0 z/ V# T2 v. e- `3 y                        if((NODE_TO_HDR(pNode)->nWords > nWordsExtra) ||5 D. q7 B: d( [7 u
                                    ((NODE_TO_HDR(pNode)->nWords == nWords) &&
    + }" t1 _! q4 u" n1 p) H! K- b                                (ALIGNED(HDR_TO_BLOCK(NODE_TO_HDR(pNode)), align))))/ J/ H! c7 c2 c3 i
                            {9 M& L/ `, Q$ p
                                    break;
    + s* |: G, l3 X& M% [. e                        }
    4 i/ L# {/ r( ?5 f+ R2 I* ?4 ]! V
                            pNode = DLL_NEXT(pNode);
    $ d4 `: ~# N. j. X9 v                }8 S; I1 R& e% U1 A$ a' E2 K# z, W
    + R9 O, c  W" S
                    if(NULL == pNode)0 }4 Z1 E2 i% u3 h. a' z
                    {6 @( Y/ L& w! l
                            /*TODO give the semaphore */
    6 L1 e: t" J  E" g7 y) Y/ t$ y                        semGive(partId->semPartId);
    ' c2 ?6 R) \1 X: [; J+ A+ \( r                        return NULL;8 S5 v2 X+ q9 j9 h$ p2 m2 W
                    }
    % V, k- {+ j* q, `) c2 {" h: v
    . q& S" i6 q: e0 K+ O+ H                pHdr = NODE_TO_HDR(pNode);
    7 k# X. Z9 P$ R+ P2 s0 |6 N                origpHdr = pHdr;+ _9 I+ _5 a/ C- ]7 R

    ( P- F8 z0 r, l# l4 x3 I& k8 T  I                pNewHdr = memAlignedBlockSplit(partId, pHdr, nWords, partId->minBlockWords, align);
    % x8 X: }" ]& t3 @, ~( W                if(NULL != pNewHdr)" b& k2 W) Z4 D3 u3 E9 `
                    {
    $ F. f  Y: p% m4 z! a1 I                        pHdr = pNewHdr;/ [+ C% e; x- G& W; _
                            break;
    0 p4 `( K, ]' R+ n$ r/ ?# _                }
    - v- @, c1 q4 Z2 W6 @; j2 F- I) H' Y+ |% V9 h
                    pNode = DLL_NEXT(pNode);
    + P: M1 w4 z; B: ?        }
      {# U! L) g' m, S( l- u" y; z: C9 g+ H" `( g
            pHdr->free = FALSE;
    . q6 q0 O( o4 N3 a        partId->allBlocksAlloc++;
    7 ], X1 y9 e7 K) \7 m& L$ A) V( Q        partId->allWordsAlloc += pHdr->nWords;  d# }, ?. r' U+ x/ V# M5 J
            partId->curBlocksAlloc++;
    ) F& {7 s* d( o+ I# I4 W9 t2 t: l        partId->curWordsAlloc += pHdr->nWords;+ M- P5 p* q" g5 ^8 w; M. z3 a

    0 p2 O% ?9 x( B2 o        /*TODO give the  semaphore hear */- Z* Y/ p; e4 N: `9 e: K9 A3 T
            semGive(partId->semPartId);. q: V9 g* c0 b  S& O! ~% I
            return (HDR_TO_BLOCK(pHdr));7 a: L6 _+ d4 P- z5 z
           
    " E: A; u/ \6 C( {}
    . V0 h5 J9 Z, l, e2 j! b( `  K: X' ?, m6 X6 {
    void* memPartAlloc(FAST PART_ID partId, unsigned bytes)" X2 ~5 B  X) E
    {
    ! U" {' e: x* L' K6 g% c# d) ~        return memPartAllignedAlloc(partId, bytes, memDefaultAlign);( t- ]. l$ p( j8 V% ^
    }+ e0 p2 y. d& u$ E: R! y

    / X# }' I: L- E0 z: ?/ h! QSTATUS memPartFree(PART_ID partId, char* pBlock)% {% Y( d. y( S/ W6 B
    {
    6 m$ \; m' b& S0 G; s! b* J+ |0 v        FAST BLOCK_HDR *pHdr;
    $ u8 v5 ]) Z2 O1 O9 E    FAST unsigned   nWords;8 D8 ~8 ^# m7 B: S3 f0 v4 S# C9 R8 c6 [4 g
        FAST BLOCK_HDR *pNextHdr;
    8 t  H, T( }2 D( r; E- b. a6 y! l+ D6 ~' H' G! H
            if(!IS_CLASS(partId, memPartClassId))
    % R( G. A; [8 }) \) L5 E        {
    5 E. a: n# F$ f+ ?9 G; v                return (ERROR);
    , U5 d% j5 I) J: p8 r        }) l- t. Q: p$ P7 c
    , ]7 v1 k! k) h# h1 T/ ?8 {
            if(NULL == pBlock)
    2 X+ y/ ]" Y2 w9 w9 \0 r" L3 w        {  d( T! ^8 |9 |
                    return (OK);
    ) M/ _& O' H' S) n$ W        }6 {" _! `$ S4 L
    ( R0 w* H; O, M
            pHdr =  BLOCK_TO_HDR(pBlock);
    , s+ I4 R9 _' ^& ~4 c) R0 Q. y$ V  Y
            semTake(partId->semPartId, WAIT_FOREVER);
    6 O5 U3 ^, q# M& a: K4 a+ D
    1 J( N9 Q+ M/ h& @% P* @% G        if((partId->options & MEM_BLOCK_CHECK)- u9 S# Y2 }! y; l
                    && !memPartBlockIsValid(partId, pHdr, FALSE))' t4 R" o9 S% x& ^3 w, C3 X
            {
    8 t6 Y/ @' P( U- Y* B                semGive(partId->semPartId);1 ]& \6 L6 w1 u  z* U
                    return (ERROR);; H' F* d1 y9 P2 q$ B, O3 Y, ~
            }% V' b# Q: R3 U" k

    2 Z# c' [" j% K( g# P- t6 j        nWords = pHdr->nWords;
    4 S1 U$ W6 h9 ?0 P  h# B        if(PREV_HDR(pHdr)->free)
    # W" q; Y/ O, H9 y        {/* the prev hdr is free and than coalesce with it *// u' P* s& p  R9 Q2 a# {3 o
                    pHdr->free = FALSE;
    4 r) H+ z9 c9 y, f                pHdr = PREV_HDR(pHdr);% c& z7 i& z" t0 a) r
                    pHdr->nWords += nWords;
    , }" v" {' a7 {5 |5 l% E- _, U1 u        }
    * k2 E+ A7 B! V        else
    8 Y  e6 e/ M# C5 K3 D: B& l% b9 U        {) c5 H; L$ ^! n8 V* }
                    pHdr->free = TRUE;
    # K- B; D, c; l( ~                dllInsert(&partId->freeList, (DL_NODE*)NULL, HDR_TO_NODE(pHdr));. N* L6 @* t  {4 a
            }
    3 u- r6 z5 N, }" W
    4 q2 }% F) v( x+ G1 K        /* check to coalesce with the next */
    ; I; K, i6 D9 B0 Q& x        pNextHdr = NEXT_HDR(pHdr);1 h3 u- S" t/ N4 K
            if(pNextHdr->free)
    ; V, ], Q+ @7 B; h. U        {2 l9 {! h: ~" {# q
                    pHdr->nWords += pNextHdr->nWords;
    ' r8 ~0 T$ R) D& _# ^                dllRemove(&partId->freeList, HDR_TO_NODE(pNextHdr));
    2 V5 z' T. z2 r6 T2 V        }
    # L9 o) o+ ]+ m; w- q- D$ J' B$ [; u1 y! L$ ?
            /* cannot use pNextHdr->prevHdr=pHdr hear */) \3 n3 s2 l8 A( a: {
            NEXT_HDR(pHdr)->prevHdr = pHdr;
    8 ^. k8 D5 k2 Y  A( ~
    % [) g. U$ O, A        partId->curBlocksAlloc--;% T4 v* k2 ^0 d4 m0 s
            partId->curWordsAlloc -= nWords;# E- d5 Q+ ~7 |, M
    - E- |/ K& b# X3 q
            /* TODO give sem hear */
    * U2 S+ l' y1 }3 f; m        semGive(partId->semPartId);
    " d- C/ _7 X: Z% H8 g* l, r       
    : Y, Y5 N' `) U% t1 X3 G2 O        return (OK);
    $ h/ T. G: N* F# j0 R# ~}: s0 q# S' [% w: F2 w6 [3 O; f2 p
    - O5 h' g4 J1 g/ H" t* C
    static BOOL memPartBlockIsValid(PART_ID partId, FAST BLOCK_HDR* pHdr, BOOL isFree)! M1 i7 g3 h) W5 r% w& f
    {) n* H) O9 Y: m" o% a3 t
            BOOL valid;7 N6 ~( A' N5 D% P; H

    ! z  m$ @: d7 R: v        TASK_LOCK();# W# C; h  t* z! i3 j
            semGive(partId->semPartId);
    2 u# g2 O4 l1 n5 u       
    , ~7 p' Z6 Z+ z" e8 l' T" e        valid = MEM_ALIGNED(pHdr)
    6 {: d5 {/ g* w7 E4 x$ I  ?        && MEM_ALIGNED(pHdr->nWords*2)
    1 |" G# N( W8 ]- R        && (pHdr->nWords < partId->totalWords)
    - _1 ^% o& g& ?, j5 Q& t        && (pHdr->free == isFree). ?+ X( i5 m" M" f
            && (pHdr == PREV_HDR(NEXT_HDR(pHdr)))' ^- X$ }; y' b- S8 y2 c5 H
            && (pHdr == NEXT_HDR(PREV_HDR(pHdr)));
    + \0 {- Q8 f! ~& d% ~       
    ' \9 U! N* {6 l6 ?, Q& y9 I        semTake(partId->semPartId, WAIT_FOREVER);
    2 F  X0 x( Y; d+ e        TASK_UNLOCK();. {3 y* |, R* U& o' A) w

    7 o# u% G8 _1 O3 [4 j, C0 z7 N% n        return valid;2 r" o% l1 d+ }4 D. m) d
    }" [" c! {& w" `* o$ T) c
    , E* g. s1 `/ N; r9 t
    static BLOCK_HDR* memAlignedBlockSplit(PART_ID partId
    6 T" V: O) O, s) y8 d* Z        , FAST BLOCK_HDR* pHdr
    9 O0 F0 m! ?9 w5 k4 u        , FAST unsigned nWords
    4 k% N3 z8 D% n2 u/ t; Y        , unsigned minWords
    % h, l! o8 Y) t/ r5 k/ j        , unsigned align)9 A/ U& d7 }+ r
    {" Q2 \7 E, z2 u* W
            FAST BLOCK_HDR *pNewHdr;
    0 l- l! B' X$ p/ L    FAST BLOCK_HDR *pNextHdr;4 {. a, N1 x+ O9 s. J
        FAST char *endOfBlock;
    / m% ^) I2 x' Z( u" d$ }% d9 \0 G2 N    FAST char *pNewBlock;
    6 {1 e2 z& L. z  L* l" g5 [    int blockSize;
    ) i( _/ M7 {; z9 Y' n" I' S# {( c4 w% _- F2 R; m% a/ u$ J
            endOfBlock = (char*)pHdr + (pHdr->nWords*2);
    0 `9 k* j$ G; H# ]* q+ x
    ! X2 ]) A9 A- F- O! C        pNewBlock = (char*)((unsigned)endOfBlock - ((nWords - sizeof(BLOCK_HDR)/2)*2));
    ( s, u; S, n  R" ?1 Q' }" f. c- C! N* c& O1 E! M
            pNewBlock = (char*)((unsigned)pNewBlock & (~(align-1)));
    : S. Q4 a( S0 R! j
    0 ~7 Y  ^; ^# r; i6 {9 n: _        pNewHdr = BLOCK_TO_HDR(pNewBlock);
    1 K  a$ A6 E0 U* D' V0 V$ E# t" o+ q2 }" m' I' E. h3 h
            blockSize = ((char*)pNewHdr - (char*)pHdr)/2;
    . u! A" C% J7 Y" B5 r7 x! W, P: @# d
            if(blockSize < minWords)& H$ g" o+ Z# q1 u) i5 ]8 B4 j
            {
    & A" b5 f# q( w; X                if(pNewHdr == pHdr)% d% B4 b: ?& n' f: V4 S
                    {& A) _0 O0 ?2 {- R: k, \
                            dllRemove(&partId->freeList, HDR_TO_NODE(pHdr));
    6 |4 q4 H- q0 R                }
    8 G4 k: {  }! ^, u" q; c                else
    $ j6 {( ?) V* X' h' k9 l                {
    " w# V  f8 M( O4 \! a                        return NULL;
    ! u1 v+ e3 X% Z$ M" i8 ?                }# O' |& e9 R, S" r) o' J5 t
            }' h* d: E* T. F9 q
            else9 }  |8 G' Q( K/ [8 S% H8 ~
            {        /* recaculate pHdr */  f" s# [. T$ l3 H& m% \1 S
                    pNewHdr->prevHdr = pHdr;$ Y8 B, b7 ~5 G6 o" T9 ?1 p0 j) E2 Q
                    pHdr->nWords = blockSize;
    # |) ~" x) V5 k# O$ Z+ X+ m! T        }
    9 h7 l" [) _7 b8 l- Y% P* U2 \8 I( u) u
            if(((U32)endOfBlock - (U32)pNewHdr - (nWords*2)) < (minWords*2))( j: c# g( m: x) @
            {
    ; q; ?2 T: I, i% M$ b                pNewHdr->nWords = (endOfBlock - pNewBlock + sizeof(BLOCK_HDR))/2;
    , V! P6 y" \1 N0 \; N" |                pNewHdr->free = TRUE;. k2 u& e; \  s+ [3 w
    7 [5 H6 ?, H; Y6 p3 J
                    NEXT_HDR(pNewHdr)->prevHdr = pNewHdr;
    ( P1 S* D0 |$ s5 N        }
    1 S. O. [, U  ^4 l        else# w8 C; t% m  [; K$ R, Q5 p
            {/* space left is enough to be a fragment on the free list then */
    1 U) U+ `3 F7 L7 d; j                pNewHdr->nWords = nWords;
    0 s) ]! Q8 A, Z+ r9 @                pNewHdr->free = TRUE;
      E* `) K( `6 \: l- ]: [' F; B/ q
    , ]9 R, T: j6 d                pNextHdr = NEXT_HDR(pNewHdr);
      Y$ M2 e3 r8 o/ u5 c; n                /* words 包括BlockHdr */
    ; r$ t# V! i% E7 d6 S2 a# ]                pNextHdr->nWords = ((U32)endOfBlock - (U32)pNextHdr) / 2;
    % g6 E+ Y! l2 H+ B                pNextHdr->prevHdr = pNewHdr;
    : H/ ~1 j$ }# ?) o9 R) _                pNextHdr->free = TRUE;
    + Y: w& i9 y% {9 J. @6 k. X" d/ Q" C8 F! H% P
                    dllAdd(&partId->freeList, HDR_TO_NODE(pNextHdr));6 _- w5 \1 z( d

    ; m" I% K9 A- l5 |/ t4 a                NEXT_HDR(pNextHdr)->prevHdr = pNewHdr;
    ; \9 j' N0 i+ h& u9 s        }
    - i/ }* D1 P2 A9 Y3 A6 K
    , Z1 r! b; z# E  I2 Q" |+ b        return (pNewHdr);  i& p# i7 x" w3 s, g& [/ J) c
    }- l( W3 ]4 S- }+ T

    % E6 G- B- N2 l( p5 ^8 b- i0 o  ystatic void memPartSemInit(PART_ID partId), ~+ n' H3 X% n9 d
    {
    ( q& m+ T5 ?$ O, h        semBInit(&semMemSysPartition, SEM_Q_FIFO, SEM_FULL);
    3 F+ b6 Y" D3 v" `0 V( z6 |5 l9 m& W7 O# R, v
            partId->semPartId = &semMemSysPartition;
    / G# O  ]* B: S/ Z# j}! u' O$ i* C+ w7 b
    1 F8 P  w( s. Y- Z
    void* malloc(unsigned bytes)
    ) R5 E0 B. w) {{# C# ?! R8 r6 U( k$ A7 \
            return memPartAlloc(memSysPartId, bytes);4 Y4 C# j) }. g( h! ~* I
    }/ K; I6 R' S8 j, X/ I3 N6 A' p

    % y' [+ ~1 J1 qvoid free(void* p)
    * [/ t' r  h/ s+ Z; x) E! t+ P  f{, _5 k: t, l3 b
            memPartFree(memSysPartId, (char*)p);( T1 t* J4 M" i) X8 o! a& i- n
    }
    8 V: j2 G+ E4 ?7 A! k
    zan
    转播转播0 分享淘帖0 分享分享0 收藏收藏0 支持支持0 反对反对0 微信微信
    您需要登录后才可以回帖 登录 | 注册地址

    qq
    收缩
    • 电话咨询

    • 04714969085
    fastpost

    关于我们| 联系我们| 诚征英才| 对外合作| 产品服务| QQ

    手机版|Archiver| |繁體中文 手机客户端  

    蒙公网安备 15010502000194号

    Powered by Discuz! X2.5   © 2001-2013 数学建模网-数学中国 ( 蒙ICP备14002410号-3 蒙BBS备-0002号 )     论坛法律顾问:王兆丰

    GMT+8, 2026-4-16 06:40 , Processed in 0.420248 second(s), 51 queries .

    回顶部