Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- list p=16f616
- #include p16f616.inc
- ;*** Configuration Bits ***
- __CONFIG _FOSC_INTOSCIO & _WDTE_OFF & _WDT_OFF & _PWRTE_ON & _MCLRE_OFF & _CP_OFF & _IOSCFS_8MHZ & _BOREN_ON
- ;**************************
- ;*** Variable Definitions ***
- VARS UDATA ; Define undefined data(s).
- numOfTasks res 1 ; This variable holds the number of tasks multiplied by 2.
- currentTask res 1 ; Index variable that points to the current task's index in "tasks"
- tasks res 4 ; This is task "array". Every task occupies 2 bytes.
- ;****************************
- ;*** Reset Vector ***
- RESET CODE 0x0000 ; Define a code block starting at 0x0000, which is reset vector, labeled "RESET"
- goto start ; Start the program.
- ;********************
- ;*** Main Code ***
- MAIN CODE
- start ; Label the start of the program as "start".
- banksel TRISA ; Select appropriate bank for TRISA.
- clrf TRISA ; Clear TRISA register. Configure all of the PORTA pins as digital outputs.
- clrf TRISC ; Clear TRISC register. TRISC and TRISA are at the same bank, no need for "banksel".
- clrf ANSEL ; Clear ANSEL register and configure all the analog pins as digital i/o.
- banksel PORTA ; Select appropriate bank for PORTA.
- clrf PORTA ; Clear PORTA register.
- clrf PORTC ; Clear PORTC register. PORTC and PORTA are at the same bank, no need for "banksel".
- movlw 0x04 ; W = Number of tasks * 2.
- movwf numOfTasks ; Since every task has two datas in it, we will multiply by 2.
- clrf currentTask ; Set the task#0 as current task.
- CALL task0 ; Call task#0 since we need to initialize it. We are going to get..
- ; ..its PCL and PCLATH values at the start address.
- movlw 0x02 ; W = 2
- addwf currentTask, f ; Increment currentTask by 2, since every task occupies 2 places.
- CALL task1 ; Call task#1, for initialazation.
- taskswitcher
- movlw 0x02 ; W = 2
- addwf currentTask, f ; Add 2 to currentTask, store it in currentTask.
- movf numOfTasks, w ; W = numOfTasks
- subwf currentTask, w ; w= f - w
- btfsc STATUS, 0 ; If currentTask >= numOfTasks
- clrf currentTask ; Clear currentTask
- movlw tasks ; Store the address of tasks, which is the start address of our task "array".
- addwf currentTask, w ; Add current task's index to the start address.
- ; For example; task1's index is 2: [task0_1][task0_2][task1_1][task1_2]....
- ; 0 1 2 3
- movwf FSR ; We have the index of current task in W. Copy it to FSR
- movf INDF, w ; Copy the contents of current task's first item to W
- movwf PCLATH ; Copy W to PCLATH. As a result, current task's PCLATH will be in PCLATH register.
- incf FSR, f ; Increment index, so that we will point to the next item of current task.
- movf INDF, w ; Copy the contents of current task's second item to W.
- movwf PCL ; Copy W to PCL. Finally, current task's PCL will be in PCL register.
- goto $ ; This instruction is not effective. But, enter the endless loop.
- ;*** TASK 0 ***
- TASK0 CODE
- ;**************
- task0
- movlw tasks ; Store the address of tasks, which is the start address of our task "array".
- addwf currentTask, w ; Add current task's index to the start address.
- movwf FSR ; We have the index of current task in W. Copy it to FSR
- movf PCLATH, w ; Copy PCLATH register's contents to W register.
- movwf INDF ; Copy W to current task's first item. We now store PCLATH.
- incf FSR,f ; Increment index, so that we will point to the next item of current task.
- movlw low($+3) ; Copy PCL+3 to W register. This will let us save the PCL of the start of the task.
- movwf INDF ; Copy W to task's next item. With that, we will initialize the current task.
- return ; We have gathered our initialazation information. Return back to main.
- task0main
- banksel PORTA ; Select the appropriate bank for PORTA
- movlw 0xAA ; Move literal to W so that W = 0xAA
- movwf PORTA ; PORTA = 0xAA. Use a LATA register to create more robust code.
- movlw tasks ; Store the address of tasks, which is the start address of our task "array".
- addwf currentTask, w ; Add current task's index to the start address.
- movwf FSR ; We have the index of current task in W. Copy it to FSR
- movf PCLATH, w ; Copy PCLATH register's contents to W register.
- movwf INDF ; Copy W to current task's first item. We now store PCLATH of the current state of the task.
- incf FSR,f ; Increment index, so that we will point to the next item of current task.
- movlw low($+3) ; Copy PCL+3 to W register. This will let us save the PCL of the current state of the task.
- movwf INDF ; Copy W to task's next item. With that, we will initialize the current task.
- goto taskswitcher ; Yield the CPU to the awaiting task by going to task switcher.
- banksel PORTA ; Select the appropriate bank for PORTA
- movlw 0x55 ; Move literal to W so that W = 0x55
- movwf PORTA ; PORTA = 0xAA. Use a LATA register to create more robust code.
- goto task0main ; Loop by going back to "task0main". We will continuously toggle PORTA.
- ;*** TASK 0 ***
- TASK1 CODE
- ;**************
- task1
- movlw tasks ; Store the address of tasks, which is the start address of our task "array".
- addwf currentTask, w ; Add current task's index to the start address.
- movwf FSR ; We have the index of current task in W. Copy it to FSR
- movf PCLATH, w ; Copy PCLATH register's contents to W register.
- movwf INDF ; Copy W to current task's first item. We now store PCLATH.
- incf FSR,f ; Increment index, so that we will point to the next item of current task.
- movlw low($+3) ; Copy PCL+3 to W register. This will let us save the PCL of the start of the task.
- movwf INDF ; Copy W to task's next item. With that, we will initialize the current task.
- return ; We have gathered our initialazation information. Return back to main.
- task1main
- banksel PORTA ; Select the appropriate bank for PORTA
- movlw 0xAA ; Move literal to W so that W = 0xAA
- movwf PORTA ; PORTA = 0xAA. Use a LATA register to create more robust code.
- movlw tasks ; Store the address of tasks, which is the start address of our task "array".
- addwf currentTask, w ; Add current task's index to the start address.
- movwf FSR ; We have the index of current task in W. Copy it to FSR
- movf PCLATH, w ; Copy PCLATH register's contents to W register.
- movwf INDF ; Copy W to current task's first item. We now store PCLATH of the current state of the task.
- incf FSR,f ; Increment index, so that we will point to the next item of current task.
- movlw low($+3) ; Copy PCL+3 to W register. This will let us save the PCL of the current state of the task.
- movwf INDF ; Copy W to task's next item. With that, we will initialize the current task.
- goto taskswitcher ; Yield the CPU to the awaiting task by going to task switcher.
- banksel PORTA ; Select the appropriate bank for PORTA
- movlw 0x55 ; Move literal to W so that W = 0x55
- movwf PORTA ; PORTA = 0xAA. Use a LATA register to create more robust code.
- goto task1main ; Loop by going back to "task1main". We will continuously toggle PORTA.
- END ; END of the program.
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement