home *** CD-ROM | disk | FTP | other *** search
/ ARM Club 3 / TheARMClub_PDCD3.iso / hensa / unix / unixlib_1 / !UnixLib37_src_sys_s__jmp < prev    next >
Encoding:
Text File  |  1996-11-09  |  4.3 KB  |  152 lines

  1. ;----------------------------------------------------------------------------
  2. ;
  3. ; $Source: /unixb/home/unixlib/source/unixlib37/src/sys/s/RCS/_jmp,v $
  4. ; $Date: 1996/11/06 22:01:42 $
  5. ; $Revision: 1.3 $
  6. ; $State: Rel $
  7. ; $Author: unixlib $
  8. ;
  9. ; $Log: _jmp,v $
  10. ; Revision 1.3  1996/11/06 22:01:42  unixlib
  11. ; Yet more changes by NB, PB and SC.
  12. ;
  13. ; Revision 1.2  1996/10/30 21:59:00  unixlib
  14. ; Massive changes made by Nick Burret and Peter Burwood.
  15. ;
  16. ; Revision 1.1  1996/04/19 21:34:32  simon
  17. ; Initial revision
  18. ;
  19. ;----------------------------------------------------------------------------
  20.  
  21.     GET    Unix37:unixlib.s.asm_dec
  22.  
  23.     AREA    |C$$code|,CODE,READONLY
  24.  
  25.     IMPORT    |__fpflag|
  26. |__fpflag_ptr|
  27.     DCD    |__fpflag|
  28.  
  29.     IMPORT    |__alloca_list|,WEAK
  30. |__alloca_list_ptr|
  31.     DCD    |__alloca_list|
  32.     IMPORT    free
  33.     IMPORT    |_exit|
  34.  
  35.     EXPORT    setjmp
  36.  
  37.     NAME    setjmp
  38. setjmp
  39.     ; record the current allocation pointer for use with longjmp
  40.     ; Note, alloca_list is a weak symbol so may not be set
  41.     ; Warning!!!
  42.     ; Do not change alloca_list so that it is not weak
  43.     ; because it is weak in _syslib.s and it would confuse the linker
  44.     LDR    a4,[pc,#|__alloca_list_ptr|-.-8]
  45.     CMP    a4,#0
  46.     LDRNE    a4,[a4,#0]
  47.     STR    a4,[a1],#4
  48.  
  49.     LDR    a4,[pc,#|__fpflag_ptr|-.-8]
  50.     LDR    a4,[a4,#0]
  51.     CMP    a4,#0
  52.     ADDEQ    a1,a1,#48
  53.     BEQ    |__setjmp_l1|
  54.     STFE    f4,[a1],#12
  55.     STFE    f5,[a1],#12
  56.     STFE    f6,[a1],#12
  57.     STFE    f7,[a1],#12
  58. |__setjmp_l1|
  59.     ; warning!!!!
  60.     ; even though a1 does not need to be saved, this position in
  61.     ; the jmp_buf is used when a child process returns via vret
  62.     STMIA    a1,{a1,v1,v2,v3,v4,v5,v6,fp,sp,lr}
  63.     MOV    a1,#0
  64.     MOVS    pc,lr
  65.  
  66.     EXPORT    longjmp
  67.  
  68.     NAME    longjmp
  69. longjmp
  70.     ; free allocations that occurred after the setjmp. This must be
  71.     ; done before any registers, including the fp registers, are
  72.     ; restored from the jmp_buf, because free() could do anything.
  73.  
  74.     ; we should be able to safely use v1-v6, since if a recursive
  75.     ; call to longjmp does occur, then the v1-v6 are going to be
  76.     ; safely restored to their current values.
  77.  
  78.     ; what about sl?, should __stack be reset ?
  79.  
  80.     LDR    v4,[a1],#4
  81.     LDR    v5,[pc,#|__alloca_list_ptr|-.-8]
  82.     CMP    v5, #0
  83.     LDRNE    v3,[v5,#0]
  84.     MOV    v1,a1
  85.     CMPNE    v3,v4
  86.     BEQ    |__longjmp_l3|
  87.     MOV    v2,a2
  88. |__longjmp_l2|
  89.     MOVS    a1,v3
  90.     BEQ    |__longjmp_fatal|    ; oh fuck!, the list has run out
  91.     LDR    v3,[v3,#0]
  92.     ; update pointers in loop.
  93.     ; must be done here in case free indirectly calls longjmp
  94.     STR    v3,[v5,#0]        ; update head of alloca_list
  95.     STR    v3,[v1,#-4]        ; update the stored value in jmp_buf
  96.     BL    free
  97.     CMP    v3,v4
  98.     BNE    |__longjmp_l2|
  99.     MOV    a2,v2
  100. |__longjmp_l3|
  101.     LDR    a4,[pc,#|__fpflag_ptr|-.-8]
  102.     LDR    a4,[a4,#0]
  103.     CMP    a4,#0
  104.     ADDEQ    v1,v1,#48
  105.     BEQ    |__longjmp_l1|
  106.     LDFE    f4,[v1],#12
  107.     LDFE    f5,[v1],#12
  108.     LDFE    f6,[v1],#12
  109.     LDFE    f7,[v1],#12
  110. |__longjmp_l1|
  111.     MOVS    a1,a2
  112.     MOVEQ    a1,#1            ; longjmp can't return 0
  113.     ; technically there is a problem here if we should be
  114.     ; moving to a higher processor mode, such as USR -> SVC
  115.     ; warning!!!!
  116.     ; while a1 probably doesn't need to be saved here, this
  117.     ; is what the old code did and UnixLib has already caught me out
  118.     ; once by using this position in the jmp_buf as the return
  119.     ; value for vret!!!!
  120.     STR    a1,[v1,#0]
  121.     LDMIA    v1,{a1,v1,v2,v3,v4,v5,v6,fp,sp,pc}^
  122.  
  123.     ; if we get here something has screwed up. The old value
  124.     ; of alloca list which we were searching for which was active
  125.     ; when the setjmp was called wasn't found. This can happen for
  126.     ; at least two reasons.
  127.     ;  1. The jmpbuf has become corrupt through being overwritten
  128.     ;  2. The user is attempting a longjmp to an invalid setjmp
  129.     ;     point, i.e., the scope of the setjmp has exited.
  130. |__longjmp_fatal|
  131.     ADR    a1,|__longjmp_fatal_msg|
  132.     SWI    XOS_NewLine
  133.     SWI    XOS_NewLine
  134.     SWI    XOS_Write0
  135.     SWI    XOS_NewLine
  136.     ; This failure is too serious to trying raising a signal, since
  137.     ; all the dynamic allocations have been freed and letting the user
  138.     ; access that memory is just too dangerous. Further, the abort code
  139.     ; or signal handler on abort may longjmp, causing recursion
  140.     ; until the stack runs out. This is all likely to crash the users
  141.     ; poor machine, so bale out now to be nice.
  142.     MOV    a1,#EXIT_FAILURE
  143.     B    |_exit|
  144. |__longjmp_fatal_msg|
  145.     DCB    "Fatal error detected in longjmp, jmpbuf possibly corrupt.",13,10
  146.     DCB    "This can happen for at least two reasons.",13,10
  147.     DCB    " - The jmpbuf has become corrupt through being overwritten.",13,10
  148.     DCB    " - The program is attempting a longjmp to an invalid setjmp point, ",13,10
  149.     DCB    "   i.e., the scope of the setjmp has exited.",0
  150.  
  151.     END
  152.