linux/arch/powerpc/platforms/cell/spufs/spu_restore_crt0.S
<<
>>
Prefs
   1/*
   2 * crt0_r.S: Entry function for SPU-side context restore.
   3 *
   4 * Copyright (C) 2005 IBM
   5 *
   6 * Entry and exit function for SPU-side of the context restore
   7 * sequence.  Sets up an initial stack frame, then branches to
   8 * 'main'.  On return, restores all 128 registers from the LSCSA
   9 * and exits.
  10 *
  11 *
  12 * This program is free software; you can redistribute it and/or modify
  13 * it under the terms of the GNU General Public License as published by
  14 * the Free Software Foundation; either version 2, or (at your option)
  15 * any later version.
  16 *
  17 * This program is distributed in the hope that it will be useful,
  18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
  19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  20 * GNU General Public License for more details.
  21 *
  22 * You should have received a copy of the GNU General Public License
  23 * along with this program; if not, write to the Free Software
  24 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  25 */
  26
  27#include <asm/spu_csa.h>
  28
  29.data
  30.align 7
  31.globl regs_spill
  32regs_spill:
  33.space SIZEOF_SPU_SPILL_REGS, 0x0
  34
  35.text
  36.global _start
  37_start:
  38        /* Initialize the stack pointer to point to 16368
  39         * (16kb-16). The back chain pointer is initialized
  40         * to NULL.
  41         */
  42        il      $0, 0
  43        il      $SP, 16368
  44        stqd    $0, 0($SP)
  45
  46        /* Allocate a minimum stack frame for the called main.
  47         * This is needed so that main has a place to save the
  48         * link register when it calls another function.
  49         */
  50        stqd    $SP, -160($SP)
  51        ai      $SP, $SP, -160
  52
  53        /* Call the program's main function. */
  54        brsl    $0, main
  55
  56.global exit
  57.global _exit
  58exit:
  59_exit:
  60        /* SPU Context Restore, Step 5: Restore the remaining 112 GPRs. */
  61        ila     $3, regs_spill + 256
  62restore_regs:
  63        lqr     $4, restore_reg_insts
  64restore_reg_loop:
  65        ai      $4, $4, 4
  66        .balignl 16, 0x40200000
  67restore_reg_insts:       /* must be quad-word aligned. */
  68        lqd     $16, 0($3)
  69        lqd     $17, 16($3)
  70        lqd     $18, 32($3)
  71        lqd     $19, 48($3)
  72        andi    $5, $4, 0x7F
  73        stqr    $4, restore_reg_insts
  74        ai      $3, $3, 64
  75        brnz    $5, restore_reg_loop
  76
  77        /* SPU Context Restore Step 17: Restore the first 16 GPRs. */
  78        lqa $0, regs_spill + 0
  79        lqa $1, regs_spill + 16
  80        lqa $2, regs_spill + 32
  81        lqa $3, regs_spill + 48
  82        lqa $4, regs_spill + 64
  83        lqa $5, regs_spill + 80
  84        lqa $6, regs_spill + 96
  85        lqa $7, regs_spill + 112
  86        lqa $8, regs_spill + 128
  87        lqa $9, regs_spill + 144
  88        lqa $10, regs_spill + 160
  89        lqa $11, regs_spill + 176
  90        lqa $12, regs_spill + 192
  91        lqa $13, regs_spill + 208
  92        lqa $14, regs_spill + 224
  93        lqa $15, regs_spill + 240
  94
  95        /* Under normal circumstances, the 'exit' function
  96         * terminates with 'stop SPU_RESTORE_COMPLETE',
  97         * indicating that the SPU-side restore code has
  98         * completed.
  99         *
 100         * However it is possible that instructions immediately
 101         * following the 'stop 0x3ffc' have been modified at run
 102         * time so as to recreate the exact SPU_Status settings
 103         * from the application, e.g. illegal instruciton, halt,
 104         * etc.
 105         */
 106.global exit_fini
 107.global _exit_fini
 108exit_fini:
 109_exit_fini:
 110        stop    SPU_RESTORE_COMPLETE
 111        stop    0
 112        stop    0
 113        stop    0
 114
 115        /* Pad the size of this crt0.o to be multiple of 16 bytes. */
 116.balignl 16, 0x0
 117