VirtualBox

source: vbox/trunk/include/iprt/asm-watcom-x86-16.h@ 76292

Last change on this file since 76292 was 75131, checked in by vboxsync, 6 years ago

iprt/asm*.h,VMMDev.h: Watcom adjustments.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 24.2 KB
Line 
1/** @file
2 * IPRT - Assembly Functions, x86 16-bit Watcom C/C++ pragma aux.
3 */
4
5/*
6 * Copyright (C) 2006-2017 Oracle Corporation
7 *
8 * This file is part of VirtualBox Open Source Edition (OSE), as
9 * available from http://www.virtualbox.org. This file is free software;
10 * you can redistribute it and/or modify it under the terms of the GNU
11 * General Public License (GPL) as published by the Free Software
12 * Foundation, in version 2 as it comes in the "COPYING" file of the
13 * VirtualBox OSE distribution. VirtualBox OSE is distributed in the
14 * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
15 *
16 * The contents of this file may alternatively be used under the terms
17 * of the Common Development and Distribution License Version 1.0
18 * (CDDL) only, as it comes in the "COPYING.CDDL" file of the
19 * VirtualBox OSE distribution, in which case the provisions of the
20 * CDDL are applicable instead of those of the GPL.
21 *
22 * You may elect to license modified versions of this file under the
23 * terms and conditions of either the GPL or the CDDL or both.
24 */
25
26#ifndef ___iprt_asm_h
27# error "Don't include this header directly."
28#endif
29#ifndef ___iprt_asm_watcom_x86_16_h
30#define ___iprt_asm_watcom_x86_16_h
31
32
33/*
34 * Turns out we cannot use 'ds' for segment stuff here because the compiler
35 * seems to insists on loading the DGROUP segment into 'ds' before calling
36 * stuff when using -ecc. Using 'es' instead as this seems to work fine.
37 *
38 * Note! The #undef that preceds the #pragma aux statements is for undoing
39 * the mangling, because the symbol in #pragma aux [symbol] statements
40 * doesn't get subjected to preprocessing. This is also why we include
41 * the watcom header at both the top and the bottom of asm.h file.
42 */
43
44#undef ASMCompilerBarrier
45#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
46# if 0 /* overkill version. */
47# pragma aux ASMCompilerBarrier = \
48 "nop" \
49 parm [] \
50 modify exact [ax bx cx dx es ds];
51# else
52# pragma aux ASMCompilerBarrier = \
53 "" \
54 parm [] \
55 modify exact [];
56# endif
57#endif
58
59#undef ASMNopPause
60#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
61#pragma aux ASMNopPause = \
62 ".686p" \
63 ".xmm2" \
64 "pause" \
65 parm [] nomemory \
66 modify exact [] nomemory;
67#endif
68
69#undef ASMAtomicXchgU8
70#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
71#pragma aux ASMAtomicXchgU8 = \
72 "xchg es:[bx], al" \
73 parm [es bx] [al] \
74 value [al] \
75 modify exact [al];
76#endif
77
78#undef ASMAtomicXchgU16
79#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
80#pragma aux ASMAtomicXchgU16 = \
81 "xchg es:[bx], ax" \
82 parm [es bx] [ax] \
83 value [ax] \
84 modify exact [ax];
85#endif
86
87#undef ASMAtomicXchgU32
88#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
89#pragma aux ASMAtomicXchgU32 = \
90 ".386" \
91 "shl ecx, 16" \
92 "mov cx, ax" \
93 "xchg es:[bx], ecx" \
94 "mov eax, ecx" \
95 "shr ecx, 16" \
96 parm [es bx] [ax cx] \
97 value [ax cx] \
98 modify exact [ax cx];
99#endif
100
101#undef ASMAtomicXchgU64
102#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
103#pragma aux ASMAtomicXchgU64 = \
104 ".586" \
105 "shl eax, 16" \
106 "mov ax, bx" /* eax = high dword */ \
107 "shl ecx, 16" \
108 "mov cx, dx" /* ecx = low dword */ \
109 "mov ebx, ecx" /* ebx = low */ \
110 "mov ecx, eax" /* ecx = high */ \
111 "try_again:" \
112 "lock cmpxchg8b es:[si]" \
113 "jnz try_again" \
114 "xchg eax, edx" \
115 "mov ebx, eax" \
116 "shr eax, 16" \
117 "mov ecx, edx" \
118 "shr ecx, 16" \
119 parm [es si] [dx cx bx ax] \
120 value [dx cx bx ax] \
121 modify exact [dx cx bx ax];
122#endif
123
124#undef ASMAtomicCmpXchgU8
125#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
126#pragma aux ASMAtomicCmpXchgU8 = \
127 ".486" \
128 "lock cmpxchg es:[bx], cl" \
129 "setz al" \
130 parm [es bx] [cl] [al] \
131 value [al] \
132 modify exact [al];
133#endif
134
135#undef ASMAtomicCmpXchgU16
136#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
137#pragma aux ASMAtomicCmpXchgU16 = \
138 ".486" \
139 "lock cmpxchg es:[bx], cx" \
140 "setz al" \
141 parm [es bx] [cx] [ax] \
142 value [al] \
143 modify exact [ax];
144#endif
145
146#undef ASMAtomicCmpXchgU32
147#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
148#pragma aux ASMAtomicCmpXchgU32 = \
149 ".486" \
150 "shl ecx, 16" \
151 "mov cx, dx" \
152 "shl eax, 16" \
153 "mov ax, di" \
154 "rol eax, 16" \
155 "lock cmpxchg es:[bx], ecx" \
156 "setz al" \
157 parm [es bx] [cx dx] [ax di] \
158 value [al] \
159 modify exact [ax cx];
160#endif
161
162/* ASMAtomicCmpXchgU64: External assembly implementation, too few registers for parameters. */
163/* ASMAtomicCmpXchgExU32: External assembly implementation, too few registers for parameters. */
164/* ASMAtomicCmpXchgExU64: External assembly implementation, too few registers for parameters. */
165
166#undef ASMSerializeInstructionCpuId
167#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
168#pragma aux ASMSerializeInstructionCpuId = \
169 ".586" \
170 "xor eax, eax" \
171 "cpuid" \
172 parm [] \
173 modify exact [ax bx cx dx];
174#endif
175
176#undef ASMSerializeInstructionIRet
177#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
178#pragma aux ASMSerializeInstructionIRet = \
179 "pushf" \
180 "push cs" \
181 "call foo" /* 'push offset done' doesn't work */ \
182 "jmp done" \
183 "foo:" \
184 "iret" \
185 "done:" \
186 parm [] \
187 modify exact [];
188#endif
189
190#undef ASMSerializeInstructionRdTscp
191#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
192#pragma aux ASMSerializeInstructionRdTscp = \
193 0x0f 0x01 0xf9 \
194 parm [] \
195 modify exact [ax dx cx];
196#endif
197
198#undef ASMAtomicReadU64
199#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
200#pragma aux ASMAtomicReadU64 = \
201 ".586" \
202 "xor eax, eax" \
203 "xor edx, edx" \
204 "xor ebx, ebx" \
205 "xor ecx, ecx" \
206 "lock cmpxchg8b es:[si]" \
207 "xchg eax, edx" \
208 "mov ebx, eax" \
209 "shr eax, 16" \
210 "mov ecx, edx" \
211 "shr ecx, 16" \
212 parm [es si] \
213 value [dx cx bx ax] \
214 modify exact [dx cx bx ax];
215#endif
216
217#undef ASMAtomicUoReadU64
218#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
219#pragma aux ASMAtomicUoReadU64 = \
220 ".586" \
221 "xor eax, eax" \
222 "xor edx, edx" \
223 "xor ebx, ebx" \
224 "xor ecx, ecx" \
225 "lock cmpxchg8b es:[si]" \
226 "xchg eax, edx" \
227 "mov ebx, eax" \
228 "shr eax, 16" \
229 "mov ecx, edx" \
230 "shr ecx, 16" \
231 parm [es si] \
232 value [dx cx bx ax] \
233 modify exact [dx cx bx ax];
234#endif
235
236#undef ASMAtomicAddU16
237#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
238#pragma aux ASMAtomicAddU16 = \
239 ".486" \
240 "lock xadd es:[bx], ax" \
241 parm [es bx] [ax] \
242 value [ax] \
243 modify exact [ax];
244#endif
245
246#undef ASMAtomicAddU32
247#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
248#pragma aux ASMAtomicAddU32 = \
249 ".486" \
250 "shl edx, 16" \
251 "mov dx, ax" \
252 "lock xadd es:[bx], edx" \
253 "mov ax, dx" \
254 "shr edx, 16" \
255 parm [es bx] [ax dx] \
256 value [ax dx] \
257 modify exact [ax dx];
258#endif
259
260#undef ASMAtomicIncU16
261#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
262#pragma aux ASMAtomicIncU16 = \
263 ".486" \
264 "mov ax, 1" \
265 "lock xadd es:[bx], ax" \
266 "inc ax" \
267 parm [es bx] \
268 value [ax] \
269 modify exact [ax];
270#endif
271
272#undef ASMAtomicIncU32
273#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
274#pragma aux ASMAtomicIncU32 = \
275 ".486" \
276 "mov edx, 1" \
277 "lock xadd es:[bx], edx" \
278 "inc edx" \
279 "mov ax, dx" \
280 "shr edx, 16" \
281 parm [es bx] \
282 value [ax dx] \
283 modify exact [ax dx];
284#endif
285
286/* ASMAtomicIncU64: Should be done by C inline or in external file. */
287
288#undef ASMAtomicDecU16
289#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
290#pragma aux ASMAtomicDecU16 = \
291 ".486" \
292 "mov ax, 0ffffh" \
293 "lock xadd es:[bx], ax" \
294 "dec ax" \
295 parm [es bx] \
296 value [ax] \
297 modify exact [ax];
298#endif
299
300#undef ASMAtomicDecU32
301#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
302#pragma aux ASMAtomicDecU32 = \
303 ".486" \
304 "mov edx, 0ffffffffh" \
305 "lock xadd es:[bx], edx" \
306 "dec edx" \
307 "mov ax, dx" \
308 "shr edx, 16" \
309 parm [es bx] \
310 value [ax dx] \
311 modify exact [ax dx];
312#endif
313
314/* ASMAtomicDecU64: Should be done by C inline or in external file. */
315
316#undef ASMAtomicOrU32
317#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
318#pragma aux ASMAtomicOrU32 = \
319 ".386" \
320 "shl edx, 16" \
321 "mov dx, ax" \
322 "lock or es:[bx], edx" \
323 parm [es bx] [ax dx] \
324 modify exact [dx];
325#endif
326
327/* ASMAtomicOrU64: Should be done by C inline or in external file. */
328
329#undef ASMAtomicAndU32
330#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
331#pragma aux ASMAtomicAndU32 = \
332 ".386" \
333 "shl edx, 16" \
334 "mov dx, ax" \
335 "lock and es:[bx], edx" \
336 parm [es bx] [ax dx] \
337 modify exact [dx];
338#endif
339
340/* ASMAtomicAndU64: Should be done by C inline or in external file. */
341
342#undef ASMAtomicUoOrU32
343#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
344#pragma aux ASMAtomicUoOrU32 = \
345 ".386" \
346 "shl edx, 16" \
347 "mov dx, ax" \
348 "or es:[bx], edx" \
349 parm [es bx] [ax dx] \
350 modify exact [dx];
351#endif
352
353/* ASMAtomicUoOrU64: Should be done by C inline or in external file. */
354
355#undef ASMAtomicUoAndU32
356#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
357#pragma aux ASMAtomicUoAndU32 = \
358 ".386" \
359 "shl edx, 16" \
360 "mov dx, ax" \
361 "and es:[bx], edx" \
362 parm [es bx] [ax dx] \
363 modify exact [dx];
364#endif
365
366/* ASMAtomicUoAndU64: Should be done by C inline or in external file. */
367
368#undef ASMAtomicUoIncU32
369#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
370#pragma aux ASMAtomicUoIncU32 = \
371 ".486" \
372 "mov edx, 1" \
373 "xadd es:[bx], edx" \
374 "inc edx" \
375 "mov ax, dx" \
376 "shr edx, 16" \
377 parm [es bx] \
378 value [ax dx] \
379 modify exact [ax dx];
380#endif
381
382#undef ASMAtomicUoDecU32
383#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
384#pragma aux ASMAtomicUoDecU32 = \
385 ".486" \
386 "mov edx, 0ffffffffh" \
387 "xadd es:[bx], edx" \
388 "dec edx" \
389 "mov ax, dx" \
390 "shr edx, 16" \
391 parm [es bx] \
392 value [ax dx] \
393 modify exact [ax dx];
394#endif
395
396#undef ASMMemZeroPage
397#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
398# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
399# pragma aux ASMMemZeroPage = \
400 "mov cx, 2048" \
401 "xor ax, ax" \
402 "rep stosw" \
403 parm [es di] \
404 modify exact [ax cx di];
405# else
406# pragma aux ASMMemZeroPage = \
407 "mov ecx, 1024" \
408 "xor eax, eax" \
409 "rep stosd" \
410 parm [es di] \
411 modify exact [ax cx di];
412# endif
413#endif
414
415#undef ASMMemZero32
416#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
417# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
418# pragma aux ASMMemZero32 = \
419 "xor ax, ax" \
420 "shr cx, 1" \
421 "shr cx, 1" \
422 "rep stosw" \
423 parm [es di] [cx] \
424 modify exact [ax dx cx di];
425# else
426# pragma aux ASMMemZero32 = \
427 "and ecx, 0ffffh" /* probably not necessary, lazy bird should check... */ \
428 "shr ecx, 2" \
429 "xor eax, eax" \
430 "rep stosd" \
431 parm [es di] [cx] \
432 modify exact [ax cx di];
433# endif
434#endif
435
436#undef ASMMemFill32
437#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
438# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
439# pragma aux ASMMemFill32 = \
440 " shr cx, 1" \
441 " shr cx, 1" \
442 " jz done" \
443 "again:" \
444 " stosw" \
445 " xchg ax, dx" \
446 " stosw" \
447 " xchg ax, dx" \
448 " dec cx" \
449 " jnz again" \
450 "done:" \
451 parm [es di] [cx] [ax dx]\
452 modify exact [cx di];
453# else
454# pragma aux ASMMemFill32 = \
455 "and ecx, 0ffffh" /* probably not necessary, lazy bird should check... */ \
456 "shr ecx, 2" \
457 "shl eax, 16" \
458 "mov ax, dx" \
459 "rol eax, 16" \
460 "rep stosd" \
461 parm [es di] [cx] [ax dx]\
462 modify exact [ax cx di];
463# endif
464#endif
465
466#undef ASMProbeReadByte
467#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
468#pragma aux ASMProbeReadByte = \
469 "mov al, es:[bx]" \
470 parm [es bx] \
471 value [al] \
472 modify exact [al];
473#endif
474
475#undef ASMBitSet
476#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
477# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
478# pragma aux ASMBitSet = \
479 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
480 " mov cl, 5" \
481 " shl ch, cl" \
482 " add bh, ch" /* Adjust the pointer. */ \
483 " mov cl, al" \
484 " shr ax, 1" /* convert to byte offset */ \
485 " shr ax, 1" \
486 " shr ax, 1" \
487 " add bx, ax" /* adjust pointer again */\
488 " and cl, 7" \
489 " mov al, 1" \
490 " shl al, cl" /* al=bitmask */ \
491 " or es:[bx], al" \
492 parm [es bx] [ax cx] \
493 modify exact [ax bx cx];
494# else
495# pragma aux ASMBitSet = \
496 "shl edx, 16" \
497 "mov dx, ax" \
498 "bts es:[bx], edx" \
499 parm [es bx] [ax dx] \
500 modify exact [dx];
501# endif
502#endif
503
504#undef ASMAtomicBitSet
505#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
506#pragma aux ASMAtomicBitSet = \
507 ".386" \
508 "shl edx, 16" \
509 "mov dx, ax" \
510 "lock bts es:[bx], edx" \
511 parm [es bx] [ax dx] \
512 modify exact [dx];
513#endif
514
515#undef ASMBitClear
516#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
517# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
518# pragma aux ASMBitClear = \
519 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
520 " mov cl, 5" \
521 " shl ch, cl" \
522 " add bh, ch" /* Adjust the pointer. */ \
523 " mov cl, al" \
524 " shr ax, 1" /* convert to byte offset */ \
525 " shr ax, 1" \
526 " shr ax, 1" \
527 " add bx, ax" /* adjust pointer again */\
528 " and cl, 7" \
529 " mov al, 1" \
530 " shl al, cl" \
531 " not al" /* al=bitmask */ \
532 " and es:[bx], al" \
533 parm [es bx] [ax cx] \
534 modify exact [ax bx cx];
535# else
536# pragma aux ASMBitClear = \
537 "shl edx, 16" \
538 "mov dx, ax" \
539 "btr es:[bx], edx" \
540 parm [es bx] [ax dx] \
541 modify exact [dx];
542# endif
543#endif
544
545#undef ASMAtomicBitClear
546#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
547#pragma aux ASMAtomicBitClear = \
548 ".386" \
549 "shl edx, 16" \
550 "mov dx, ax" \
551 "lock btr es:[bx], edx" \
552 parm [es bx] [ax dx] \
553 modify exact [dx];
554#endif
555
556#undef ASMBitToggle
557#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
558# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
559# pragma aux ASMBitToggle = \
560 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
561 " mov cl, 5" \
562 " shl ch, cl" \
563 " add bh, ch" /* Adjust the pointer. */ \
564 " mov cl, al" \
565 " shr ax, 1" /* convert to byte offset */ \
566 " shr ax, 1" \
567 " shr ax, 1" \
568 " add bx, ax" /* adjust pointer again */\
569 " and cl, 7" \
570 " mov al, 1" \
571 " shl al, cl" /* al=bitmask */ \
572 " xor es:[bx], al" \
573 parm [es bx] [ax cx] \
574 modify exact [ax bx cx];
575# else
576# pragma aux ASMBitToggle = \
577 "shl edx, 16" \
578 "mov dx, ax" \
579 "btc es:[bx], edx" \
580 parm [es bx] [ax dx] \
581 modify exact [dx];
582# endif
583#endif
584
585#undef ASMAtomicBitToggle
586#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
587#pragma aux ASMAtomicBitToggle = \
588 ".386" \
589 "shl edx, 16" \
590 "mov dx, ax" \
591 "lock btc es:[bx], edx" \
592 parm [es bx] [ax dx] \
593 modify exact [dx];
594#endif
595
596#undef ASMBitTestAndSet
597#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
598# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
599# pragma aux ASMBitTestAndSet = \
600 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
601 " mov cl, 5" \
602 " shl ch, cl" \
603 " add bh, ch" /* Adjust the pointer. */ \
604 " mov cl, al" \
605 " shr ax, 1" /* convert to byte offset */ \
606 " shr ax, 1" \
607 " shr ax, 1" \
608 " add bx, ax" /* adjust pointer again */\
609 " and cl, 7" /* cl=byte shift count */ \
610 " mov ah, 1" \
611 " shl ah, cl" /* ah=bitmask */ \
612 " mov al, es:[bx]" \
613 " or ah, al" \
614 " mov es:[bx], ah" \
615 " shr al, cl" \
616 " and al, 1" \
617 parm [es bx] [ax cx] \
618 value [al] \
619 modify exact [ax bx cx];
620# else
621# pragma aux ASMBitTestAndSet = \
622 "shl edx, 16" \
623 "mov dx, ax" \
624 "bts es:[bx], edx" \
625 "setc al" \
626 parm [es bx] [ax dx] \
627 value [al] \
628 modify exact [ax dx];
629# endif
630#endif
631
632#undef ASMAtomicBitTestAndSet
633#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
634#pragma aux ASMAtomicBitTestAndSet = \
635 ".386" \
636 "shl edx, 16" \
637 "mov dx, ax" \
638 "lock bts es:[bx], edx" \
639 "setc al" \
640 parm [es bx] [ax dx] \
641 value [al] \
642 modify exact [ax dx];
643#endif
644
645#undef ASMBitTestAndClear
646#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
647# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
648# pragma aux ASMBitTestAndClear = \
649 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
650 " mov cl, 5" \
651 " shl ch, cl" \
652 " add bh, ch" /* Adjust the pointer. */ \
653 " mov cl, al" \
654 " shr ax, 1" /* convert to byte offset */ \
655 " shr ax, 1" \
656 " shr ax, 1" \
657 " add bx, ax" /* adjust pointer again */\
658 " and cl, 7" /* cl=byte shift count */ \
659 " mov ah, 1" \
660 " shl ah, cl" \
661 " not ah" /* ah=bitmask */ \
662 " mov al, es:[bx]" \
663 " and ah, al" \
664 " mov es:[bx], ah" \
665 " shr al, cl" \
666 " and al, 1" \
667 parm [es bx] [ax cx] \
668 value [al] \
669 modify exact [ax bx cx];
670# else
671# pragma aux ASMBitTestAndClear = \
672 "shl edx, 16" \
673 "mov dx, ax" \
674 "btr es:[bx], edx" \
675 "setc al" \
676 parm [es bx] [ax dx] \
677 value [al] \
678 modify exact [ax dx];
679# endif
680#endif
681
682#undef ASMAtomicBitTestAndClear
683#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
684#pragma aux ASMAtomicBitTestAndClear = \
685 ".386" \
686 "shl edx, 16" \
687 "mov dx, ax" \
688 "lock btr es:[bx], edx" \
689 "setc al" \
690 parm [es bx] [ax dx] \
691 value [al] \
692 modify exact [ax dx];
693#endif
694
695#undef ASMBitTestAndToggle
696#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
697# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
698# pragma aux ASMBitTestAndToggle = \
699 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
700 " mov cl, 5" \
701 " shl ch, cl" \
702 " add bh, ch" /* Adjust the pointer. */ \
703 " mov cl, al" \
704 " shr ax, 1" /* convert to byte offset */ \
705 " shr ax, 1" \
706 " shr ax, 1" \
707 " add bx, ax" /* adjust pointer again */\
708 " and cl, 7" /* cl=byte shift count */ \
709 " mov ah, 1" \
710 " shl ah, cl" /* ah=bitmask */ \
711 " mov al, es:[bx]" \
712 " xor ah, al" \
713 " mov es:[bx], ah" \
714 " shr al, cl" \
715 " and al, 1" \
716 parm [es bx] [ax cx] \
717 value [al] \
718 modify exact [ax bx cx];
719# else
720# pragma aux ASMBitTestAndToggle = \
721 "shl edx, 16" \
722 "mov dx, ax" \
723 "btc es:[bx], edx" \
724 "setc al" \
725 parm [es bx] [ax dx] \
726 value [al] \
727 modify exact [ax dx];
728# endif
729#endif
730
731#undef ASMAtomicBitTestAndToggle
732#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
733#pragma aux ASMAtomicBitTestAndToggle = \
734 ".386" \
735 "shl edx, 16" \
736 "mov dx, ax" \
737 "lock btc es:[bx], edx" \
738 "setc al" \
739 parm [es bx] [ax dx] \
740 value [al] \
741 modify exact [ax dx];
742#endif
743
744#undef ASMBitTest
745#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
746# if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
747# pragma aux ASMBitTest = \
748 " mov ch, cl" /* Only the three lowest bits are relevant due to 64KB segments */ \
749 " mov cl, 5" \
750 " shl ch, cl" \
751 " add bh, ch" /* Adjust the pointer. */ \
752 " mov cl, al" \
753 " shr ax, 1" /* convert to byte offset */ \
754 " shr ax, 1" \
755 " shr ax, 1" \
756 " add bx, ax" /* adjust pointer again */\
757 " and cl, 7" \
758 " mov al, es:[bx]" \
759 " shr al, cl" \
760 " and al, 1" \
761 parm [es bx] [ax cx] \
762 value [al] \
763 modify exact [ax bx cx];
764# else
765# pragma aux ASMBitTest = \
766 "shl edx, 16" \
767 "mov dx, ax" \
768 "bt es:[bx], edx" \
769 "setc al" \
770 parm [es bx] [ax dx] nomemory \
771 value [al] \
772 modify exact [ax dx] nomemory;
773# endif
774#endif
775
776/* ASMBitFirstClear: External file. */
777/* ASMBitNextClear: External file. */
778/* ASMBitFirstSet: External file. */
779/* ASMBitNextSet: External file. */
780
781#if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
782/* ASMBitFirstSetU32: External file. */
783#else
784# undef ASMBitFirstSetU32
785# ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
786# pragma aux ASMBitFirstSetU32 = \
787 "shl edx, 16" \
788 "mov dx, ax" \
789 "bsf eax, edx" \
790 "jz not_found" \
791 "inc ax" \
792 "jmp done" \
793 "not_found:" \
794 "xor ax, ax" \
795 "done:" \
796 parm [ax dx] nomemory \
797 value [ax] \
798 modify exact [ax dx] nomemory;
799# endif
800#endif
801
802#if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
803/* ASMBitFirstSetU64: External file. */
804#else
805# undef ASMBitFirstSetU64
806# ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
807# pragma aux ASMBitFirstSetU64 = \
808 ".386" \
809 "shl ecx, 16" \
810 "mov cx, dx" \
811 "bsf ecx, ecx" \
812 "jz not_found_low" \
813 "mov ax, cx" \
814 "inc ax" \
815 "jmp done" \
816 \
817 "not_found_low:" \
818 "shr eax, 16" \
819 "mov ax, bx" \
820 "bsf eax, eax" \
821 "jz not_found_high" \
822 "add ax, 33" \
823 "jmp done" \
824 \
825 "not_found_high:" \
826 "xor ax, ax" \
827 "done:" \
828 parm [dx cx bx ax] nomemory \
829 value [ax] \
830 modify exact [ax cx] nomemory;
831# endif
832#endif
833
834#if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
835/* ASMBitFirstSetU16: External file. */
836#else
837# undef ASMBitFirstSetU16
838# ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
839# pragma aux ASMBitFirstSetU16 = \
840 "bsf ax, ax" \
841 "jz not_found" \
842 "inc ax" \
843 "jmp done" \
844 "not_found:" \
845 "xor ax, ax" \
846 "done:" \
847 parm [ax] nomemory \
848 value [ax] \
849 modify exact [ax] nomemory;
850# endif
851#endif
852
853#if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
854/* ASMBitLastSetU32: External file. */
855#else
856# undef ASMBitLastSetU32
857# ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
858# pragma aux ASMBitLastSetU32 = \
859 "shl edx, 16" \
860 "mov dx, ax" \
861 "bsr eax, edx" \
862 "jz not_found" \
863 "inc ax" \
864 "jmp done" \
865 "not_found:" \
866 "xor ax, ax" \
867 "done:" \
868 parm [ax dx] nomemory \
869 value [ax] \
870 modify exact [ax dx] nomemory;
871# endif
872#endif
873
874#if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
875/* ASMBitLastSetU64: External file. */
876#else
877# undef ASMBitLastSetU64
878# ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
879# pragma aux ASMBitLastSetU64 = \
880 ".386" \
881 "shl ecx, 16" \
882 "mov cx, dx" \
883 "bsf ecx, ecx" \
884 "jz not_found_low" \
885 "mov ax, cx" \
886 "inc ax" \
887 "jmp done" \
888 \
889 "not_found_low:" \
890 "shr eax, 16" \
891 "mov ax, bx" \
892 "bsf eax, eax" \
893 "jz not_found_high" \
894 "add ax, 33" \
895 "jmp done" \
896 \
897 "not_found_high:" \
898 "xor ax, ax" \
899 "done:" \
900 parm [dx cx bx ax] nomemory \
901 value [ax] \
902 modify exact [ax cx] nomemory;
903# endif
904#endif
905
906#if defined(__SW_0) || defined(__SW_1) || defined(__SW_2)
907/* ASMBitLastSetU16: External file. */
908#else
909# undef ASMBitLastSetU16
910# ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
911# pragma aux ASMBitLastSetU16 = \
912 "bsr ax, ax" \
913 "jz not_found" \
914 "inc ax" \
915 "jmp done" \
916 "not_found:" \
917 "xor ax, ax" \
918 "done:" \
919 parm [ax] nomemory \
920 value [ax] \
921 modify exact [ax] nomemory;
922# endif
923#endif
924
925#undef ASMByteSwapU16
926#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
927#pragma aux ASMByteSwapU16 = \
928 "xchg al, ah" \
929 parm [ax] nomemory \
930 value [ax] \
931 modify exact [ax] nomemory;
932#endif
933
934#undef ASMByteSwapU32
935#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
936#pragma aux ASMByteSwapU32 = \
937 "xchg dh, al" \
938 "xchg dl, ah" \
939 parm [ax dx] nomemory \
940 value [ax dx] \
941 modify exact [ax dx] nomemory;
942#endif
943
944#undef ASMRotateLeftU32
945#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
946#pragma aux ASMRotateLeftU32 = \
947 ".386" \
948 "shl edx, 16" \
949 "mov dx, ax" \
950 "rol edx, cl" \
951 "mov eax, edx" \
952 "shr edx, 16" \
953 parm [ax dx] [cx] nomemory \
954 value [ax dx] \
955 modify exact [ax dx] nomemory;
956#endif
957
958#undef ASMRotateRightU32
959#ifdef IPRT_ASM_WATCOM_X86_16_WITH_PRAGMAS
960#pragma aux ASMRotateRightU32 = \
961 ".386" \
962 "shl edx, 16" \
963 "mov dx, ax" \
964 "ror edx, cl" \
965 "mov eax, edx" \
966 "shr edx, 16" \
967 parm [ax dx] [cx] nomemory \
968 value [ax dx] \
969 modify exact [ax dx] nomemory;
970#endif
971
972#endif
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette