News:

MASM32 SDK Description, downloads and other helpful links
MASM32.com New Forum Link
masmforum WebSite

msvcrt include and library.

Started by hutch--, January 20, 2005, 09:44:49 AM

Previous topic - Next topic

hutch--

I don't personally have any code to test the include and library file for MSVCRT but the library built OK so if anyone has some time to test these it would be most appreciated. I extracted the exports from the DLL in win2k, made them all PROTO C :VARARG and then started building the library. I had to remove a number of name conflixts which I have put at the top of the include file.

[attachment deleted by admin]
Download site for MASM32      New MASM Forum
https://masm32.com          https://masm32.com/board/index.php

Vortex

#1
Hi Hutch,

Nice work :U

Here is my dll2inc tool converting DLL files to include and module definition files:


dll2inc msvcrt.dll


You get two files named msvcrt.inc and msvcrt.def
To build the import library with Pelle's librarian:


\masm32\bin\polib /OUT:msvcrt.lib \windows\system32\msvcrt.dll


msvcrt.lib with a size of 147.4 Kb on Win Xp Home Sp2

[attachment deleted by admin]

hutch--

Vortex,

Compliments, its a nice tool you have created. What we need is for you to get all of these tools up on your website so they are easily obtained by anyone who needs them.
Download site for MASM32      New MASM Forum
https://masm32.com          https://masm32.com/board/index.php

hutch--

The next question is does anyone know what the reference material for msvcrt is and how do you get at it. I suspect it will be part of Visual C which is probably a copyright problem but there are over 700 functions that appear usable in it so if there is an easy way to do the reference material, it would make this scale of functionality easily available to a large number of people.
Download site for MASM32      New MASM Forum
https://masm32.com          https://masm32.com/board/index.php

Vortex

Hi Hutch,

What I found in MSDN:

Run-Time Library Reference

http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vclib/html/vcrefruntimelibraryreference.asp

An alternate for msvcrt.dll is crtdll.dll An example, the compiler Lcc-Win32 uses crtdll

MazeGen

It would be very nice to use msvcrt in MASM!

But there can be some problems with the "fake" prototypes (I mean, all are :VARARG) in my project. I would like to get the real ones, but they are scattered around in many .h files.
How to collect them and make .inc file? Or what is the best method to achieve them?

BTW, I have almost no experience with C/C++.

Vortex

Hi MazeGen,

To get the real prototypes, you can convert the .h files manually:

int __cdecl printf(const char * restrict, ...);

printf PROTO C :DWORD,:VARARG

int __cdecl sprintf(char * restrict, const char * restrict, ...);

sprintf PROTO C :DWORD,:DWORD,:VARARG

int __cdecl puts(const char *);

puts PROTO C :DWORD



Pelle's free C compiler set provides all these header files and they are classified in two main groups. One group for the standard C functions and the other for Win32 API functions.

Probably, it would be interesting to code a tool automating the conversion process.

Hi Hutch,

Nowadays, I am working on my homepage. I will try to put it up at the weekend.

MazeGen

Hi Wortex,

Quote from: Vortex on January 21, 2005, 11:38:05 AM
To get the real prototypes, you can convert the .h files manually

Huh, it could be a lot of work - more than 700 functions...

Quote from: VortexProbably, it would be interesting to code a tool automating the conversion process.

There's no sort of h2inc for such files already?

MichaelW

IIRC MSVCRT.DLL is included with all recent versions of Windows. I'm not sure about CRTDLL.DLL.

There are also the Global Constants. I have not investigated many of the constants, but I have needed RAND_MAX and errno, and IIRC I got the value of errno by calling the name as a function.

BTW, the CRT rand function is much faster than nrandom (60 vs 87 clocks on my system).


eschew obfuscation

Vortex

Hi MazeGen,

I remember there was a h2inc tool but I am not sure if it can perform a correct conversion process. Maybe, it's better to code a new version.

P1

msvcrt for XP ver 7.X, 316K, came with OS.
msvcrt for 2K ver 6.X, 281K, Updated from the OS distribution, but one did come with it. (289K)

I would hope that the differences reflect only OS implementation (KERNEL32.dll) and not functional ones.  I wish had some extra time to check up on this further.

Then we would have a simular problem with windows.inc file versioning.

Regards,  P1  :8)


MazeGen

Hi Vortex,

Quote from: Vortex on January 21, 2005, 06:30:07 PM
I remember there was a h2inc tool but I am not sure if it can perform a correct conversion process. Maybe, it's better to code a new version.

you're right, I just get last version of h2inc and it is old obsolete MS-DOS executable and can't be used in this way.
It would be nice to have new version, but my knowledge of this problematic is poor.

I realized how worth would be to use msvcrt library - a lot of very well known functions; tested miliard times; my native asm forum is almost dead, with this library I can ask questins also in C forum; etc. etc.

I'm ready to convert the prototypes manually, but I'm very busy nowadays, so it has to wait...

MichaelW

I had to comment out the following lines in MSVCRT.INC to avoid naming conflicts:

556 atol
604 isalpha
609 islower
613 isupper
673 strcat
eschew obfuscation

MichaelW

I have now done some testing of the library and include file, after making the changes noted in my last post, and everything I tested seems to work OK. I think the math routines are probably the most useful components, and to use them reasonably you must be able to monitor errors, so I tested the _matherr and errno components. I think something needs to be done about getting the necessary constants and structures together in an include file. And I think it might prevent some confusion if a system of equates were implemented that would allow the CRT functions to be named as CRT functions, say with a "crt_" prefix.

; ««««««««««««««««««««««««««««««««««««««««««««««««««««««««««

    .486                       ; create 32 bit code
    .model flat, stdcall       ; 32 bit memory model
    option casemap :none       ; case sensitive

    include \masm32\include\windows.inc
    include \masm32\include\masm32.inc
    include \masm32\include\gdi32.inc
    include \masm32\include\user32.inc
    include \masm32\include\kernel32.inc
    include \masm32\include\Comctl32.inc
    include \masm32\include\comdlg32.inc
    include \masm32\include\shell32.inc
    include \masm32\include\oleaut32.inc
    include \masm32\include\msvcrt.inc

    includelib \masm32\lib\masm32.lib
    includelib \masm32\lib\gdi32.lib
    includelib \masm32\lib\user32.lib
    includelib \masm32\lib\kernel32.lib
    includelib \masm32\lib\Comctl32.lib
    includelib \masm32\lib\comdlg32.lib
    includelib \masm32\lib\shell32.lib
    includelib \masm32\lib\oleaut32.lib
    includelib \masm32\lib\msvcrt.lib

    include \masm32\macros\macros.asm

    ; _errno returns the address of the errno variable.
    errno MACRO
        invoke _errno
        mov   eax,[eax]
        EXITM <eax>
    ENDM

    ; Did not actually test this.
    set_errno MACRO val
        push  eax
        call  _errno
        mov   DWORD PTR[eax], val
        pop   eax
    ENDM

    _matherr PROTO :DWORD

    _exception STRUCT
        extype  DWORD ?
        lpName  DWORD ?
        arg1    REAL8 ?
        arg2    REAL8 ?
        rval    REAL8 ?
    _exception ENDS
; ««««««««««««««««««««««««««««««««««««««««««««««««««««««««««
    .data
        str1        db "MY OTHER BROTHER DARRYL",0
        double      dq 0
        int_part    dq 0
        fract_part  dq 0

        except      _exception <>
    .code
; ««««««««««««««««««««««««««««««««««««««««««««««««««««««««««
start:
; ««««««««««««««««««««««««««««««««««««««««««««««««««««««««««
    invoke printf,chr$("%s",13,10), ADDR str1
    invoke _strlwr, ADDR str1
    invoke printf,chr$("%s",13,10), ADDR str1
    invoke _strrev, ADDR str1
    invoke printf,chr$("%s",13,10), ADDR str1
    invoke _strrev, ADDR str1
    invoke printf,chr$("%s",13,10), ADDR str1
    invoke _strupr, ADDR str1
    invoke printf,chr$("%s",13,10), ADDR str1
    invoke strtok, ADDR str1, chr$(" ")
    invoke printf,chr$("%s",13,10), eax
  @@:
    invoke strtok, NULL, chr$(" ")
    test  eax,eax
    jz    @F
    invoke printf,chr$("%s",13,10), eax
    jmp   @B
  @@:
    fldpi
    fstp double
    invoke modf, double, ADDR int_part
    ; Return value is left on FPU stack.
    fstp  fract_part
    invoke printf,chr$("%1.0f  %f",13,10), int_part, fract_part

    ; MASM will not correctly encode a single invoke that calls
    ; the errno macro twice, so I had to split the following.
    invoke printf, chr$("errno = %d",13,10), errno()   
    invoke printf, chr$("strerror = '%s'",13,10), FUNC(strerror, errno())

    invoke __setusermatherr, ADDR _matherr
    invoke log, FP8(-2.0)

    invoke printf, chr$("errno = %d",13,10), errno()
    invoke printf, chr$("strerror = '%s'",13,10), FUNC(strerror, errno())

    invoke _open, chr$("c:\myotherbrotherdarryl"), 0

    invoke printf, chr$("errno = %d",13,10), errno()
    invoke printf, chr$("strerror = '%s'",13,10), FUNC(strerror, errno())

    invoke printf,chr$(13,10,"Press any key to exit...")
  @@:   
    call _kbhit
    test  eax, eax
    jz    @B
    exit

_matherr proc lpExcept:DWORD
    mov   ebx, lpExcept
    ASSUME ebx:PTR _exception
    invoke printf, chr$("_matherr return:",13,10)
    invoke printf, chr$("  exception type = %d",13,10), [ebx].extype
    invoke printf, chr$("  function name = '%s'",13,10), [ebx].lpName
    invoke printf, chr$("  arg1 = %f",13,10), [ebx].arg1
    ;invoke printf, chr$("  arg2 = %f",13,10), [ebx].arg2
    invoke printf, chr$("  return value = %f",13,10), [ebx].rval
    ASSUME ebx:NOTHING
    mov   eax, 0        ; return zero so errno will be set
    ret
_matherr endp
; ««««««««««««««««««««««««««««««««««««««««««««««««««««««««««
end start

struct _exception {
  int type;       /* exception type - see below */
  char *name;     /* name of function where error occured */
  double arg1;    /* first argument to function */
  double arg2;    /* second argument (if any) to function */
  double retval;  /* value to be returned by function */
  } ;

/* Constant definitions for the exception type passed in the
_exception struct */

#define _DOMAIN     1   /* argument domain error */
#define _SING       2   /* argument singularity */
#define _OVERFLOW   3   /* overflow range error */
#define _UNDERFLOW  4   /* underflow range error */
#define _TLOSS      5   /* total loss of precision */
#define _PLOSS      6   /* partial loss of precision */

#define EDOM        33
#define ERANGE      34

#define _O_RDONLY   0x0000  /* open for reading only */
#define _O_WRONLY   0x0001  /* open for writing only */
#define _O_RDWR     0x0002  /* open for reading and writing */
#define _O_APPEND   0x0008  /* writes done at eof */

#define _O_CREAT    0x0100  /* create and open file */
#define _O_TRUNC    0x0200  /* open and truncate */
#define _O_EXCL     0x0400  /* open only if file doesn't already exist */

#define _S_IREAD    0000400         /* read permission, owner */
#define _S_IWRITE   0000200         /* write permission, owner */


MY OTHER BROTHER DARRYL
my other brother darryl
lyrrad rehtorb rehto ym
my other brother darryl
MY OTHER BROTHER DARRYL
MY
OTHER
BROTHER
DARRYL
3  0.141593
errno = 0
strerror = 'No error'
_matherr return:
  exception type = 1
  function name = 'log'
  arg1 = -2.000000
  return value = -1.#IND00
errno = 33
strerror = 'Domain error'
errno = 2
strerror = 'No such file or directory'

eschew obfuscation

pbrennick