flat assembler
Message board for the users of flat assembler.

Index > Windows > UnicoWS in FASM

Author
Thread Post new topic Reply to topic
DimonSoft



Joined: 03 Mar 2010
Posts: 1228
Location: Belarus
DimonSoft 29 Jul 2010, 19:45
Searching the message board didn't give any suitable results, so...

How can I use UnicoWS (Microsoft Layer for Unicode) in my FASM programs? What steps should be performed?

Thanks.

P.S. Please, don't ask me, why do I need older Windows versions support Wink
Post 29 Jul 2010, 19:45
View user's profile Send private message Visit poster's website Reply with quote
vid
Verbosity in development


Joined: 05 Sep 2003
Posts: 7105
Location: Slovakia
vid 29 Jul 2010, 20:06
Quote:
P.S. Please, don't ask me, why do I need older Windows versions support

damn!

O presume from "linking" point of view it is used just like any other DLL. There are plenty of examples of using DLLs in FASM.

As for interface of that DLL, it ought to be documented somewhere on MSDN or (old) Platform SDK.

In case it uses COM/OLE, it can be quite more complicated. It seems too ancient technology to provide relevant google results in a quick search. Sad
Post 29 Jul 2010, 20:06
View user's profile Send private message Visit poster's website AIM Address MSN Messenger ICQ Number Reply with quote
DimonSoft



Joined: 03 Mar 2010
Posts: 1228
Location: Belarus
DimonSoft 29 Jul 2010, 20:26
Quote:

it is used just like any other DLL

As far as I could find, the previously mentioned LIB-file contained code, which chose whether UnicoWS- or WinNT-implementation is to be used.

If I use it like any other DLL... I will have to write my own wrappers then (I hoped I won't have to)... The other way is to add UnicoWS-functions to imports, but then the application will always use UnicoWS-implementation Sad

I'm probably wrong at some point?..
Post 29 Jul 2010, 20:26
View user's profile Send private message Visit poster's website Reply with quote
vid
Verbosity in development


Joined: 05 Sep 2003
Posts: 7105
Location: Slovakia
vid 30 Jul 2010, 11:11
Quote:
If I use it like any other DLL... I will have to write my own wrappers then (I hoped I won't have to)... The other way is to add UnicoWS-functions to imports, but then the application will always use UnicoWS-implementation

If your application doesn't always use UnicoWS and you want to be able to run on systems which don't have it, then yeah, you need dynamic linking (LoadLibrary + GetProcAddress). It isn't very hard to do, and you don't need LIB for that.

If you static link it (add it to imports), then yeah, it will have to be present on every system where you want to run your app, even if you don't call it.

Another problem is how to use this library. Have you ever used this library, say, in different programming language?
Post 30 Jul 2010, 11:11
View user's profile Send private message Visit poster's website AIM Address MSN Messenger ICQ Number Reply with quote
DimonSoft



Joined: 03 Mar 2010
Posts: 1228
Location: Belarus
DimonSoft 30 Jul 2010, 12:10
AFAIK, it just exports Unicode-functions, which have the same names as their analogues in WinNT systems. So, it doesn't seem to be any more difficult to use it, if you mean the need to know, what parameters should be passed, etc.

So sad, anyway Sad
Post 30 Jul 2010, 12:10
View user's profile Send private message Visit poster's website Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20621
Location: In your JS exploiting you and your system
revolution 30 Jul 2010, 12:22
DimonSoft: What is your sadness due to?

1. Having to provide a copy of unicows.dll?
2. Having to statically link (and load) unicows.dll?
3. Having the overhead of unicows.dll for each system call in Win2K-and-up systems?

The first is probably not solvable unless you write all your own W functions and embed permanently.

The second can be solved with LoadLibrary/GetProcaddress. A one time event at app startup to rebind all W functions calls.

The third can be solved by rebinding back to the usual W windows functions dynamically at startup with LoadLibrary/GetProcaddress but in the reverse sense from the second reason above. Also a one time event at startup.
Code:
;At startup
  cmp     [WindowsHasUnicode],TRUE
    jz      .finished_rebinding
 invoke  LoadLibrary,'unicows.dll'
 invoke  GetProcaddress,eax,'MessageBoxW'
  mov     [MessageBoxW],eax
    .finished_rebinding:

;...

;Normal running
        invoke  MessageBoxW,0,0,'Hi',0

;...    
[edit] rather than the static solution I show above, you can scan the import table for any functions ending in 'W' and rebind to unicows.dll.
Post 30 Jul 2010, 12:22
View user's profile Send private message Visit poster's website Reply with quote
DimonSoft



Joined: 03 Mar 2010
Posts: 1228
Location: Belarus
DimonSoft 30 Jul 2010, 13:03
The sadness is just because of the necessity to write additional code Wink I'm already doing that. Just a little bit of work and a short delay...

Thanks everybody
Post 30 Jul 2010, 13:03
View user's profile Send private message Visit poster's website Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20621
Location: In your JS exploiting you and your system
revolution 30 Jul 2010, 13:44
I was playing:
Code:
include 'win32wx.inc'

.code

begin:
 stdcall bind_unicows
        invoke  MessageBoxW,0,'bind unicows','bind unicows',0
   invoke  ExitProcess,0

proc bind_unicows uses ebx esi edi
     stdcall query_unicode_support
       test    eax,1 shl 31
        jz      .finished_binding
   invoke  GetModuleHandleA,0
  mov     ebx,eax
     invoke  LoadLibraryA,uncows_name
    test    eax,eax
     jz      .finished_binding
   mov     esi,eax
     mov     edi,[ebx+0x3c]          ;get PE header
      mov     edi,[ebx+edi+0x80]      ;get import table
   add     edi,ebx
    .next_module:
    test    dword[edi+0xc],-1
   jz      .finished_binding
   push    edi
 mov     edi,[edi+0x0]
    .next_function:
    mov     ecx,[ebx+edi]
       test    ecx,ecx
     jz      .finished_module
    invoke  lstrlenA,addr ebx+ecx+2
     mov     ecx,[ebx+edi]
       add     eax,ebx
     cmp     byte[ecx+eax+2-1],'W'
     jnz     .finished_function
  invoke  GetProcAddress,esi,addr ebx+ecx+2
   test    eax,eax
     jz      .finished_function
  mov     edx,[esp]
   mov     ecx,[edx+0x10]
      sub     ecx,[edx+0x0]
       add     ecx,edi
     mov     [ebx+ecx],eax
    .finished_function:
        add     edi,4
       jmp     .next_function
    .finished_module:
 pop     edi
 add     edi,0x14
    jmp     .next_module
    .finished_binding:
  ret
endp

proc query_unicode_support uses esi
      invoke  GetVersion
  mov     esi,eax
     test    esi,1 shl 31
        jz      .done
       invoke  GetFileAttributesW,dummy_file_name
  cmp     eax,-1
      jnz     .done
       invoke  GetLastError
        cmp     eax,123                 ;ERROR_INVALID_NAME
 jnz     .done
       mov     esi,0x0a280105
    .done:
    mov     eax,esi
     ret
endp

.data

        align 2
     dummy_file_name:    du      '???.???',0
       uncows_name:                db      'unicows.dll',0

.end begin    
NOTE: You have to use the 'A' functions when doing the binding.
Post 30 Jul 2010, 13:44
View user's profile Send private message Visit poster's website Reply with quote
DimonSoft



Joined: 03 Mar 2010
Posts: 1228
Location: Belarus
DimonSoft 14 Nov 2012, 22:12
revolution wrote:
I was playing:
Code:
include 'win32wx.inc'

.code

begin:
  stdcall bind_unicows
        invoke  MessageBoxW,0,'bind unicows','bind unicows',0
   invoke  ExitProcess,0

proc bind_unicows uses ebx esi edi
     stdcall query_unicode_support
       test    eax,1 shl 31
        jz      .finished_binding
   invoke  GetModuleHandleA,0
  mov     ebx,eax
     invoke  LoadLibraryA,uncows_name
    test    eax,eax
     jz      .finished_binding
   mov     esi,eax
     mov     edi,[ebx+0x3c]          ;get PE header
      mov     edi,[ebx+edi+0x80]      ;get import table
   add     edi,ebx
    .next_module:
    test    dword[edi+0xc],-1
   jz      .finished_binding
   push    edi
 mov     edi,[edi+0x0]
    .next_function:
    mov     ecx,[ebx+edi]
       test    ecx,ecx
     jz      .finished_module
    invoke  lstrlenA,addr ebx+ecx+2
     mov     ecx,[ebx+edi]
       add     eax,ebx
     cmp     byte[ecx+eax+2-1],'W'
     jnz     .finished_function
  invoke  GetProcAddress,esi,addr ebx+ecx+2
   test    eax,eax
     jz      .finished_function
  mov     edx,[esp]
   mov     ecx,[edx+0x10]
      sub     ecx,[edx+0x0]
       add     ecx,edi
     mov     [ebx+ecx],eax
    .finished_function:
        add     edi,4
       jmp     .next_function
    .finished_module:
 pop     edi
 add     edi,0x14
    jmp     .next_module
    .finished_binding:
  ret
endp

proc query_unicode_support uses esi
      invoke  GetVersion
  mov     esi,eax
     test    esi,1 shl 31
        jz      .done
       invoke  GetFileAttributesW,dummy_file_name
  cmp     eax,-1
      jnz     .done
       invoke  GetLastError
        cmp     eax,123                 ;ERROR_INVALID_NAME
 jnz     .done
       mov     esi,0x0a280105
    .done:
    mov     eax,esi
     ret
endp

.data

        align 2
     dummy_file_name:    du      '???.???',0
       uncows_name:                db      'unicows.dll',0

.end begin    
NOTE: You have to use the 'A' functions when doing the binding.


I know that almost 2 years have passed, but revolution, I still can't understand two things in your code. It works great, but I just really want to understand it fully. I guess, it will also be useful for other visitors.

1. Could you, please, tell more about the trick with GetFileAttributesW: what is actually checked here? I guess, it should always return ERROR_INVALID_NAME or something like that, but Google works bad for "???.???" Sad

2. As you've mentioned, Unicode-versions of functions should not be used before either we're sure that they are available or their binding is done. But there's a call to GetFileAttributesW within query_unicode_support() procedure, for non-Win9x versions. What's the idea of that?

Thanks.
Post 14 Nov 2012, 22:12
View user's profile Send private message Visit poster's website Reply with quote
revolution
When all else fails, read the source


Joined: 24 Aug 2004
Posts: 20621
Location: In your JS exploiting you and your system
revolution 14 Nov 2012, 23:23
All the W functions are present in the system libraries but are just stubs that return -1 when unicode support is not provided. So calling GetFileAttributesW with an invalid filename will return a different value depending upon whether unicode is already supported or not,
Post 14 Nov 2012, 23:23
View user's profile Send private message Visit poster's website Reply with quote
f0dder



Joined: 19 Feb 2004
Posts: 3175
Location: Denmark
f0dder 15 Nov 2012, 00:34
Seems like you've went for another solution, but... UNICOWS.LIB contains code, not just imports for UNICOWS.DLL.

So you could simply assembly your project to COFF and add a linker to the mix - presto, done. Iirc (caveat: it's been 5+ years since I worked with it) UNICOWS.LIB does dynamic loading of the DLL, so on NT systems the DLL won't be loaded, and can be safely deleted.
Post 15 Nov 2012, 00:34
View user's profile Send private message Reply with quote
DimonSoft



Joined: 03 Mar 2010
Posts: 1228
Location: Belarus
DimonSoft 15 Nov 2012, 06:51
revolution wrote:

All the W functions are present in the system libraries but are just stubs that return -1 when unicode support is not provided. So calling GetFileAttributesW with an invalid filename will return a different value depending upon whether unicode is already supported or not,

Got it. Thanks.

f0dder wrote:
Seems like you've went for another solution, but... UNICOWS.LIB contains code, not just imports for UNICOWS.DLL.

So you could simply assembly your project to COFF and add a linker to the mix - presto, done. Iirc (caveat: it's been 5+ years since I worked with it) UNICOWS.LIB does dynamic loading of the DLL, so on NT systems the DLL won't be loaded, and can be safely deleted.

The code does nearly the same, except that you don't need any linker. As for me, it's much easier than doing the whole magic with lib-files Smile
Post 15 Nov 2012, 06:51
View user's profile Send private message Visit poster's website Reply with quote
Display posts from previous:
Post new topic Reply to topic

Jump to:  


< Last Thread | Next Thread >
Forum Rules:
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Copyright © 1999-2025, Tomasz Grysztar. Also on GitHub, YouTube.

Website powered by rwasa.