Annotation of Gnu-Mach/i386/dos/i16/i16_crt0.S, revision 1.1.1.1

1.1       root        1: /* 
                      2:  * Copyright (c) 1995-1994 The University of Utah and
                      3:  * the Computer Systems Laboratory at the University of Utah (CSL).
                      4:  * All rights reserved.
                      5:  *
                      6:  * Permission to use, copy, modify and distribute this software is hereby
                      7:  * granted provided that (1) source code retains these copyright, permission,
                      8:  * and disclaimer notices, and (2) redistributions including binaries
                      9:  * reproduce the notices in supporting documentation, and (3) all advertising
                     10:  * materials mentioning features or use of this software display the following
                     11:  * acknowledgement: ``This product includes software developed by the
                     12:  * Computer Systems Laboratory at the University of Utah.''
                     13:  *
                     14:  * THE UNIVERSITY OF UTAH AND CSL ALLOW FREE USE OF THIS SOFTWARE IN ITS "AS
                     15:  * IS" CONDITION.  THE UNIVERSITY OF UTAH AND CSL DISCLAIM ANY LIABILITY OF
                     16:  * ANY KIND FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
                     17:  *
                     18:  * CSL requests users of this software to return to [email protected] any
                     19:  * improvements that they make and grant CSL redistribution rights.
                     20:  *
                     21:  *      Author: Bryan Ford, University of Utah CSL
                     22:  */
                     23: 
                     24: #include <mach/machine/asm.h>
                     25: 
                     26: #include "config.h"
                     27: #include "i16_crt0.h"
                     28: 
                     29:        .code16
                     30:        .text
                     31: 
                     32: ENTRY(i16_entry)
                     33:        /* DOS starts us up with our stack pointer pointing
                     34:           to the very top of our BSS segment.
                     35:           ds and es point to the PSP.  */
                     36: 
                     37: #define DELAY jmp 1f; 1: jmp 1f; 1: jmp 1f; 1:
                     38: 
                     39:        /* Check to make sure we're running on a 386 or higher -
                     40:           _without_ using any 32-bit instructions of course.
                     41:           Tricky, since gas doesn't support 16-bit addressing modes. :-)
                     42:           We can't produce any 16-bit relocations either,
                     43:           because ELF doesn't support them.
                     44:           This code is basically straight out of the Pentium manual,
                     45:           except gassed of coursed.  */
                     46:        pushfw
                     47:        DELAY
                     48:        popw    %bx
                     49:        movw    $0xfff,%ax
                     50:        andw    %bx,%ax
                     51:        pushw   %ax
                     52:        DELAY
                     53:        popfw
                     54:        DELAY
                     55:        pushfw
                     56:        DELAY
                     57:        popw    %ax
                     58:        and     $0xf000,%ax
                     59:        cmpw    $0xf000,%ax
                     60: 
                     61:        je      1f
                     62:        orw     $0xf000,%bx
                     63:        pushw   %bx
                     64:        DELAY
                     65:        popfw
                     66:        DELAY
                     67:        pushfw
                     68:        DELAY
                     69:        popw    %ax
                     70:        andw    $0xf000,%ax
                     71:        jnz     4f
                     72: 1:
                     73:        /* Gak!  We're running on an 8086/8088/80286!  */
                     74:        callw   5f
                     75:        .ascii  "This program requires a 386 or better.\r\n\0"
                     76: 5:     popw    %si
                     77:        movw    %cs,%ax
                     78:        movw    %ax,%ds
                     79:        cld
                     80: 2:     lodsb
                     81:        orb     %al,%al
                     82:        jz      3f
                     83:        movb    $0x02,%ah
                     84:        movb    %al,%dl
                     85:        int     $0x21
                     86:        jmp     2b
                     87: 3:     movw    $0x4c02,%ax
                     88:        int     $0x21
                     89: 4:
                     90:        /* Now we can use 32-bit instructions all we want.  */
                     91: 
                     92:        /* Save the PSP segment address (dx).  */
                     93:        movw    %ds,%dx
                     94: 
                     95:        /* Find our real-mode code segment (ax).  */
                     96:        movw    %cs,%ax
                     97: 
                     98: #ifdef ENABLE_PAGE_ALIGNED_KERNEL
                     99:        /* Move our code and data so that everything is on a page boundary.
                    100:           Theoretically we _could_ go past the end of available memory,
                    101:           since we're not checking, but it's enormously unlikely.  */
                    102:        std
                    103:        movw    %ax,%ds
                    104:        addw    $0xff,%ax
                    105:        andw    $0xff00,%ax
                    106:        movw    %ax,%es
                    107:        movl    $EXT(edata),%ecx
                    108:        subl    $EXT(i16_entry_2),%ecx
                    109:        movl    $EXT(edata)-1,%esi
                    110:        movw    %si,%di
                    111:        rep
                    112:        movsb
                    113: 
                    114:        /* Start running at the new address.  */
                    115:        pushl   $EXT(i16_entry_2)
                    116:        movw    %ax,2(%esp)
                    117:        lretw
                    118: 
                    119: ENTRY(i16_entry_2)
                    120:        /* We're now page aligned.  */
                    121: #endif ENABLE_PAGE_ALIGNED_KERNEL
                    122: 
                    123:        /* Load the data segment registers appropriately.  */
                    124:        movw    %ax,%es
                    125:        movw    %ax,%ss
                    126: 
                    127:        /* Start using a real stack.  */
                    128:        movl    $EXT(crt0_stack)+CRT0_STACK_SIZE,%esp
                    129: 
                    130:        /* Clear our BSS segment.  */
                    131:        movl    $EXT(edata),%edi
                    132:        movl    $EXT(end),%ecx
                    133:        subw    %di,%cx
                    134:        xorb    %al,%al
                    135:        cld
                    136:        rep
                    137:        stosb
                    138: 
                    139:        /* Find the size of the environment array (si) 
                    140:           and the number of environment variables plus one (bx).
                    141:           The PSP segment is still in dx.  */
                    142:        movw    %dx,%ds
                    143:        movw    0x2c,%ds
                    144:        xorw    %si,%si
                    145: 1:     lodsb
                    146:        orb     %al,%al
                    147:        jnz     1b
                    148:        lodsb
                    149:        orb     %al,%al
                    150:        jnz     1b
                    151: 
                    152:        /* Allocate space for the environment array on the stack.
                    153:           Also make sure the top 16 bits of ESP are cleared,
                    154:           and that the stack pointer is longword aligned.  */
                    155:        subw    %si,%sp
                    156:        andl    $0x0000fffc,%esp
                    157: 
                    158:        /* Copy the environment array to the local stack.
                    159:           We present it backwards, but big deal - shouldn't matter.  */
                    160:        xorl    %edi,%edi
                    161:        movw    %sp,%di
                    162:        xorl    %esi,%esi
                    163:        pushl   %esi
                    164:        jmp     3f
                    165: 2:     pushl   %edi
                    166:        stosb
                    167: 1:     lodsb
                    168:        stosb
                    169:        orb     %al,%al
                    170:        jnz     1b
                    171: 3:     lodsb
                    172:        orb     %al,%al
                    173:        jnz     2b
                    174:        movl    %esp,%cs:EXT(environ)
                    175: 
                    176:        /* Copy the program name to the local stack;
                    177:           it will be used as argv[0].  */
                    178:        lodsw
                    179:        movw    %si,%bx
                    180: 1:     pushw   $0
                    181:        lodsb
                    182:        orb     %al,%al
                    183:        jz      2f
                    184:        lodsb
                    185:        orb     %al,%al
                    186:        jnz     1b
                    187: 2:     movw    %bx,%si
                    188:        movw    %sp,%di
                    189: 3:     lodsb
                    190:        stosb
                    191:        orb     %al,%al
                    192:        jnz     3b
                    193:        movl    %esp,%ebp
                    194: 
                    195:        /* Build argv[1..n] from the command tail in the PSP.
                    196:           Count the arguments in ebx.  */
                    197:        movw    %dx,%ds
                    198:        xorl    %ecx,%ecx
                    199:        xorl    %ebx,%ebx
                    200:        movb    0x80,%cl        /* get size of command tail */
                    201:        incw    %cx             /* plus the return character */
                    202:        movw    $0x80,%si
                    203:        addw    %cx,%si         /* si = ptr to return character */
                    204:        movw    %sp,%di
                    205:        decw    %di
                    206:        subw    %cx,%sp         /* allocate space on the stack */
                    207:        andw    $0xfffc,%sp
                    208:        pushl   %ebx
                    209:        std
                    210: 1:     xorb    %al,%al         /* store a null terminator for this arg */
                    211:        stosb
                    212:        incl    %ebx
                    213: 2:     cmpw    $0x80,%si
                    214:        je      5f
                    215:        lodsb                   /* scan backwards for the end of an arg */
                    216:        cmpb    $0x20,%al
                    217:        jbe     2b
                    218: 3:     stosb                   /* copy the arg */
                    219:        cmpw    $0x80,%si
                    220:        je      4f
                    221:        lodsb
                    222:        cmpb    $0x20,%al
                    223:        ja      3b
                    224: 4:     movw    %di,%cx         /* push an arg pointer */
                    225:        incw    %cx
                    226:        pushl   %ecx
                    227:        jmp     1b
                    228: 5:
                    229: 
                    230:        /* Push the argv[0] pointer.  */
                    231:        pushl   %ebp
                    232: 
                    233:        /* Push the argument and envirnonment parameters on the stack.  */
                    234:        movl    %esp,%eax
                    235:        pushl   %cs:EXT(environ)
                    236:        pushl   %eax
                    237:        pushl   %ebx
                    238: 
                    239:        /* Release all conventional memory above the top of our BSS.
                    240:           The PSP segment is still in dx.  */
                    241:        movl    $EXT(end)+15,%ebx
                    242:        shrw    $4,%bx
                    243:        movw    %cs,%ax
                    244:        addw    %ax,%bx
                    245:        subw    %dx,%bx
                    246:        movw    %dx,%es
                    247:        movb    $0x4a,%ah
                    248:        int     $0x21
                    249: 
                    250:        /* Load the normal data segment registers.  */
                    251:        movw    %cs,%ax
                    252:        movw    %ax,%ds
                    253:        movw    %ax,%es
                    254: 
                    255:        /* GCC wants the direction flag cleared at all times.  */
                    256:        cld
                    257: 
                    258:        /* Initialize the bss and run the program.  */
                    259:        call    EXT(i16_main)
                    260: 
                    261:        .globl  EXT(crt0_stack)
                    262:        .comm   EXT(crt0_stack),CRT0_STACK_SIZE
                    263: 
                    264:        .globl  EXT(environ)
                    265:        .comm   EXT(environ),4
                    266: 
                    267: 
                    268:        .data
                    269: 
                    270:        .section .anno,"aw",@progbits
                    271:        P2ALIGN(4)
                    272:        .globl  __ANNO_START__
                    273: __ANNO_START__:
                    274: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.