Subversion Repositories Kolibri OS

Rev

Rev 7984 | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. #ifndef INCLUDE_DLL_H
  2. #define INCLUDE_DLL_H
  3. #print "[include <dll.h>]\n"
  4.  
  5. #ifndef INCLUDE_FILESYSTEM_H
  6. #include "../lib/fs.h"
  7. #endif
  8.  
  9. #ifdef LANG_RUS
  10.         #define _TEXT_ERROR_ADD "'Žè¨¡ª  ¯à¨ § £à㧪¥ ¡¨¡«¨®â¥ª¨\n"
  11. #elif LANG_EST
  12.         #define _TEXT_ERROR_ADD "'Viga teegi laadimisel\n"
  13. #else
  14.         #define _TEXT_ERROR_ADD "'Error while loading library\n"
  15. #endif
  16.  
  17. char a_libdir[43]  = "/sys/lib/\0";
  18.  
  19. // stdcall with 1 parameter
  20. :void dll_Load() {
  21. asm {
  22.         push    ebp
  23.         mov     ebp, esp
  24.         mov     esi, SSDWORD[EBP+8]
  25.                 @next_lib:    
  26.         mov     edx, DSDWORD[ESI]
  27.         or      edx, edx
  28.         jz      exit
  29.         push    esi
  30.         mov     esi, DSDWORD[ESI+4]
  31.         mov     edi, #a_libdir+9
  32.  
  33. @loc01:
  34.         lodsb
  35.         stosb
  36.         or      al, al
  37.         jnz     loc01
  38.  
  39.         mov     eax, 68
  40.         mov     ebx, 19
  41.         mov     ecx, #a_libdir
  42.         int     0x40
  43.         or      eax, eax
  44.         jz      fail
  45.  
  46.         push    edx
  47.         push    eax
  48.         call    dll_Link
  49.  
  50.         push    eax
  51.         mov     eax, DSDWORD[eax]
  52.         cmp     DSDWORD[EAX], '_bil'    // somehow this needs to be reversed..
  53.         pop     eax
  54.         jnz     loc02
  55.  
  56.         push    DSDWORD[EAX+4]
  57.         call    dll_Init
  58. @loc02:
  59.  
  60.         pop     esi
  61.         add     esi, 8
  62.         jmp     next_lib
  63. @exit:
  64.         xor     eax, eax
  65.         leave
  66.         ret     4
  67.        
  68. @fail:        
  69.         add     esp, 4
  70.         xor     eax, eax
  71.         inc     eax
  72.         leave
  73.         ret     4
  74.     }
  75. }
  76.  
  77. //stdcall with 2 parameters
  78. :void dll_Link() {
  79. asm {
  80.         push    ebp
  81.         mov     ebp, esp
  82.         push    eax
  83.         mov     esi, SSDWORD[EBP+12]
  84.         test    esi, esi
  85.         jz      done
  86. @next:        
  87.         lodsd
  88.         test    eax, eax
  89.         jz      done
  90.         push    eax
  91.         push    SSDWORD[EBP+8]
  92.         call    dll_GetProcAddress
  93.         or      eax, eax
  94.         jz      loc03
  95.         mov     DSDWORD[esi-4], eax
  96.         jmp     next
  97. @loc03:
  98.         mov     SSDWORD[esp], 0
  99. @done:
  100.         pop     eax
  101.         leave
  102.         ret     8
  103.     }
  104. }
  105.  
  106.  
  107. //stdcall with 1 parameter
  108. :void dll_Init() {
  109. asm {
  110.         push    ebp
  111.         mov     ebp, esp
  112.         pushad
  113.         mov     eax, #malloc
  114.         mov     ebx, #free;
  115.         mov     ecx, #realloc;
  116.         mov     edx, #dll_Load;
  117.         call    SSDWORD[EBP+8]
  118.         popad
  119.         leave
  120.         ret     4
  121.     }
  122. }
  123.  
  124.  
  125. // stdcall with 2 parameters
  126. :void dll_GetProcAddress(){
  127. asm {
  128.         push    ebp
  129.         mov     ebp, esp
  130.         mov     edx, CSDWORD[EBP+8]
  131.         xor     eax, eax
  132.  
  133. @next:        
  134.         or      edx, edx
  135.         jz      end
  136.         cmp     CSDWORD[edx], 0
  137.         jz      end
  138.  
  139.         push    CSDWORD[EBP+12]
  140.         push    CSDWORD[EDX]
  141.         call    dll_StrCmp
  142.         test    eax, eax
  143.         jz      ok
  144.         add     edx, 8
  145.         jmp     next
  146. @ok:
  147.         mov     eax, DSDWORD[EDX+4]
  148. @end:
  149.         leave
  150.         ret     8
  151.     }
  152. }
  153.  
  154.  
  155. // stdcall with 2 parameters
  156. :void dll_StrCmp() {
  157. asm {
  158.         push    ebp
  159.         mov     ebp, esp
  160.         push    esi
  161.         push    edi
  162.         mov     esi, CSDWORD[EBP+8]
  163.         mov     edi, CSDWORD[EBP+12]
  164.         xor     eax, eax
  165. @label1:
  166.         lodsb
  167.         scasb
  168.         jne     fail
  169.         or      al, al
  170.         jnz     label1
  171.         jmp     label_ok
  172. @fail:
  173.         or      eax, -1
  174. @label_ok:
  175.         pop     edi
  176.         pop     esi
  177.         leave
  178.         ret     8
  179.     }
  180. }
  181.  
  182. :void load_dll(dword dllname, import_table, byte need_init)
  183. {
  184. // load DLL
  185.         $mov     eax, 68
  186.         $mov     ebx, 19
  187.         ECX=dllname;
  188.         $int     0x40
  189.         $test    eax, eax
  190.         $jz      exit01
  191.  
  192. // initialize import
  193.         $mov     edx,eax
  194.         ESI=import_table;
  195.  
  196. @import_loop01:
  197.         $lodsd
  198.         $test    eax,eax
  199.         $jz      import_done01
  200.         $push    edx
  201. @import_find01:
  202.         $mov     ebx,DSDWORD[EDX]
  203.         $test    ebx, ebx
  204.         $jz      exit01
  205.         $push    eax
  206. @nex101:
  207.         $mov     cl,DSBYTE[EAX];
  208.         $cmp     cl,DSBYTE[EBX];
  209.         $jnz     import_find_next01
  210.         $test    cl,cl
  211.         $jz      import_found01
  212.         $inc     eax
  213.         $inc     ebx
  214.         $jmp     nex101
  215. @import_find_next01:
  216.         $pop     eax
  217.         $add     edx, 8
  218.         $jmp     import_find01
  219. @import_found01:
  220.         $pop     eax
  221.         $mov     eax,DSDWORD[edx+4]
  222.         $mov     DSDWORD[esi-4],eax
  223.         $pop     edx
  224.        
  225.         $jmp     import_loop01
  226. @import_done01:
  227.         #ifndef NO_DLL_INIT
  228.         IF (need_init) dll_Init (DSDWORD[EDX+4]);
  229.         #endif
  230.         return;
  231. @exit01:
  232.         error_init(dllname);
  233. }
  234.  
  235. :inline void error_init(dword lirary_path)
  236. {
  237.     char error_text[1024];
  238.     strcpy(#error_text, _TEXT_ERROR_ADD);
  239.     strcat(#error_text, lirary_path);
  240.     strcat(#error_text, "' -E");
  241.     notify(#error_text);
  242. }
  243.  
  244.  
  245. #endif