Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

What is actually startup code??

Status
Not open for further replies.

brunokasimin

Member level 4
Joined
Jun 13, 2008
Messages
70
Helped
2
Reputation
4
Reaction score
2
Trophy points
1,288
Activity points
1,828
startup code

What is actually startup code?? From what i knew, Startup code is executed immediately upon reset of the target system.I have been looking for the easy explanation in google but could not find the simple explanation..Can somebody explain me in easy detail??
 

startup code

Start up code is added by the compiler to your C program and located at the reset vector by the linker. It usually just initialises the stack pointer and if you have global varables, statics and constants, it initialises them.
It then calls your 'main()' function to start your program.
The source code for the start up file will be somewhere in the compiler directories, it is usually only a small file, maybe in assembler or C, read the manual, you can modify it if you want something to happen before calling 'main()'.
 

Re: startup code

Do you refer main() as the one fromC program?
 

Re: startup code

Yes, the start up code is the code that calls 'main()' to start your program.
Here is the source code for the start up file used by the Microchip Mplab C30 compiler. You will find the source code for the start up file for your compiler in the '\lib\src' directories. The code is placed at the reset vector by the linker and runs first on processor reset.
You can modify the code if you want to do something before calling 'main()'.

Code:
;; 
;; C Run-time startup module for dsPIC30 C compiler.
;; (c) Copyright 2002,2004,2007 Microchip Technology, All rights reserved
;;
;; Primary version, with data initialization support.
;; The linker loads this version when the --data-init
;; option is selected.
;; 
;; See file crt1.s for the alternate version without
;; data initialization support.
;; 
;; Entry __reset takes control at device reset and
;; performs the following:
;;
;;  1. initialize stack and stack limit register
;;  2. initialize PSV window if __const_length > 0
;;  3. process the data initialization template
;;  4. call the user's _main entry point
;;
;; Assigned to section .init, which may be allocated
;; at a specific address in linker scripts. 
;;
;; Supports the zero-parameter form of main() by default.
;; If the symbol __ARGV is defined, supports the two-parameter
;; form of main().
;;
;; Un-comment the following line to define symbol __ARGV:
;;      .equiv __ARGV,1
;; 
        
        .equ __30F2010, 1   
        .include "p30f2010.inc"

        .section .init,code

        .global __resetPRI
        .ifdef __C30ELF
        .type   __resetPRI,@function
        .endif
__resetPRI:     
        .weak   __reset
        .ifdef __C30ELF
        .type   __reset,@function
        .endif
__reset:
;;
;; Initialize stack, PSV, and data
;; 
;; registers used:  w0
;;
;; Inputs (defined by user or linker):
;;  __SP_init
;;  __SPLIM_init
;; 
;; Outputs:
;;  (does not return - resets the processor)
;; 
;; Calls:
;;  __psv_init
;;  __data_init
;;  _main or __main
;; 

        mov      #__SP_init,w15    ; initialize w15
        mov      #__SPLIM_init,w0  ; 
        mov      w0,_SPLIM         ; initialize SPLIM
        nop                        ; wait 1 cycle

        rcall    __psv_init        ; initialize PSV
        rcall    __data_init       ; initialize data
                                   ;  clears w0, so ARGC = 0

        .ifdef __ARGV
          rcall  __main            ; call two-parameter main() setup
        .else
          call  _main              ; call user's main()
        .endif

        .pword 0xDA4000            ; halt the simulator
        reset                      ; reset the processor


        .weak __psv_init
__psv_init:
;; 
;; Initialize PSV window if _constlen > 0
;; 
;; Registers used:  w0
;; 
;; Inputs (defined by linker):
;;  __const_length
;;  __const_psvpage
;; 
;; Outputs:
;;  (none)
;; 

        bclr     _CORCON,#PSV        ; disable PSV (default)
        mov      #__const_length,w0  ; 
        cp0      w0                  ; test length of constants
        bra      z,1f                ; br if zero

        mov      #__const_psvpage,w0 ; 
        mov      w0,_PSVPAG          ; PSVPAG = psvpage(constants)
        bset     _CORCON,#PSV        ; enable PSV

1:      return                       ;  and exit

        
        .weak __data_init
__data_init:
;; 
;; Process data init template
;;
;; The template is null-terminated, with records
;; in the following format:
;;
;; struct data_record {
;;  char *dst;        /* destination address  */
;;  int  len;         /* length in bytes      */
;;  int  format;      /* format code          */
;;  char dat[0];      /* variable length data */
;; };
;; 
;; Registers used:  w0 w1 w2 w3 w4 w5
;; 
;; Inputs (defined by linker):
;;  __dinit_tbloffset
;;  __dinit_tblpage
;; 
;; Outputs:
;;  (none)
;;
;; Calls:
;;  __memcpypd3
;; 
        .equiv   FMT_CLEAR,0    ;  format codes
        .equiv   FMT_COPY2,1    ; 
        .equiv   FMT_COPY3,2    ; 

        mov      #__dinit_tbloffset,w0 ; w0,w1 = template
        mov      #__dinit_tblpage,w1   ;
        bra      4f                    ; br to continue

1:      add      w0,#2,w0       ; template+=2
        addc     w1,#0,w1       ; 
        mov      w1,_TBLPAG     ; TBLPAG = tblpage(template)

        tblrdl.w [w0],w3        ; w3 = len 
        add      w0,#2,w0       ; template+=2
        addc     w1,#0,w1       ; 
        mov      w1,_TBLPAG     ; TBLPAG = tblpage(template)

        tblrdl.w [w0],w5        ; w5 = format
        add      w0,#2,w0       ; template+=2
        addc     w1,#0,w1       ; 
        clr      w4             ; upper = FALSE (default)

        cp       w5,#FMT_CLEAR  ; test format
        bra      nz,2f          ; br if not FMT_CLEAR

        ;; FMT_CLEAR - clear destination memory
        dec      w3,w3          ; decrement & test len
        bra      n,4f           ; br if negative

        repeat   w3             ; 
        clr.b    [w2++]         ; clear memory      
        bra      4f             ; br to continue

        ;; FMT_COPY2, FMT_COPY3 - copy bytes
2:      cp       w5,#FMT_COPY2  ; test format
        bra      z,3f           ; br if FMT_COPY2

        setm     w4             ; upper = TRUE

3:      rcall    __memcpypd3    ; copy 2 or 3 bytes

4:      mov      w1,_TBLPAG     ; TBLPAG = tblpage(template)
        tblrdl.w [w0],w2        ; w2 = next dst      
        cp0      w2             ; 
        bra      nz,1b          ; loop on non-zero dst

        retlw    #0,w0          ; exit (clears ARGC also)

        
__memcpypd3:
;; 
;; Copy data from program memory to data memory
;; 
;; Registers used:  w0 w1 w2 w3 w4 w5
;; 
;; Inputs:
;;  w0,w1 = source address   (24 bits)
;;  w2 = destination address (16 bits)
;;  w3 = number of bytes (even or odd)
;;  w4 = upper byte flag   (0 = false)
;; 
;; Outputs:
;;  w0,w1 = next source address (24 bits)
;; 

1:      mov      w1,_TBLPAG     ; TBLPAG = tblpage(src)
        mov      w0,w5          ; w5 =   tbloffset(src)
        add      w0,#2,w0       ; src+=2
        addc     w1,#0,w1       ;

        tblrdl.b [w5++],[w2++]  ; dst++ = lo byte
        dec      w3,w3          ; num--
        bra      z,2f           ; br if done

        tblrdl.b [w5--],[w2++]  ; dst++ = hi byte
        dec      w3,w3          ; num--
        bra      z,2f           ; br if done

        cp0      w4             ; test upper flag
        bra      z,1b           ; br if false

        tblrdh.b [w5],[w2++]    ; dst++ = upper byte
        dec      w3,w3          ; num--
        bra      nz,1b          ; br if not done

2:      return                  ; exit


        .ifdef __ARGV        
__main:
;; 
;; Initialize a stack frame to support
;;   the two-parameter form of main()
;; 
;; Registers used:  w0 w1
;;
;; Inputs:
;;  (none)
;;
;; Outputs:
;;  (none)
;;
;; Calls:
;;  _main
;; 
        lnk      #6             ; construct frame

        mov      #0,w0          ; store a null terminator
        mov.b    w0,[w15-6]     ;  for program name

        sub      w15,#6,w1
        mov      w1,[w15-4]     ; argv[0] = &pgmname             
        mov      w0,[w15-2]     ; argv[1] = 0

        mov      #1,w0          ; w0 = argc
        sub      w15,#4,w1      ; w1 = &argv
        call    _main           ; call the user's main()

        ulnk                    ; destroy frame
        return                  ;  and exit
        .endif

        .end
 
Status
Not open for further replies.

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top