⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dispatch.mod

📁 该应用软件可以实现大多数单片机的仿真实验
💻 MOD
字号:
;**********************************************************************
;* Module    : DISPATCH.MOD
;* Programmer: Tony Papadimitriou
;* Purpose   : The dispatcher module for OS calls
;* Language  : MC68HC11 (ASM11 v1.83+)
;* Status    : FREEWARE, Copyright (c) 1999 by Tony Papadimitriou
;* Segments  : RAM    : Variables
;*           : ROM    : Code
;*           : SEG9   : OS definitions (this allows adding more functions)
;*           : VECTORS: SWI vector
;* Note(s)   : INCLUDE last (i.e., after ALL OS-defining includes
;*           : This file also contains functions that are used
;*           : practically in every program, such as fDelayMS
;*           : Occupies SWI vector
;* History   : 99.11.01 Original
;**********************************************************************

#ifmain ;------------------------------------------------------------
                    #listoff
                    #include  811E2.INC
                    #include  COMMON.INC
                    #liston

                    #SEG9
                    org       $FF00
                    #ROM
                    org       $F800
#endif ;-------------------------------------------------------------

                    #SEG9
#ifndef OSCommands
OSCommands          equ       *
#endif

fDelayMS            equ       *-OSCommands/2      ;Delay variable number of ms
                    dw        ?DelayMS

fUpcase             equ       *-OSCommands/2      ;Convert char in RegA to uppercase
                    dw        ?Upcase

?OS.Entries         equ       *-OSCommands/2      ;Number of opcodes defined

#if ?OS.Entries > 255
?OS_16BIT
                    #warning  Max. functions (256) exceeded, redesign for OSW
#endif

                    #ROM
;**********************************************************************
;*               OS DISPATCHER (OS CALLS COME HERE)                   *
;**********************************************************************
;* Call format: OS CallName                                           *
;* Returns    : No Carry if no error, B is unaffected                 *
;*            : Carry if error, B holds error code                    *
;* Note(s)    : Interrupts will be allowed during the call if the I   *
;*            : bit before the call was clear, otherwise they won't.  *
;* Total Stack: 11 (9 for caller + 2 for local storage without subs)  *
;**********************************************************************
                    #push
                    #mapoff
?SWI_Handler        tsy                           ;point Y to SWI stack frame
                    brset     CCR_,y,I.,?SWI_Continue ;if I bit was set before OS call, don't allow ints
                    cli                           ;Enable interrupts
?SWI_Continue       ldx       PC_,y               ;adjust PC for opcode
#ifdef ?OS_16BIT
                    ldd       ,x                  ;OSW type calls
                    inx                           ;skip 2nd opcode byte
#else
                    clra                          ;we're gonna use D (for OS calls)
                    ldb       ,x                  ;get OS opcode byte
#endif
                    inx                           ;skip 1st opcode byte
                    stx       PC_,y               ;and save new PC to return to
                    cpd       #?OS.Entries        ;is it a valid OpCode?
                    bhs       ?SWI_Ret
#ifdef ?OS_16BIT
                    lsld                          ;multiply by two (size of table entries)
                    addd      #OSCommands         ;add starting address
                    xgdx                          ;and put result in X
#else
                    ldx       #OSCommands         ;point to command table
                    abx:2                         ;add offset twice (size of table entries)
#endif
                    ldx       ,x                  ;get function JMP vector
                    jsr       ,x                  ;Perform function
                    tsx                           ;X now points to user stack frame
;now, we should prepare the stack frame to be returned with appropriate values
                    bcs       ?SWI_Error
                    bclr      CCR_,x,C.           ;clear Carry flag
                    rti                           ;no error exit
?SWI_Error          bset      CCR_,x,C.           ;set Carry flag
                    stb       B_,x                ;save error code for user
#ifndef AnRTI
AnRTI
#endif
                    rti                           ;A globally accessed RTI

; The following section handles invalid OS Opcodes
?SWI_Ret            ldx       PC_,y               ;adjust PC to start of opcode
                    dex:2                         ;..back 1 byte for operand and 1 for the OS opcode
                    stx       PC_,y               ;and save new PC to return to
                    ldx       ILLOP_VECTOR
                    cpx       #ERASED_STATE       ;Check if not initialized (for EPROM, ie., $FFFF)
                    beq       ?SWI_Ret.2
                    jmp       ,x                  ;Invalid System Call
?SWI_Ret.2          equ       *                   ;In case ILLOP handler not installed
Halt_MCU            ldx       #500
                    os        fDelayMS            ;Let pending hardware events complete
                    sei                           ;Disable interrupts
; --- Shut down all peripherals (on and off chip)
                    pshx
                    ldx       #REGS
                    clr       [OPTION,x           ;Power-down A/D
                    clr       [SCCR2,x            ;Disable SCI
                    clr       [SPCR,x             ;Disable SPI
                    clr       [TMSK1,x            ;Disable IC/OC interrupts
                    clr       [TMSK2,x            ;Disable Timer interrupts
                    pulx
                    os        fDelayMS            ;Let subsystems turn off
                    cls                           ;Enable STOP instruction
#ifdef DEBUG
                    nop                           ;Instead of STOP (for SIM11x)
#else
                    stop                          ;and stay here in deep sleep
#endif
                    bra       *-1                 ;in case of XIRQ, go back to sleep
                    #pull


; Purpose: Delay ~ RegX milliseconds (not counting caller's overhead)
?DelayMS            ldx       X_,y                ;Get milliseconds to delay
?DelayMS.Loop       pshx
#ifdef DEBUG
                    ldx       #1                  ;for SIM11x use minimum delay
#else
                    ldx       #333                ;constant for 1 millisecond
#endif
                    dex
                    bne       *-1
                    pulx
                    dex
                    bne       ?DelayMS.Loop
                    clc                           ;No errors in any case
                    rts

; Purpose: Convert ASCII character in A to uppercase
; Input  : RegA->char
; Output : RegA->CHAR
?Upcase             lda       A_,y
                    bsr       Upcase
                    sta       A_,y
                    clc
                    rts

; Routine: Upcase
; Purpose: Convert character in A to uppercase
; Input  : A=character
; Output : A=CHARACTER
Upcase              cmpa      #'a'                 ;less than 'A'?
                    blo       ?Upcase.Exit         ;yes, skip
                    cmpa      #'z'                 ;greater than 'Z'?
                    bhi       ?Upcase.Exit         ;yes, skip
                    suba      #'a'-'A'             ;do the conversion
?Upcase.Exit        rts

                    #VECTORS
?vectors            equ       *

                    org       $FFF6
                    dw        ?SWI_Handler

                    org       ?vectors

                    end

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -