xref: /qemu/accel/tcg/ldst_common.c.inc (revision 7653b1ea)
1/*
2 * Routines common to user and system emulation of load/store.
3 *
4 *  Copyright (c) 2003 Fabrice Bellard
5 *
6 * SPDX-License-Identifier: GPL-2.0-or-later
7 *
8 * This work is licensed under the terms of the GNU GPL, version 2 or later.
9 * See the COPYING file in the top-level directory.
10 */
11/*
12 * Load helpers for tcg-ldst.h
13 */
14
15tcg_target_ulong helper_ldub_mmu(CPUArchState *env, uint64_t addr,
16                                 MemOpIdx oi, uintptr_t retaddr)
17{
18    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_8);
19    return do_ld1_mmu(env_cpu(env), addr, oi, retaddr, MMU_DATA_LOAD);
20}
21
22tcg_target_ulong helper_lduw_mmu(CPUArchState *env, uint64_t addr,
23                                 MemOpIdx oi, uintptr_t retaddr)
24{
25    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_16);
26    return do_ld2_mmu(env_cpu(env), addr, oi, retaddr, MMU_DATA_LOAD);
27}
28
29tcg_target_ulong helper_ldul_mmu(CPUArchState *env, uint64_t addr,
30                                 MemOpIdx oi, uintptr_t retaddr)
31{
32    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_32);
33    return do_ld4_mmu(env_cpu(env), addr, oi, retaddr, MMU_DATA_LOAD);
34}
35
36uint64_t helper_ldq_mmu(CPUArchState *env, uint64_t addr,
37                        MemOpIdx oi, uintptr_t retaddr)
38{
39    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_64);
40    return do_ld8_mmu(env_cpu(env), addr, oi, retaddr, MMU_DATA_LOAD);
41}
42
43/*
44 * Provide signed versions of the load routines as well.  We can of course
45 * avoid this for 64-bit data, or for 32-bit data on 32-bit host.
46 */
47
48tcg_target_ulong helper_ldsb_mmu(CPUArchState *env, uint64_t addr,
49                                 MemOpIdx oi, uintptr_t retaddr)
50{
51    return (int8_t)helper_ldub_mmu(env, addr, oi, retaddr);
52}
53
54tcg_target_ulong helper_ldsw_mmu(CPUArchState *env, uint64_t addr,
55                                 MemOpIdx oi, uintptr_t retaddr)
56{
57    return (int16_t)helper_lduw_mmu(env, addr, oi, retaddr);
58}
59
60tcg_target_ulong helper_ldsl_mmu(CPUArchState *env, uint64_t addr,
61                                 MemOpIdx oi, uintptr_t retaddr)
62{
63    return (int32_t)helper_ldul_mmu(env, addr, oi, retaddr);
64}
65
66Int128 helper_ld16_mmu(CPUArchState *env, uint64_t addr,
67                       MemOpIdx oi, uintptr_t retaddr)
68{
69    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_128);
70    return do_ld16_mmu(env_cpu(env), addr, oi, retaddr);
71}
72
73Int128 helper_ld_i128(CPUArchState *env, uint64_t addr, uint32_t oi)
74{
75    return helper_ld16_mmu(env, addr, oi, GETPC());
76}
77
78/*
79 * Store helpers for tcg-ldst.h
80 */
81
82void helper_stb_mmu(CPUArchState *env, uint64_t addr, uint32_t val,
83                    MemOpIdx oi, uintptr_t ra)
84{
85    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_8);
86    do_st1_mmu(env_cpu(env), addr, val, oi, ra);
87}
88
89void helper_stw_mmu(CPUArchState *env, uint64_t addr, uint32_t val,
90                    MemOpIdx oi, uintptr_t retaddr)
91{
92    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_16);
93    do_st2_mmu(env_cpu(env), addr, val, oi, retaddr);
94}
95
96void helper_stl_mmu(CPUArchState *env, uint64_t addr, uint32_t val,
97                    MemOpIdx oi, uintptr_t retaddr)
98{
99    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_32);
100    do_st4_mmu(env_cpu(env), addr, val, oi, retaddr);
101}
102
103void helper_stq_mmu(CPUArchState *env, uint64_t addr, uint64_t val,
104                    MemOpIdx oi, uintptr_t retaddr)
105{
106    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_64);
107    do_st8_mmu(env_cpu(env), addr, val, oi, retaddr);
108}
109
110void helper_st16_mmu(CPUArchState *env, uint64_t addr, Int128 val,
111                     MemOpIdx oi, uintptr_t retaddr)
112{
113    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_128);
114    do_st16_mmu(env_cpu(env), addr, val, oi, retaddr);
115}
116
117void helper_st_i128(CPUArchState *env, uint64_t addr, Int128 val, MemOpIdx oi)
118{
119    helper_st16_mmu(env, addr, val, oi, GETPC());
120}
121
122/*
123 * Load helpers for cpu_ldst.h
124 */
125
126static void plugin_load_cb(CPUArchState *env, abi_ptr addr, MemOpIdx oi)
127{
128    qemu_plugin_vcpu_mem_cb(env_cpu(env), addr, oi, QEMU_PLUGIN_MEM_R);
129}
130
131uint8_t cpu_ldb_mmu(CPUArchState *env, abi_ptr addr, MemOpIdx oi, uintptr_t ra)
132{
133    uint8_t ret;
134
135    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_UB);
136    ret = do_ld1_mmu(env_cpu(env), addr, oi, ra, MMU_DATA_LOAD);
137    plugin_load_cb(env, addr, oi);
138    return ret;
139}
140
141uint16_t cpu_ldw_mmu(CPUArchState *env, abi_ptr addr,
142                     MemOpIdx oi, uintptr_t ra)
143{
144    uint16_t ret;
145
146    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_16);
147    ret = do_ld2_mmu(env_cpu(env), addr, oi, ra, MMU_DATA_LOAD);
148    plugin_load_cb(env, addr, oi);
149    return ret;
150}
151
152uint32_t cpu_ldl_mmu(CPUArchState *env, abi_ptr addr,
153                     MemOpIdx oi, uintptr_t ra)
154{
155    uint32_t ret;
156
157    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_32);
158    ret = do_ld4_mmu(env_cpu(env), addr, oi, ra, MMU_DATA_LOAD);
159    plugin_load_cb(env, addr, oi);
160    return ret;
161}
162
163uint64_t cpu_ldq_mmu(CPUArchState *env, abi_ptr addr,
164                     MemOpIdx oi, uintptr_t ra)
165{
166    uint64_t ret;
167
168    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_64);
169    ret = do_ld8_mmu(env_cpu(env), addr, oi, ra, MMU_DATA_LOAD);
170    plugin_load_cb(env, addr, oi);
171    return ret;
172}
173
174Int128 cpu_ld16_mmu(CPUArchState *env, abi_ptr addr,
175                    MemOpIdx oi, uintptr_t ra)
176{
177    Int128 ret;
178
179    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_128);
180    ret = do_ld16_mmu(env_cpu(env), addr, oi, ra);
181    plugin_load_cb(env, addr, oi);
182    return ret;
183}
184
185/*
186 * Store helpers for cpu_ldst.h
187 */
188
189static void plugin_store_cb(CPUArchState *env, abi_ptr addr, MemOpIdx oi)
190{
191    qemu_plugin_vcpu_mem_cb(env_cpu(env), addr, oi, QEMU_PLUGIN_MEM_W);
192}
193
194void cpu_stb_mmu(CPUArchState *env, abi_ptr addr, uint8_t val,
195                 MemOpIdx oi, uintptr_t retaddr)
196{
197    helper_stb_mmu(env, addr, val, oi, retaddr);
198    plugin_store_cb(env, addr, oi);
199}
200
201void cpu_stw_mmu(CPUArchState *env, abi_ptr addr, uint16_t val,
202                 MemOpIdx oi, uintptr_t retaddr)
203{
204    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_16);
205    do_st2_mmu(env_cpu(env), addr, val, oi, retaddr);
206    plugin_store_cb(env, addr, oi);
207}
208
209void cpu_stl_mmu(CPUArchState *env, abi_ptr addr, uint32_t val,
210                    MemOpIdx oi, uintptr_t retaddr)
211{
212    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_32);
213    do_st4_mmu(env_cpu(env), addr, val, oi, retaddr);
214    plugin_store_cb(env, addr, oi);
215}
216
217void cpu_stq_mmu(CPUArchState *env, abi_ptr addr, uint64_t val,
218                 MemOpIdx oi, uintptr_t retaddr)
219{
220    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_64);
221    do_st8_mmu(env_cpu(env), addr, val, oi, retaddr);
222    plugin_store_cb(env, addr, oi);
223}
224
225void cpu_st16_mmu(CPUArchState *env, abi_ptr addr, Int128 val,
226                  MemOpIdx oi, uintptr_t retaddr)
227{
228    tcg_debug_assert((get_memop(oi) & MO_SIZE) == MO_128);
229    do_st16_mmu(env_cpu(env), addr, val, oi, retaddr);
230    plugin_store_cb(env, addr, oi);
231}
232
233/*
234 * Wrappers of the above
235 */
236
237uint32_t cpu_ldub_mmuidx_ra(CPUArchState *env, abi_ptr addr,
238                            int mmu_idx, uintptr_t ra)
239{
240    MemOpIdx oi = make_memop_idx(MO_UB, mmu_idx);
241    return cpu_ldb_mmu(env, addr, oi, ra);
242}
243
244int cpu_ldsb_mmuidx_ra(CPUArchState *env, abi_ptr addr,
245                       int mmu_idx, uintptr_t ra)
246{
247    return (int8_t)cpu_ldub_mmuidx_ra(env, addr, mmu_idx, ra);
248}
249
250uint32_t cpu_lduw_be_mmuidx_ra(CPUArchState *env, abi_ptr addr,
251                               int mmu_idx, uintptr_t ra)
252{
253    MemOpIdx oi = make_memop_idx(MO_BEUW | MO_UNALN, mmu_idx);
254    return cpu_ldw_mmu(env, addr, oi, ra);
255}
256
257int cpu_ldsw_be_mmuidx_ra(CPUArchState *env, abi_ptr addr,
258                          int mmu_idx, uintptr_t ra)
259{
260    return (int16_t)cpu_lduw_be_mmuidx_ra(env, addr, mmu_idx, ra);
261}
262
263uint32_t cpu_ldl_be_mmuidx_ra(CPUArchState *env, abi_ptr addr,
264                              int mmu_idx, uintptr_t ra)
265{
266    MemOpIdx oi = make_memop_idx(MO_BEUL | MO_UNALN, mmu_idx);
267    return cpu_ldl_mmu(env, addr, oi, ra);
268}
269
270uint64_t cpu_ldq_be_mmuidx_ra(CPUArchState *env, abi_ptr addr,
271                              int mmu_idx, uintptr_t ra)
272{
273    MemOpIdx oi = make_memop_idx(MO_BEUQ | MO_UNALN, mmu_idx);
274    return cpu_ldq_mmu(env, addr, oi, ra);
275}
276
277uint32_t cpu_lduw_le_mmuidx_ra(CPUArchState *env, abi_ptr addr,
278                               int mmu_idx, uintptr_t ra)
279{
280    MemOpIdx oi = make_memop_idx(MO_LEUW | MO_UNALN, mmu_idx);
281    return cpu_ldw_mmu(env, addr, oi, ra);
282}
283
284int cpu_ldsw_le_mmuidx_ra(CPUArchState *env, abi_ptr addr,
285                          int mmu_idx, uintptr_t ra)
286{
287    return (int16_t)cpu_lduw_le_mmuidx_ra(env, addr, mmu_idx, ra);
288}
289
290uint32_t cpu_ldl_le_mmuidx_ra(CPUArchState *env, abi_ptr addr,
291                              int mmu_idx, uintptr_t ra)
292{
293    MemOpIdx oi = make_memop_idx(MO_LEUL | MO_UNALN, mmu_idx);
294    return cpu_ldl_mmu(env, addr, oi, ra);
295}
296
297uint64_t cpu_ldq_le_mmuidx_ra(CPUArchState *env, abi_ptr addr,
298                              int mmu_idx, uintptr_t ra)
299{
300    MemOpIdx oi = make_memop_idx(MO_LEUQ | MO_UNALN, mmu_idx);
301    return cpu_ldq_mmu(env, addr, oi, ra);
302}
303
304void cpu_stb_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint32_t val,
305                       int mmu_idx, uintptr_t ra)
306{
307    MemOpIdx oi = make_memop_idx(MO_UB, mmu_idx);
308    cpu_stb_mmu(env, addr, val, oi, ra);
309}
310
311void cpu_stw_be_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint32_t val,
312                          int mmu_idx, uintptr_t ra)
313{
314    MemOpIdx oi = make_memop_idx(MO_BEUW | MO_UNALN, mmu_idx);
315    cpu_stw_mmu(env, addr, val, oi, ra);
316}
317
318void cpu_stl_be_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint32_t val,
319                          int mmu_idx, uintptr_t ra)
320{
321    MemOpIdx oi = make_memop_idx(MO_BEUL | MO_UNALN, mmu_idx);
322    cpu_stl_mmu(env, addr, val, oi, ra);
323}
324
325void cpu_stq_be_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint64_t val,
326                          int mmu_idx, uintptr_t ra)
327{
328    MemOpIdx oi = make_memop_idx(MO_BEUQ | MO_UNALN, mmu_idx);
329    cpu_stq_mmu(env, addr, val, oi, ra);
330}
331
332void cpu_stw_le_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint32_t val,
333                          int mmu_idx, uintptr_t ra)
334{
335    MemOpIdx oi = make_memop_idx(MO_LEUW | MO_UNALN, mmu_idx);
336    cpu_stw_mmu(env, addr, val, oi, ra);
337}
338
339void cpu_stl_le_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint32_t val,
340                          int mmu_idx, uintptr_t ra)
341{
342    MemOpIdx oi = make_memop_idx(MO_LEUL | MO_UNALN, mmu_idx);
343    cpu_stl_mmu(env, addr, val, oi, ra);
344}
345
346void cpu_stq_le_mmuidx_ra(CPUArchState *env, abi_ptr addr, uint64_t val,
347                          int mmu_idx, uintptr_t ra)
348{
349    MemOpIdx oi = make_memop_idx(MO_LEUQ | MO_UNALN, mmu_idx);
350    cpu_stq_mmu(env, addr, val, oi, ra);
351}
352
353/*--------------------------*/
354
355uint32_t cpu_ldub_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
356{
357    int mmu_index = cpu_mmu_index(env_cpu(env), false);
358    return cpu_ldub_mmuidx_ra(env, addr, mmu_index, ra);
359}
360
361int cpu_ldsb_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
362{
363    return (int8_t)cpu_ldub_data_ra(env, addr, ra);
364}
365
366uint32_t cpu_lduw_be_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
367{
368    int mmu_index = cpu_mmu_index(env_cpu(env), false);
369    return cpu_lduw_be_mmuidx_ra(env, addr, mmu_index, ra);
370}
371
372int cpu_ldsw_be_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
373{
374    return (int16_t)cpu_lduw_be_data_ra(env, addr, ra);
375}
376
377uint32_t cpu_ldl_be_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
378{
379    int mmu_index = cpu_mmu_index(env_cpu(env), false);
380    return cpu_ldl_be_mmuidx_ra(env, addr, mmu_index, ra);
381}
382
383uint64_t cpu_ldq_be_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
384{
385    int mmu_index = cpu_mmu_index(env_cpu(env), false);
386    return cpu_ldq_be_mmuidx_ra(env, addr, mmu_index, ra);
387}
388
389uint32_t cpu_lduw_le_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
390{
391    int mmu_index = cpu_mmu_index(env_cpu(env), false);
392    return cpu_lduw_le_mmuidx_ra(env, addr, mmu_index, ra);
393}
394
395int cpu_ldsw_le_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
396{
397    return (int16_t)cpu_lduw_le_data_ra(env, addr, ra);
398}
399
400uint32_t cpu_ldl_le_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
401{
402    int mmu_index = cpu_mmu_index(env_cpu(env), false);
403    return cpu_ldl_le_mmuidx_ra(env, addr, mmu_index, ra);
404}
405
406uint64_t cpu_ldq_le_data_ra(CPUArchState *env, abi_ptr addr, uintptr_t ra)
407{
408    int mmu_index = cpu_mmu_index(env_cpu(env), false);
409    return cpu_ldq_le_mmuidx_ra(env, addr, mmu_index, ra);
410}
411
412void cpu_stb_data_ra(CPUArchState *env, abi_ptr addr,
413                     uint32_t val, uintptr_t ra)
414{
415    int mmu_index = cpu_mmu_index(env_cpu(env), false);
416    cpu_stb_mmuidx_ra(env, addr, val, mmu_index, ra);
417}
418
419void cpu_stw_be_data_ra(CPUArchState *env, abi_ptr addr,
420                        uint32_t val, uintptr_t ra)
421{
422    int mmu_index = cpu_mmu_index(env_cpu(env), false);
423    cpu_stw_be_mmuidx_ra(env, addr, val, mmu_index, ra);
424}
425
426void cpu_stl_be_data_ra(CPUArchState *env, abi_ptr addr,
427                        uint32_t val, uintptr_t ra)
428{
429    int mmu_index = cpu_mmu_index(env_cpu(env), false);
430    cpu_stl_be_mmuidx_ra(env, addr, val, mmu_index, ra);
431}
432
433void cpu_stq_be_data_ra(CPUArchState *env, abi_ptr addr,
434                        uint64_t val, uintptr_t ra)
435{
436    int mmu_index = cpu_mmu_index(env_cpu(env), false);
437    cpu_stq_be_mmuidx_ra(env, addr, val, mmu_index, ra);
438}
439
440void cpu_stw_le_data_ra(CPUArchState *env, abi_ptr addr,
441                        uint32_t val, uintptr_t ra)
442{
443    int mmu_index = cpu_mmu_index(env_cpu(env), false);
444    cpu_stw_le_mmuidx_ra(env, addr, val, mmu_index, ra);
445}
446
447void cpu_stl_le_data_ra(CPUArchState *env, abi_ptr addr,
448                        uint32_t val, uintptr_t ra)
449{
450    int mmu_index = cpu_mmu_index(env_cpu(env), false);
451    cpu_stl_le_mmuidx_ra(env, addr, val, mmu_index, ra);
452}
453
454void cpu_stq_le_data_ra(CPUArchState *env, abi_ptr addr,
455                        uint64_t val, uintptr_t ra)
456{
457    int mmu_index = cpu_mmu_index(env_cpu(env), false);
458    cpu_stq_le_mmuidx_ra(env, addr, val, mmu_index, ra);
459}
460
461/*--------------------------*/
462
463uint32_t cpu_ldub_data(CPUArchState *env, abi_ptr addr)
464{
465    return cpu_ldub_data_ra(env, addr, 0);
466}
467
468int cpu_ldsb_data(CPUArchState *env, abi_ptr addr)
469{
470    return (int8_t)cpu_ldub_data(env, addr);
471}
472
473uint32_t cpu_lduw_be_data(CPUArchState *env, abi_ptr addr)
474{
475    return cpu_lduw_be_data_ra(env, addr, 0);
476}
477
478int cpu_ldsw_be_data(CPUArchState *env, abi_ptr addr)
479{
480    return (int16_t)cpu_lduw_be_data(env, addr);
481}
482
483uint32_t cpu_ldl_be_data(CPUArchState *env, abi_ptr addr)
484{
485    return cpu_ldl_be_data_ra(env, addr, 0);
486}
487
488uint64_t cpu_ldq_be_data(CPUArchState *env, abi_ptr addr)
489{
490    return cpu_ldq_be_data_ra(env, addr, 0);
491}
492
493uint32_t cpu_lduw_le_data(CPUArchState *env, abi_ptr addr)
494{
495    return cpu_lduw_le_data_ra(env, addr, 0);
496}
497
498int cpu_ldsw_le_data(CPUArchState *env, abi_ptr addr)
499{
500    return (int16_t)cpu_lduw_le_data(env, addr);
501}
502
503uint32_t cpu_ldl_le_data(CPUArchState *env, abi_ptr addr)
504{
505    return cpu_ldl_le_data_ra(env, addr, 0);
506}
507
508uint64_t cpu_ldq_le_data(CPUArchState *env, abi_ptr addr)
509{
510    return cpu_ldq_le_data_ra(env, addr, 0);
511}
512
513void cpu_stb_data(CPUArchState *env, abi_ptr addr, uint32_t val)
514{
515    cpu_stb_data_ra(env, addr, val, 0);
516}
517
518void cpu_stw_be_data(CPUArchState *env, abi_ptr addr, uint32_t val)
519{
520    cpu_stw_be_data_ra(env, addr, val, 0);
521}
522
523void cpu_stl_be_data(CPUArchState *env, abi_ptr addr, uint32_t val)
524{
525    cpu_stl_be_data_ra(env, addr, val, 0);
526}
527
528void cpu_stq_be_data(CPUArchState *env, abi_ptr addr, uint64_t val)
529{
530    cpu_stq_be_data_ra(env, addr, val, 0);
531}
532
533void cpu_stw_le_data(CPUArchState *env, abi_ptr addr, uint32_t val)
534{
535    cpu_stw_le_data_ra(env, addr, val, 0);
536}
537
538void cpu_stl_le_data(CPUArchState *env, abi_ptr addr, uint32_t val)
539{
540    cpu_stl_le_data_ra(env, addr, val, 0);
541}
542
543void cpu_stq_le_data(CPUArchState *env, abi_ptr addr, uint64_t val)
544{
545    cpu_stq_le_data_ra(env, addr, val, 0);
546}
547