blob: f547e8e1d29c3fa91ab9051b7627d8fe2c7394c2 (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
|
# Methods for constructing buffered-file objects.
#
# TODO: There are hard-coded parameters here for buffer sizes. When they
# overflow, tracking down what's going on can get hairy.
#
# HACK: buffered-file stores naked addrs. This is safe because buffered-file
# objects are opaque. But still sub-optimal; they'll be harder to reclaim when
# we get around to that.
== code
open: # filename: (addr array byte), write?: boolean, out: (addr handle buffered-file)
# . prologue
55/push-ebp
89/<- %ebp 4/r32/esp
# . save registers
50/push-eax
51/push-ecx
52/push-edx
53/push-ebx
56/push-esi
57/push-edi
# ecx = filename
8b/-> *(ebp+8) 1/r32/ecx
# var size/edx: int = filename->length + 1 for the trailing null character
8b/-> *ecx 2/r32/edx
42/increment-edx
# var s/esi: (stream size)
29/subtract-from %esp 2/r32/edx
52/push-edx # size
68/push 0/imm32/read
68/push 0/imm32/write
89/<- %esi 4/r32/esp
# copy filename and a final null character
(clear-stream %esi)
(write %esi %ecx)
# spill edx
52/push-edx
# var fd/ecx: fd = open(filename)
8d/copy-address *(esi+0xc) 3/r32/ebx
8b/-> *(ebp+0xc) 1/r32/ecx/flags
ba/copy-to-edx 0x180/imm32/permissions
e8/call syscall_open/disp32
89/<- %ecx 0/r32/eax
# restore edx
5a/pop-to-edx
# if fd < 0 return
3d/compare-eax-with 0/imm32
7c/jump-if-< $open:end/disp8
# allocate a buffered-file
(allocate Heap 0x1010 *(ebp+0x10)) # file-buffer-size + 16 for other fields
# var out-addr/edi: (addr buffered-file)
8b/-> *(ebp+0x10) 7/r32/edi
(lookup *edi *(edi+4)) # => eax
89/<- %edi 0/r32/eax
# out-addr->size = 4KB
c7 0/subop/copy *(edi+0xc) 0x1000/imm32/file-buffer-size # Stream-size + 4 for fd
# out-addr->fd = fd
89/<- *edi 1/r32/ecx
$open:end:
# . reclaim locals
01/add-to %esp 2/r32/edx
81 0/subop/add %esp 0xc/imm32
# . restore registers
5f/pop-to-edi
5e/pop-to-esi
5b/pop-to-ebx
5a/pop-to-edx
59/pop-to-ecx
58/pop-to-eax
# . epilogue
89/<- %esp 5/r32/ebp
5d/pop-to-ebp
c3/return
populate-buffered-file-containing: # contents: (addr array byte), out: (addr handle buffered-file)
# . prologue
55/push-ebp
89/<- %ebp 4/r32/esp
# . save registers
50/push-eax
51/push-ecx
56/push-esi
57/push-edi
# esi = contents
8b/-> *(ebp+8) 6/r32/esi
# var n/ecx: int = len(contents)
8b/-> *esi 1/r32/ecx
# var stream/edi: (handle stream byte)
68/push 0/imm32
68/push 0/imm32
89/<- %edi 4/r32/esp
# allocate stream
(new-stream Heap %ecx 1 %edi)
# var stream-addr/edi: (addr stream byte) = lookup(stream)
(lookup *edi *(edi+4)) # => eax
89/<- %edi 0/r32/eax
# write contents to stream
(write %edi %esi)
# allocate buffered-file
(allocate Heap 0x110 *(ebp+0xc))
# var out-addr/eax: (addr buffered-file)
8b/-> *(ebp+0xc) 0/r32/eax
(lookup *eax *(eax+4)) # => eax
# out-addr->size = 256 bytes
c7 0/subop/copy *(eax+0xc) 0x100/imm32/file-buffer-size
# out-addr->fd = stream
89/<- *eax 7/r32/edi
$populate-buffered-file-containing:end:
# . reclaim locals
81 0/subop/add %esp 8/imm32
# . restore registers
5f/pop-to-edi
5e/pop-to-esi
59/pop-to-ecx
58/pop-to-eax
# . epilogue
89/<- %esp 5/r32/ebp
5d/pop-to-ebp
c3/return
new-buffered-file: # out: (addr handle buffered-file)
# . prologue
55/push-ebp
89/<- %ebp 4/r32/esp
# . save registers
50/push-eax
51/push-ecx
# var stream/ecx: (handle stream byte)
68/push 0/imm32
68/push 0/imm32
89/<- %ecx 4/r32/esp
# allocate stream
(new-stream Heap 0x100 1 %ecx)
# var stream-addr/ecx: (addr stream byte) = lookup(stream)
(lookup *ecx *(ecx+4)) # => eax
89/<- %ecx 0/r32/eax
# allocate buffered-file
(allocate Heap 0x110 *(ebp+8))
# var out-addr/eax: (addr buffered-file)
8b/-> *(ebp+8) 0/r32/eax
(lookup *eax *(eax+4)) # => eax
# out-addr->size = 256 bytes
c7 0/subop/copy *(eax+0xc) 0x100/imm32/file-buffer-size
# out-addr->fd = stream
89/<- *eax 1/r32/ecx
$new-buffered-file:end:
# . reclaim locals
81 0/subop/add %esp 8/imm32
# . restore registers
59/pop-to-ecx
58/pop-to-eax
# . epilogue
89/<- %esp 5/r32/ebp
5d/pop-to-ebp
c3/return
|