Last update Oct 8, 2002
lib\sdx.lod lib\cx.obj src\dos32\cx.asm src\dos32\lib\x386.libinto the same directories and then you can develop for DOSX again.
e.g. If you want to define 'NDEBUG' only, specify only 'NDEBUG'. If in addition, you want to specify -Ab, you must write:
-Ab -DNDEBUG
The solution is to #define _WIN32_WINNT=0x0400 in order to force windows.h to include winsock2.h, not winsock.h.
"This application uses SCT3D32.DLL, which has not been correctly installed."This message is generated by SCT3D32.DLL itself (a Microsoft supplied DLL), and is produced when it is not residing in the system directory. SCT3D32.DLL is in the \dm\bin directory. Copy it to your windows system directory (which on NT is \winnt40\system32), and rename the one in \dm\bin to SCT3D32.DLL.OLD.
This is the only known DLL with this problem.
void *_x386_zero_base_ptr;You now can build a 32 bit absolute address by adding a 32bit offset to this pointer:
char *ScreenAtA000 = (char*)_x386_zero_base_ptr + 0xA0000;Note that you don't use segment:offset in this case but a linear memory address.
//----------------------------------------------------------------------- // written by Roland VARICHON for RONE Technologies 69100 FRANCE #endif #if (sizeof(int)==2) #define __INTSIZE 2 #else #define __INTSIZE 4 #endif #if (__INTSIZE==4) #include//getDS #endif //----------------------------------------------------------------------- //some definitions and declaration: #if (__INTSIZE==2) #define dword unsigned long #else #define dword unsigned int #endif #define dosptr dword //real mode far pointer: segment:offset #define dosptr_tooff(ptr) ( ((((unsigned)(ptr))>>12) & ~0xf)+(((unsigned)(ptr)) & 0xffff) ) //transform a dosptr to an offset based on 0000:0000 addresse extern "C" dosptr off_todosptr(const dword s); //transform an offset based on 0000:0000 addresse to a dosptr //see asm code below extern "C" dosptr dosptr_align(const dosptr ptr); //align a dosptr: transform it so that offset <= 0xf //see asm code below extern "C" dosptr dosptr_add(const dosptr ptr, const dword v); //add v to a dosptr, return an aligned dosptr //!! v must be >=0 //see asm code below extern "C" dosptr dosptr_seek(const dosptr ptr, const long v); //same as dosptr_add but v can be <0 //see asm code below //----------------------------------------------------------------------------- //C++ code #if (__INTSIZE==2) #define _dosptr_toptr(ptr) ( ((void*)(ptr)) ) //nop on 16 bit lare model #define _ptr_align(ptr) ( ((void*)dosptr_align((dosptr)(ptr))) ) //align a real mode far pointer: transform it so that offset <= 0xf #define _ptr_add(ptr,v) ( ((void*)dosptr_add((dosptr)(ptr),v)) ) //add an offset to a real mode far pointer, return an aligned real mode far pointer //!! v must be >=0 #define _ptr_seek(ptr,v) ( ((void*)dosptr_seek((dosptr)(ptr),v)) ) //same as _ptr_add but v can be <0 #else //__INTSIZE==4 //#include //_x386_get_abs_addresse //commented here because in a SC++ version, if included here it didn't compile, i don't know why #define DGROUP MK_FP(getDS(),0) #define _offtoptr(off) ( ((void*)(-_x386_get_abs_address(DGROUP)+off)) ) //transform an offset based on 0000:0000 addresse to a DOSX near pointer #define _dosptr_toptr(ptr) ( ((void*)(-_x386_get_abs_address(DGROUP)+dosptr_tooff(ptr))) ) //transform a real mode far pointer to a DOSX near pointer #define _ptr_align(ptr) ( ((void*)(ptr)) ) //nop in DOSX model #define _ptr_add(ptr,v) ( ((void*)(((byte*)(ptr))+((unsigned)(v)))) ) //add an offset to a pointer #define _ptr_seek(ptr,v) ( ((void*)(((byte*)(ptr))+((int)(v)))) ) //same as _ptr_add but v is int #endif //__INTSIZE==2 //----------------------------------------------------------------------------- //ASSEMBLY CODE ; you may have to rewrite the functions as i can't give ; you all the macro i wrote for assembly ;it may be enough to be understandable ;just know that all names beginning with '@' charactere are macros ;extern "C" dword dosptr_tooff(dosptr s); @CS @PROC _dosptr_tooff,<_dosptr ??s>; @enter movzx eax,WORD PTR P.??s movzx edx,WORD PTR P.??s[WORD] shl edx,4 add eax,edx IF (INTG EQ 2) shld edx,eax,16 ENDIF @leave @ENDP @ENDS ;extern "C" dosptr off_todosptr(dword s); ;// @CS @PROC _off_todosptr,<_dword ??s>; @enter mov eax,P.??s mov edx,eax shr edx,4 and _ax,0fh IF (INTG EQ 4) shl eax,16 shrd eax,edx,16 ENDIF @leave @ENDP @ENDS ;extern "C" dosptr dosptr_align(dosptr ptr); ;// @CS @PROC _dosptr_align,<_dosptr ??ptr>; @enter movzx eax,WORD PTR P.??ptr mov edx,eax shr _dx,4 add dx,WORD PTR P.??ptr[WORD] and _ax,0fh IF (INTG EQ 4) shl eax,16 shrd eax,edx,16 ENDIF @leave @ENDP @ENDS ;extern "C" dosptr dosptr_add(dosptr ptr, dword v); ;// @CS @PROC _dosptr_add,<_dosptr ??ptr, _dword ??v>; @enter movzx eax,WORD PTR P.??ptr add eax,P.??v mov edx,eax shr edx,4 add dx,WORD PTR P.??ptr[WORD] and _ax,0fh IF (INTG EQ 4) shl eax,16 shrd eax,edx,16 ENDIF @leave @ENDP @ENDS ;extern "C" dosptr dosptr_seek(dosptr ptr, long_short v); ;// @CS @PROC _dosptr_seek,<_dosptr ??ptr, _dword ??v>; @enter movzx eax,WORD PTR P.??ptr movzx edx,WORD PTR P.??ptr[WORD] shl edx,4 add eax,edx add eax,P.??v mov edx,eax shr edx,4 and _ax,0fh IF (INTG EQ 4) shl eax,16 shrd eax,edx,16 ENDIF @leave @ENDP @ENDS -----------------------------------------------
#if (sizeof(int)==4) #define _CALL_INT(intnum,regsin,regsout) int86_real(intnum,&(regsin),&(regsout)) #define _CALL_INTS(intnum,regsin,regsout,segregs) int86x_real(intnum,&(regsin),&(regsout),&(segregs)) #else #define _CALL_INT(intnum,regsin,regsout) int86(intnum,®sin,®sout) #define _CALL_INTS(intnum,regsin,regsout,segregs) int86x(intnum,&(regsin),&(regsout),&(segregs)) #endif
unsigned short _x386_convmemalloc(unsigned size); //allocate a conventional memory block //return the conventional memory segment, 0 if error //!!! allocate 4 k byte minimum !!! //!!! there is no way to deallocate this memory !!! unsigned short _x386_convmemalloc(const unsigned size) { REGS regs; regs.x.bx = (unsigned short)((size + 15) >> 4); regs.h.ah = 0x48; int86(0x21, ®s, ®s); return (regs.x.flags & _cf_) ? 0 // DOS error number is in ax : regs.x.ax; }example:
#if (sizeof(int)==4) unsigned convmemseg,dosptr; // real mode segment, pointer void* dosxptr; // DOSX pointer #define DGROUP MKFP(getDS(),0) convmemseg = (unsigned)_x386_convmemalloc(size); dosptr = convmemseg << 16; // offset = 0 dosxptr = (void*)( - _x386_get_abs_address(DGROUP) + (convmemseg << 4)); #endif
Add 'class=CODE' in the segment declaration. DOSX sets the code segment to execute only, and does not set the execution privilege bits for code segments, so it is necessary to be accurate about which segments are code and which are data.
(Thanks to Laurentiu Pancescu for tracking this down.)
sc -ms -0 -g -L/co/ma foo.cand proceeding to load CodeView in "real" DOS produces the message:
CV0104 Warning: CodeView information for 'D:\FOO.EXE' is newer than this version of CodeViewThe version of codeview is 4.01 as supplied in the MASM 6.11 package, dated from 1992. Using /cvversion:4 to the linker produces the same result, as well as using compiler option -g4. Using masm to assemble an example program and linking using Microsoft Link does work with codeview. Linking the same .obj file with optlink/cvversion:4 produces the same failure.
sc -ms -0 -g -L/co/l/i/nocv foo.exe cvpack /minimal foo.exeand cv will work.
(Thanks to Jack Jay for tracking this down.)
#include <windows.h> void main() { gethostbyname(0); }The function gethostbyname() is declared in \dm\include\win32\winsock.h, and is exported from the Windows system dLL wsock32.dll. Compiling and linking test.c produces:
E:>sc test link test,,,user32+kernel32/noi; OPTLINK (R) for Win32 Release 7.50B1 Copyright (C) Digital Mars 1989 - 2001 All Rights Reserved test.obj(test) Error 42: Symbol Undefined _gethostbyname@4 --- errorlevel 1 E:>If implib is run over wsock32.dll to create wsock32.lib, it still doesn't link because the name in wsock32.dll is gethostbyname, not _gethostbyname@4. The solution is to create a module definition file wsock32.def with the contents:
LIBRARY wsock32 EXETYPE NT SUBSYSTEM WINDOWS EXPORTS _gethostbyname@4 = gethostbynameThis establishes a translation from one name to the other. Add each of the exports needed. Then run implib over it with:
implib wsock32.lib wsock32.defand link with:
sc test.obj wsock32.liband it should then link successfully.
Replace the numbers with the correct resource ID defines from "resource.h".
(Thanks to Andrew Corkan for tracking this down.)
\program files\dev\dm
(note
embedded space between "program" and "files"). The solution is
to 1) use paths that don't embed spaces or 2)use the subst
command, i.e. subst z: \program files\dev
and then
refer to the files as being off of z: in the IDDE.
(Thanks to Chris Widdows and Jan Knepper for tracking this down.)
(Thanks to Laurentiu Pancescu for tracking this down.)
(Thanks to Nic Tiger.)
(Thanks to Frank Albe.)