Subversion Repositories Kolibri OS

Rev

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

  1. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  2. ;;                                                              ;;
  3. ;; Copyright (C) KolibriOS team 2004-2019. All rights reserved. ;;
  4. ;; Distributed under terms of the GNU General Public License    ;;
  5. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  6.  
  7. $Revision: 7657 $
  8.  
  9. ;
  10. ; Formatted Debug Output (FDO)
  11. ; Copyright (c) 2005-2006, mike.dld
  12. ; Created: 2005-01-29, Changed: 2006-11-10
  13. ;
  14. ; For questions and bug reports, mail to mike.dld@gmail.com
  15. ;
  16. ; Available format specifiers are: %s, %d, %u, %x (with partial width support)
  17. ;
  18.  
  19. ; to be defined:
  20. ;   __DEBUG__ equ 1
  21. ;   __DEBUG_LEVEL__ equ 5
  22.  
  23. _esp equ esp
  24.  
  25. macro put_board {
  26.         call    sys_msg_board
  27. }
  28.  
  29. macro debug_func name {
  30.  if used name
  31.   name@of@func equ name
  32. }
  33.  
  34. macro debug_beginf {
  35.  align 4
  36.  name@of@func:
  37. }
  38.  
  39. debug_endf fix end if
  40.  
  41. macro DEBUGS _sign,[_str] {
  42.  common
  43.   local tp
  44.   tp equ 0
  45.   match _arg:_num,_str \{
  46.    DEBUGS_N _sign,_num,_arg
  47.    tp equ 1
  48.   \}
  49.   match =0 _arg,tp _str \{
  50.    DEBUGS_N _sign,,_arg
  51.   \}
  52. }
  53.  
  54. macro DEBUGS_N _sign,_num,[_str] {
  55.  common
  56.         pushf
  57.         pushad
  58.   local ..str,..label,is_str
  59.   is_str = 0
  60.  forward
  61.   if _str eqtype ''
  62.    is_str = 1
  63.   end if
  64.  common
  65.   if is_str = 1
  66.         jmp     ..label
  67.    ..str db _str,0
  68.    ..label:
  69.         mov     edx, ..str
  70.   else
  71. esp equ esp+4*8+4
  72.         mov     edx, _str
  73. esp equ _esp
  74.   end if
  75.   if ~_num eq
  76.    if _num eqtype eax
  77.     if _num in <eax,ebx,ecx,edx,edi,ebp,esp>
  78.         mov     esi, _num
  79.     else if ~_num eq esi
  80.         movzx   esi, _num
  81.     end if
  82.    else if _num eqtype 0
  83.         mov     esi, _num
  84.    else
  85.     local tp
  86.     tp equ 0
  87.     match [_arg],_num \{
  88.         mov     esi, dword[_arg]
  89.      tp equ 1
  90.     \}
  91.     match =0 =dword[_arg],tp _num \{
  92.         mov     esi, dword[_arg]
  93.      tp equ 1
  94.     \}
  95.     match =0 =word[_arg],tp _num \{
  96.         movzx   esi, word[_arg]
  97.      tp equ 1
  98.     \}
  99.     match =0 =byte[_arg],tp _num \{
  100.         movzx   esi, byte[_arg]
  101.      tp equ 1
  102.     \}
  103.     match =0,tp \{
  104.      'Error: specified string width is incorrect'
  105.     \}
  106.    end if
  107.   else
  108.         mov     esi, 0x7FFFFFFF
  109.   end if
  110.         call    fdo_debug_outstr
  111.         popad
  112.         popf
  113. }
  114.  
  115. macro DEBUGD _sign,_dec {
  116.  local tp
  117.  tp equ 0
  118.  match _arg:_num,_dec \{
  119.   DEBUGD_N _sign,_num,_arg
  120.   tp equ 1
  121.  \}
  122.  match =0 _arg,tp _dec \{
  123.   DEBUGD_N _sign,,_arg
  124.  \}
  125. }
  126.  
  127. macro DEBUGD_N _sign,_num,_dec {
  128.         pushf
  129.         pushad
  130.  if (~_num eq)
  131.   if (_dec eqtype eax | _dec eqtype 0)
  132.    'Error: precision allowed only for in-memory variables'
  133.   end if
  134.   if (~_num in <1,2,4>)
  135.    if _sign
  136.     'Error: 1, 2 and 4 are only allowed for precision in %d'
  137.    else
  138.     'Error: 1, 2 and 4 are only allowed for precision in %u'
  139.    end if
  140.   end if
  141.  end if
  142.  if _dec eqtype eax
  143.   if _dec in <ebx,ecx,edx,esi,edi,ebp,esp>
  144.         mov     eax, _dec
  145.   else if ~_dec eq eax
  146.    if _sign = 1
  147.         movsx   eax, _dec
  148.    else
  149.         movzx   eax, _dec
  150.    end if
  151.   end if
  152.  else if _dec eqtype 0
  153.         mov     eax, _dec
  154.  else
  155. ;  add esp,4*8+4
  156. esp equ esp+4*8+4
  157.   if _num eq
  158.         mov     eax, dword _dec
  159.   else if _num = 1
  160.    if _sign = 1
  161.         movsx   eax, byte _dec
  162.    else
  163.         movzx   eax, byte _dec
  164.    end if
  165.   else if _num = 2
  166.    if _sign = 1
  167.         movsx   eax, word _dec
  168.    else
  169.         movzx   eax, word _dec
  170.    end if
  171.   else
  172.         mov     eax, dword _dec
  173.   end if
  174. esp equ _esp
  175. ;  sub esp,4*8+4
  176.  end if
  177.         mov     cl, _sign
  178.         call    fdo_debug_outdec
  179.         popad
  180.         popf
  181. }
  182.  
  183. macro DEBUGH _sign,_hex {
  184.  local tp
  185.  tp equ 0
  186.  match _arg:_num,_hex \{
  187.   DEBUGH_N _sign,_num,_arg
  188.   tp equ 1
  189.  \}
  190.  match =0 _arg,tp _hex \{
  191.   DEBUGH_N _sign,,_arg
  192.  \}
  193. }
  194.  
  195. macro DEBUGH_N _sign,_num,_hex {
  196.         pushf
  197.         pushad
  198.  if (~_num eq) & (~_num in <1,2,3,4,5,6,7,8>)
  199.   'Error: 1..8 are only allowed for precision in %x'
  200.  end if
  201.  if _hex eqtype eax
  202.   if _hex in <eax,ebx,ecx,edx,esi,edi,ebp,esp>
  203.    if ~_hex eq eax
  204.         mov     eax, _hex
  205.    end if
  206.         mov     edx, 8
  207.   else if _hex in <ax,bx,cx,dx,si,di,bp,sp>
  208.    if ~_hex eq ax
  209.         movzx   eax, _hex
  210.    end if
  211.    if (_num eq)
  212.         mov     edx, 4
  213.    end if
  214.   else if _hex in <al,ah,bl,bh,cl,ch,dl,dh>
  215.    if ~_hex eq al
  216.         movzx   eax, _hex
  217.    end if
  218.    if (_num eq)
  219.         mov     edx, 2
  220.    end if
  221.   end if
  222.  else if _hex eqtype 0
  223.         mov     eax, _hex
  224.  else
  225. ;  add esp,4*8+4
  226. esp equ esp+4*8+4
  227.         mov     eax, dword _hex
  228. esp equ _esp
  229. ;  sub esp,4*8+4
  230.  end if
  231.  if ~_num eq
  232.         mov     edx, _num
  233.  else
  234.   if ~_hex eqtype eax
  235.         mov     edx, 8
  236.   end if
  237.  end if
  238.         call    fdo_debug_outhex
  239.         popad
  240.         popf
  241. }
  242.  
  243. ;-----------------------------------------------------------------------------
  244.  
  245. debug_func fdo_debug_outchar
  246. debug_beginf
  247.         pushad
  248.         movzx   ecx, al
  249.         mov     ebx, 1
  250.         put_board
  251.         popad
  252.         ret
  253. debug_endf
  254.  
  255. debug_func fdo_debug_outstr
  256. debug_beginf
  257.         mov     ebx, 1
  258.   .l1:
  259.         dec     esi
  260.         js      .l2
  261.         movzx   ecx, byte[edx]
  262.         or      cl, cl
  263.         jz      .l2
  264.         put_board
  265.         inc     edx
  266.         jmp     .l1
  267.   .l2:
  268.         ret
  269. debug_endf
  270.  
  271. debug_func fdo_debug_outdec
  272. debug_beginf
  273.         or      cl, cl
  274.         jz      @f
  275.         or      eax, eax
  276.         jns     @f
  277.         neg     eax
  278.         push    eax
  279.         mov     al, '-'
  280.         call    fdo_debug_outchar
  281.         pop     eax
  282.     @@:
  283.         movi    ecx, 10
  284.         push    -'0'
  285.   .l1:
  286.         xor     edx, edx
  287.         div     ecx
  288.         push    edx
  289.         test    eax, eax
  290.         jnz     .l1
  291.   .l2:
  292.         pop     eax
  293.         add     al, '0'
  294.         jz      .l3
  295.         call    fdo_debug_outchar
  296.         jmp     .l2
  297.   .l3:
  298.         ret
  299. debug_endf
  300.  
  301. debug_func fdo_debug_outhex
  302.   __fdo_hexdigits db '0123456789ABCDEF'
  303. debug_beginf
  304.         mov     cl, dl
  305.         neg     cl
  306.         add     cl, 8
  307.         shl     cl, 2
  308.         rol     eax, cl
  309.   .l1:
  310.         rol     eax, 4
  311.         push    eax
  312.         and     eax, 0x0000000F
  313.         mov     al, [__fdo_hexdigits+eax]
  314.         call    fdo_debug_outchar
  315.         pop     eax
  316.         dec     edx
  317.         jnz     .l1
  318.         ret
  319. debug_endf
  320.  
  321. ;-----------------------------------------------------------------------------
  322.  
  323. macro DEBUGF _level,_format,[_arg] {
  324.  common
  325.  if __DEBUG__ = 1 & _level >= __DEBUG_LEVEL__
  326.   local ..f1,f2,a1,a2,c1,c2,c3,..lbl
  327.   _debug_str_ equ __debug_str_ # a1
  328.   a1 = 0
  329.   c2 = 0
  330.   c3 = 0
  331.   f2 = 0
  332.   repeat ..lbl-..f1
  333.    virtual at 0
  334.     db _format,0,0
  335.     load c1 word from %-1
  336.    end virtual
  337.    if c1 = '%s'
  338.     virtual at 0
  339.      db _format,0,0
  340.      store word 0 at %-1
  341.      load c1 from f2-c2
  342.     end virtual
  343.     if c1 <> 0
  344.      DEBUGS 0,_debug_str_+f2-c2
  345.     end if
  346.     c2 = c2 + 1
  347.     f2 = %+1
  348.     DEBUGF_HELPER S,a1,0,_arg
  349.    else if c1 = '%x'
  350.     virtual at 0
  351.      db _format,0,0
  352.      store word 0 at %-1
  353.      load c1 from f2-c2
  354.     end virtual
  355.     if c1 <> 0
  356.      DEBUGS 0,_debug_str_+f2-c2
  357.     end if
  358.     c2 = c2 + 1
  359.     f2 = %+1
  360.     DEBUGF_HELPER H,a1,0,_arg
  361.    else if c1 = '%d' | c1 = '%u'
  362.     local c4
  363.     if c1 = '%d'
  364.      c4 = 1
  365.     else
  366.      c4 = 0
  367.     end if
  368.     virtual at 0
  369.      db _format,0,0
  370.      store word 0 at %-1
  371.      load c1 from f2-c2
  372.     end virtual
  373.     if c1 <> 0
  374.      DEBUGS 0,_debug_str_+f2-c2
  375.     end if
  376.     c2 = c2 + 1
  377.     f2 = %+1
  378.     DEBUGF_HELPER D,a1,c4,_arg
  379.    else if c1 = '\n'
  380.     c3 = c3 + 1
  381.    end if
  382.   end repeat
  383.   virtual at 0
  384.    db _format,0,0
  385.    load c1 from f2-c2
  386.   end virtual
  387.   if (c1<>0)&(f2<>..lbl-..f1-1)
  388.    DEBUGS 0,_debug_str_+f2-c2
  389.   end if
  390.   virtual at 0
  391.    ..f1 db _format,0
  392.    ..lbl:
  393.    __debug_strings equ __debug_strings,_debug_str_,<_format>,..lbl-..f1-1-c2-c3
  394.   end virtual
  395.  end if
  396. }
  397.  
  398. macro DEBUGFG _level, _group, _format, [_arg] {
  399.  common
  400.   if _group eqtype
  401.    DEBUGF _level, _format,_arg
  402.   else
  403.    if _level >= _group
  404.     DEBUGF 999, _format,_arg
  405.    end if
  406.   end if
  407. }
  408.  
  409. macro __include_debug_strings dummy,[_id,_fmt,_len] {
  410.  common
  411.   local c1,a1,a2
  412.  forward
  413.   if defined _len & ~_len eq
  414.    _id:
  415.    a1 = 0
  416.    a2 = 0
  417.    repeat _len
  418.     virtual at 0
  419.      db _fmt,0,0
  420.      load c1 word from %+a2-1
  421.     end virtual
  422.     if (c1='%s')|(c1='%x')|(c1='%d')|(c1='%u')
  423.      db 0
  424.      a2 = a2 + 1
  425.     else if (c1='\n')
  426.      dw $0A0D
  427.      a1 = a1 + 1
  428.      a2 = a2 + 1
  429.     else
  430.      db c1 and 0x0FF
  431.     end if
  432.    end repeat
  433.    db 0
  434.   end if
  435. }
  436.  
  437. macro DEBUGF_HELPER _letter,_num,_sign,[_arg] {
  438.  common
  439.   local num
  440.   num = 0
  441.  forward
  442.   if num = _num
  443.    DEBUG#_letter _sign,_arg
  444.   end if
  445.   num = num+1
  446.  common
  447.   _num = _num+1
  448. }
  449.  
  450. macro include_debug_strings {
  451.  if __DEBUG__ = 1
  452.   match dbg_str,__debug_strings \{
  453.    __include_debug_strings dbg_str
  454.   \}
  455.  end if
  456. }
  457.