Subversion Repositories Kolibri OS

Rev

Rev 3698 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  2. ;;                                                              ;;
  3. ;; Copyright (C) KolibriOS team 2004-2010. All rights reserved. ;;
  4. ;; Distributed under terms of the GNU General Public License    ;;
  5. ;;                                                              ;;
  6. ;;  queue.inc                                                   ;;
  7. ;;                                                              ;;
  8. ;;    Written by hidnplayr@kolibrios.org                        ;;
  9. ;;                                                              ;;
  10. ;;          GNU GENERAL PUBLIC LICENSE                          ;;
  11. ;;             Version 2, June 1991                             ;;
  12. ;;                                                              ;;
  13. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  14.  
  15. $Revision: 2305 $
  16.  
  17. ; The Queues implemented by these macros form a ring-buffer.
  18. ; The data to these queue's always looks like this:
  19. ;
  20. ; At top, you have the queue struct, wich has the size (number of currently queued packets, read and write pointers.
  21. ; This struct is followed by a number of slots wich you can read and write to using the macros.
  22. ; How these slots look like is up to you to chose, normally they should have at least a pointer to where the real data is.
  23. ; (you can see some examples below)
  24.  
  25.  
  26. struct  queue
  27.  
  28.         size           dd ?    ; number of queued packets in this queue
  29.         w_ptr          dd ?    ; current writing pointer in queue
  30.         r_ptr          dd ?    ; current reading pointer
  31.  
  32. ends
  33.  
  34. ; The following macros share these inputs:
  35.  
  36. ; ptr           = pointer to where the queue data is located
  37. ; size          = number of slots/entrys in the queue
  38. ; entry_size    = size of one slot, in bytes
  39. ; failaddr      = the address where macro will jump to when there is no data in the queue
  40.  
  41. ; additionally, add_to_queue requires you to set esi to the data wich you want to queue
  42. ; get_from_queue on the other hand will return a pointer in esi, to the entry you're interessed in
  43. ; PS: macros WILL destroy ecx and edi
  44.  
  45. macro add_to_queue ptr, size, entry_size, failaddr {
  46.  
  47.         cmp     [ptr + queue.size], size        ; Check if queue isnt full
  48.         jae     failaddr
  49.  
  50.         inc     [ptr + queue.size]              ; if not full, queue one more
  51.  
  52.         mov     edi, [ptr + queue.w_ptr]        ; Current write pointer (FIFO!)
  53.         mov     ecx, entry_size/4               ; Write the queue entry
  54.         rep     movsd                           ;
  55.  
  56.         lea     ecx, [size*entry_size+ptr+sizeof.queue]
  57.         cmp     edi, ecx                        ; entry size
  58.         jb      .no_wrap
  59.  
  60.         sub     edi, size*entry_size
  61.  
  62.   .no_wrap:
  63.         mov     [ptr + queue.w_ptr], edi
  64.  
  65. }
  66.  
  67.  
  68.  
  69. macro get_from_queue ptr, size, entry_size,  failaddr {
  70.  
  71.         cmp     [ptr + queue.size], 0           ; any packets queued?
  72.         je      failaddr
  73.  
  74.         dec     [ptr + queue.size]              ; if so, dequeue one
  75.  
  76.         mov     esi, [ptr + queue.r_ptr]
  77.         push    esi
  78.  
  79.         add     esi, entry_size
  80.  
  81.         lea     ecx, [size*entry_size+ptr+sizeof.queue]
  82.         cmp     esi, ecx                        ; entry size
  83.         jb      .no_wrap
  84.  
  85.         sub     esi, size*entry_size
  86.  
  87.   .no_wrap:
  88.         mov     dword [ptr + queue.r_ptr], esi
  89.  
  90.         pop     esi
  91.  
  92. }
  93.  
  94. macro init_queue ptr {
  95.  
  96.         mov     [ptr + queue.size] , 0
  97.         lea     edi, [ptr + sizeof.queue]
  98.         mov     [ptr + queue.w_ptr], edi
  99.         mov     [ptr + queue.r_ptr], edi
  100. }