1#!/bin/sh
2
3# -----------------------------------------------------------------------
4#  gentramp.sh - Copyright (c) 2010, Plausible Labs Cooperative, Inc.
5#
6#  ARM Trampoline Page Generator
7#
8#  Permission is hereby granted, free of charge, to any person obtaining
9#  a copy of this software and associated documentation files (the
10#  ``Software''), to deal in the Software without restriction, including
11#  without limitation the rights to use, copy, modify, merge, publish,
12#  distribute, sublicense, and/or sell copies of the Software, and to
13#  permit persons to whom the Software is furnished to do so, subject to
14#  the following conditions:
15#
16#  The above copyright notice and this permission notice shall be included
17#  in all copies or substantial portions of the Software.
18#
19#  THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND,
20#  EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
21#  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
22#  NONINFRINGEMENT.  IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
23#  HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
24#  WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
25#  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
26#  DEALINGS IN THE SOFTWARE.
27#  -----------------------------------------------------------------------
28
29PROGNAME=$0
30
31# Each trampoline is exactly 3 instructions, or 12 bytes. If any of these values change,
32# the entire arm trampoline implementation must be updated to match, too.
33
34# Size of an individual trampoline, in bytes
35TRAMPOLINE_SIZE=12
36
37# Page size, in bytes
38PAGE_SIZE=4096
39
40# Compute the size of the reachable config page; The first 16 bytes of the config page
41# are unreachable due to our maximum pc-relative ldr offset.
42PAGE_AVAIL=`expr $PAGE_SIZE - 16`
43
44# Compute the number of of available trampolines.
45TRAMPOLINE_COUNT=`expr $PAGE_AVAIL / $TRAMPOLINE_SIZE`
46
47header () {
48    echo "# GENERATED CODE - DO NOT EDIT"
49    echo "# This file was generated by $PROGNAME"
50    echo ""
51
52    # Write out the license header
53cat << EOF
54#  Copyright (c) 2010, Plausible Labs Cooperative, Inc.
55#  
56#  Permission is hereby granted, free of charge, to any person obtaining
57#  a copy of this software and associated documentation files (the
58#  ``Software''), to deal in the Software without restriction, including
59#  without limitation the rights to use, copy, modify, merge, publish,
60#  distribute, sublicense, and/or sell copies of the Software, and to
61#  permit persons to whom the Software is furnished to do so, subject to
62#  the following conditions:
63#
64#  The above copyright notice and this permission notice shall be included
65#  in all copies or substantial portions of the Software.
66#
67#  THE SOFTWARE IS PROVIDED ``AS IS'', WITHOUT WARRANTY OF ANY KIND,
68#  EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
69#  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
70#  NONINFRINGEMENT.  IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
71#  HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
72#  WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
73#  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
74#  DEALINGS IN THE SOFTWARE.
75#  -----------------------------------------------------------------------
76
77EOF
78
79    # Write out the trampoline table, aligned to the page boundary
80    echo ".text"
81    echo ".align 12"
82    echo ".globl _ffi_closure_trampoline_table_page"
83    echo "_ffi_closure_trampoline_table_page:"
84}
85
86
87# WARNING - Don't modify the trampoline code size without also updating the relevant libffi code
88trampoline () {
89    cat << END
90
91    // trampoline
92    // Save to stack
93    stmfd sp!, {r0-r3}
94
95    // Load the context argument from the config page.
96    // This places the first usable config value at _ffi_closure_trampoline_table-4080
97    // This accounts for the above 4-byte stmfd instruction, plus 8 bytes constant when loading from pc.
98    ldr r0, [pc, #-4092]
99
100    // Load the jump address from the config page.
101    ldr pc, [pc, #-4092]
102
103END
104}
105
106main () {
107    # Write out the header
108    header
109
110    # Write out the trampolines
111    local i=0
112    while [ $i -lt ${TRAMPOLINE_COUNT} ]; do
113        trampoline
114        local i=`expr $i + 1`
115    done
116}
117
118main
119