dllALib.s
上传用户:nvosite88
上传日期:2007-01-17
资源大小:4983k
文件大小:7k
源码类别:

VxWorks

开发平台:

C/C++

  1. /* dllALib.s - i80x86 assembly doubly linked list manipulation */
  2. /* Copyright 1984-2001 Wind River Systems, Inc. */
  3. /*
  4. modification history
  5. --------------------
  6. 01d,22aug01,hdn  added FUNC/FUNC_LABEL, replaced .align with .balign
  7. 01c,01jun93,hdn  updated to 5.1.
  8.   - fixed #else and #endif
  9.   - changed VOID to void
  10.   - changed ASMLANGUAGE to _ASMLANGUAGE
  11.   - changed copyright notice
  12. 01b,13oct92,hdn  debugged.
  13. 01a,07apr92,hdn  written based on TRON version.
  14. */
  15. /*
  16. DESCRIPTION
  17. This subroutine library supports the creation and maintenance of a
  18. doubly linked list.  The user supplies a list descriptor (type DL_LIST)
  19. that will contain pointers to the first and last nodes in the list.
  20. The nodes in the list can be any user-defined structure, but they must reserve
  21. space for a pointer as their first element.  The forward chain is terminated
  22. with a NULL pointer.
  23. This library in conjunction with dllLib.c, and the macros defined in dllLib.h,
  24. provide a reduced version of the routines offered in lstLib(1).  For
  25. efficiency, the count field has been eliminated, and enqueueing and dequeueing
  26. functions have been hand optimized.
  27. .ne 16
  28. NON-EMPTY LIST:
  29. .CS
  30.    ---------             --------          --------
  31.    | head--------------->| next----------->| next---------
  32.    |       |             |      |          |      |      |
  33.    |       |        ------ prev |<---------- prev |      |
  34.    |       |       |     |      |          |      |      |
  35.    | tail------    |     | ...  |    ----->| ...  |      |
  36.    |-------|  |    v                 |                   v
  37.               |  -----               |                 -----
  38.               |   ---                |                  ---
  39.               |    -                 |                   -
  40.               ------------------------
  41. .CE
  42. .ne 12
  43. EMPTY LIST:
  44. .CS
  45. -----------
  46.         |  head------------------
  47.         |         |             |
  48.         |  tail----------       |
  49.         |         |     |       v
  50.         |         |   -----   -----
  51.         -----------    ---     ---
  52.                         - -
  53. .CE
  54. */
  55. #define _ASMLANGUAGE
  56. #include "vxWorks.h"
  57. #include "asm.h"
  58. .data
  59. .globl FUNC(copyright_wind_river)
  60. .long FUNC(copyright_wind_river)
  61. #ifndef PORTABLE
  62. /* internals */
  63. .globl GTEXT(dllInsert)
  64. .globl GTEXT(dllAdd)
  65. .globl GTEXT(dllRemove)
  66. .globl GTEXT(dllGet)
  67. .text
  68. .balign 16
  69. /*******************************************************************************
  70. *
  71. * dllInsert - insert node in list after specified node
  72. *
  73. * This routine inserts the specified node in the specified list.
  74. * The new node is placed following the specified 'previous' node in the list.
  75. * If the specified previous node is NULL, the node is inserted at the head
  76. * of the list.
  77. * void dllInsert (pList, pPrev, pNode)
  78. *    FAST DL_LIST *pList; /* pointer to list descriptor *
  79. *    FAST DL_NODE *pPrev; /* pointer to node after which to insert *
  80. *    FAST DL_NODE *pNode; /* pointer to node to be inserted *
  81. * INTERNAL
  82.     {
  83.     FAST DL_NODE *pNext;
  84.     if (pPrev == NULL)
  85. { /* new node is to be first in list *
  86. pNext = pList->head;
  87. pList->head = pNode;
  88. }
  89.     else
  90. { /* make prev node point fwd to new *
  91. pNext = pPrev->next;
  92. pPrev->next = pNode;
  93. }
  94.     if (pNext == NULL)
  95. pList->tail = pNode; /* new node is to be last in list *
  96.     else
  97. pNext->previous = pNode; /* make next node point back to new *
  98.     pNode->next = pNext;    /* set pointers in new node *
  99.     pNode->previous = pPrev;
  100.     }
  101. */
  102. FUNC_LABEL(dllInsert)
  103. pushl %ebx
  104. pushl %esi
  105. movl SP_ARG1+8(%esp),%eax /* pList into %eax */
  106. movl SP_ARG2+8(%esp),%edx /* pPrev into %edx */
  107. movl SP_ARG3+8(%esp),%ecx /* pNode into %ecx */
  108. movl %eax,%esi /* %esi = pList */
  109. cmpl $0,%edx
  110. je dllInsert1
  111. movl %edx,%esi /* %esi = pPrev */
  112. dllInsert1:
  113. movl (%esi),%ebx /* %ebx = (%esi)->next */
  114. movl %ecx,(%esi) /* (%esi)->next = pNode */
  115. dllInsert2:
  116. movl %eax,%esi /* %esi = pList */
  117. cmpl $0,%ebx /* (pNext == NULL)? */
  118. je dllInsert3
  119. movl %ebx,%esi /* %esi = pPrev */
  120. dllInsert3:
  121. movl %ecx,4(%esi) /* (%esi)->previous = pNode */
  122. movl %ebx,(%ecx) /* pNode->next     = pNext */
  123. movl %edx,4(%ecx) /* pNode->previous = pPrev */
  124. popl %esi
  125. popl %ebx
  126. ret
  127. /*******************************************************************************
  128. *
  129. * dllAdd - add node to end of list
  130. *
  131. * This routine adds the specified node to the end of the specified list.
  132. * void dllAdd (pList, pNode)
  133. *    DL_LIST *pList; /* pointer to list descriptor *
  134. *    DL_NODE *pNode; /* pointer to node to be added *
  135. * INTERNAL
  136.     {
  137.     dllInsert (pList, pList->tail, pNode);
  138.     }
  139. */
  140. .balign 16,0x90
  141. FUNC_LABEL(dllAdd)
  142. movl SP_ARG1(%esp),%eax /* %eax = pList */
  143. movl SP_ARG2(%esp),%ecx /* %ecx = pNode */
  144. movl 4(%eax),%edx /* %edx = pList->tail = pPrev */
  145. movl %ecx,4(%eax) /* pList->tail     = pNode */
  146. movl %edx,4(%ecx) /* pNode->previous = pPrev/NULL */
  147. movl $0,(%ecx) /* pNode->next     = NULL */
  148. cmpl $0,%edx
  149. je dllAdd1
  150. movl %ecx,(%edx) /* pPrev->next    = pNode */
  151. ret
  152. .balign 16,0x90
  153. dllAdd1:
  154. movl %ecx,(%eax) /* pList->head     = pNode */
  155. ret
  156. /*******************************************************************************
  157. *
  158. * dllRemove - remove specified node in list
  159. *
  160. * Remove the specified node in the doubly linked list.
  161. * void dllRemove (pList, pNode)
  162. *    DL_LIST *pList; /* pointer to list descriptor *
  163. *    DL_NODE *pNode; /* pointer to node to be deleted *
  164. * INTERNAL
  165.     {
  166.     if (pNode->previous == NULL)
  167. pList->head = pNode->next;
  168.     else
  169. pNode->previous->next = pNode->next;
  170.     if (pNode->next == NULL)
  171. pList->tail = pNode->previous;
  172.     else
  173. pNode->next->previous = pNode->previous;
  174.     }
  175. */
  176. .balign 16,0x90
  177. FUNC_LABEL(dllRemove)
  178. pushl %ebx
  179. pushl %esi
  180. movl SP_ARG1+8(%esp),%edx /* %edx = pList */
  181. movl SP_ARG2+8(%esp),%eax /* %eax = pNode */
  182. movl 4(%eax),%ecx /* %ecx = pNode->previous */
  183. movl %edx,%ebx /* %ebx = pList */
  184. cmpl $0,%ecx /* (pNode->previous == NULL)? */
  185. je dllRemove1
  186. movl %ecx,%ebx /* %ebx = pNode->previous */
  187. dllRemove1:
  188. movl (%eax),%esi /* (%ebx) = pNode->next */
  189. movl %esi,(%ebx)
  190. movl %edx,%ebx /* %ebx = pList */
  191. cmpl $0,%esi /* (pNode->next == NULL)? */
  192. je dllRemove2
  193. movl %esi,%ebx /* %ebx = pNode->next */
  194. dllRemove2:
  195. movl %ecx,4(%ebx) /* 4(%ebx) = pNode->previous */
  196. popl %esi
  197. popl %ebx
  198. ret
  199. /*******************************************************************************
  200. *
  201. * dllGet - get (delete and return) first node from list
  202. *
  203. * This routine gets the first node from the specified list, deletes the node
  204. * from the list, and returns a pointer to the node gotten.
  205. *
  206. * RETURNS
  207. * Pointer to the node gotten, or
  208. * NULL if the list is empty.
  209. * DL_NODE *dllGet (pList)
  210. *    FAST DL_LIST *pList; /* pointer to list from which to get node *
  211. * INTERNAL
  212.     {
  213.     FAST DL_NODE *pNode = pList->head;
  214.     if (pNode != NULL)
  215. dllRemove (pList, pNode);
  216.     return (pNode);
  217.     }
  218. */
  219. .balign 16,0x90
  220. FUNC_LABEL(dllGet)
  221. movl SP_ARG1(%esp),%edx /* %edx = pList */
  222. movl (%edx),%eax /* %eax = pList->head(is pNode) */
  223. cmpl $0,%eax /* if (%eax == NULL) we're done */
  224. je dllGet2
  225. movl (%eax),%ecx /* %ecx = pNode->next */
  226. movl %ecx,(%edx) /* (%edx) = %ecx */
  227. cmpl $0,%ecx /* (pNode->next == NULL)? */
  228. je dllGet1
  229. movl %ecx,%edx /* %edx = pNode->next */
  230. dllGet1:
  231. movl $0,4(%edx) /* 4(%edx) = NULL */
  232. dllGet2:
  233. ret
  234. #endif /* (!PORTABLE) */