X-Authentication-Warning: delorie.com: mailnull set sender to djgpp-workers-bounces using -f Date: Fri, 8 Feb 2002 09:17:43 -0500 Message-Id: <200202081417.g18EHhW06830@envy.delorie.com> From: DJ Delorie To: djgpp-workers AT delorie DOT com Subject: [user8201 AT usisp DOT com: ] Reply-To: djgpp-workers AT delorie DOT com ------- Start of forwarded message ------- X-Sender: user8201 AT pop DOT usisp DOT com (Unverified) Date: Thu, 07 Feb 2002 20:26:20 -0800 To: dj AT delorie DOT com From: Willow Schlanger Subject: Content-Type: text/plain; charset="us-ascii"; format=flowed Hi! I recently ran CWSDPMI under BOCHS, an open-source CPU emulator, and discovered a bug in CWSDPMI. The problem is in MSWITCH.ASM: test byte ptr _features,10h ;Page Size Extensions? jz short nopse db 0fh,20h,0e0h ;mov eax,cr4 or al,10h ;Enable 4Mb pages db 0fh,22h,0e0h ;mov cr4,eax nopse: The above begins on line 168 of the original MSWITCH.ASM file from csdpmi5s.zip, which I downloaded from here: http://clio.rice.edu/cwsdpmi/. I believe this is the latest version of CSDPMI because if one goes to http://www.delorie.com/djgpp/zip-picker.html and chooses "MS-DOS, OpenDOS, PC-DOS" from "Pick one of the following:" and checks "Sources for everything you download", and clciks "Tell me which files I need", then csdpmi5s.zip is referenced. _features contains the EDX value returned after CPUID has been executed with an argument of 1. As you can see, CWSDPMI thinks bit 4 of the EDX that is output by CPUID with an argument of 1 indicates whether or not the Page Size Extension (PSE) feature is available. This is not correct. Consult the Intel documentation and you will see that, in fact, bit 4 indicates whether or not the Time Stamp Counter (TSC) feature is available. The bit that indicates whether or not the PSE is available, is bit 3. Thus the above snippet should read: test byte ptr _features,08h ;Page Size Extensions? jz short nopse db 0fh,20h,0e0h ;mov eax,cr4 or al,10h ;Enable 4Mb pages db 0fh,22h,0e0h ;mov cr4,eax nopse: I suspect the problem occurred in the following way: someone probably tried to convert 2 to the power of 3 to hex and wrongly thought it was 10h rather than 08h. To avoid similiar mistakes int the future, try this: 00001000b. With that one can easilly verify that it is bit 3 being set. Or do this, if TASM support it: (1 shl 3). I'm pretty sure TASM do support that. Note that this is not a serious error for non-emulator users because, to my knowledge, there exists no sillicon processor that supports TSD's but doesn't support PSE's. Note that I do not know that for a fact, however, and it's a good idea to fix anyways, so that CWSDPMI can be reliably used on software CPUs. BOCHS is a highly portable x86 CPU emulator. It was originally made with 486 support, then SOME Pentium support (w/o MMX etc.) was added in. Note that adding Time Stamp Counters was probably easier for the BOCHS developers than adding 4MB paging, because as you can imagine, a TSC just requires incrementing a number each cycle, while 4MB paging requires adding a new TLB mechanism, etc. The present version of BOCHS is bochs-1.3 ; you can get it from bochs.sourceforge.net if you want, but it is not going to be very useful to you, unless you want to install DOS in it, run CWSDPMI in it, and check the log file, like I did, but it could take several hours to get accustomed to bochs... still, source code is available). The present version of BOCHS _does_ support the TSD feature, but does _not_ support PSE feature. Consequently, running CWSDPMI in the emulator results in the emulator spewing this into its log file: 00031984071i[CPU ] MOV_CdRd: ignoring write to CR4 of 0x00000010 00031984071i[CPU ] MOV_CdRd: (CR4) write of 0x00000010 not supported! There's a comment in the bochs source code file that produced that message that says this: "Only allow writes of 0 to CR4 for now. Writes to bits in CR4 should not be 1s as CPUID returns not-supported for all of these features." That is because the BOCHS CPUID instruction does not set any of the feature bits except for bit 4. This is the comment by the code that sets that bit of the features in the CPUID instruciton emulator: "implement TSC" That's why the log file gets filled with those "not supported!" messages. Note that I don't know if CWSDPMI actually _uses_ 4MB pages. I hope it doesn't. If it does than that could explain why my program is still crashing in the emulator. Do you know if it does use 4MB pages? In the mean time I'm going to make the fix I suggested above to the CWSDPMI source code, see if I can manage to assemble it somehow (I _might_ have TASM somewhere.. but it will be version 3.2 or whatever came with some old Borland product for DOS). (I'm also going to make a change to my local copy of the BOCHS source code. I'd like it to stop spewing about reads from cr4 like it also does now). I suggest you make that fix too and incorporate it in the latest version. I would appreciate it if you'd increase the default value for CWSDPMI.EXE's maximum swap file size to 1GB. With modern PC's that's quite practical; it's twice the physical RAM my PC has (512MB) while a while ago perhaps the present default of 128MB was practical. Maybe even do 2GB. I had to run CWSPARAM and change it to 1GB to keep my program from crashing. Feel free to write back, forward this to whoever you like, etc. ------- End of forwarded message -------