1 /* SPDX-License-Identifier: GPL-2.0-or-later */
4 * Copyright (C) 2016 by Matthias Welwarsky <matthias.welwarsky@sysgo.com>
12 #include "target_type.h"
13 #include "arm_adi_v5.h"
16 #include <jtag/jtag.h>
18 #define MEM_AP_COMMON_MAGIC 0x4DE4DA50
22 struct adiv5_dap
*dap
;
27 static int mem_ap_target_create(struct target
*target
, Jim_Interp
*interp
)
29 struct mem_ap
*mem_ap
;
30 struct adiv5_private_config
*pc
;
32 pc
= (struct adiv5_private_config
*)target
->private_config
;
36 if (pc
->ap_num
== DP_APSEL_INVALID
) {
37 LOG_ERROR("AP number not specified");
41 mem_ap
= calloc(1, sizeof(struct mem_ap
));
43 LOG_ERROR("Out of memory");
47 mem_ap
->ap_num
= pc
->ap_num
;
48 mem_ap
->common_magic
= MEM_AP_COMMON_MAGIC
;
49 mem_ap
->dap
= pc
->dap
;
51 target
->arch_info
= mem_ap
;
53 if (!target
->gdb_port_override
)
54 target
->gdb_port_override
= strdup("disabled");
59 static int mem_ap_init_target(struct command_context
*cmd_ctx
, struct target
*target
)
61 LOG_DEBUG("%s", __func__
);
62 target
->state
= TARGET_UNKNOWN
;
63 target
->debug_reason
= DBG_REASON_UNDEFINED
;
67 static void mem_ap_deinit_target(struct target
*target
)
69 struct mem_ap
*mem_ap
= target
->arch_info
;
71 LOG_DEBUG("%s", __func__
);
74 dap_put_ap(mem_ap
->ap
);
76 free(target
->private_config
);
77 free(target
->arch_info
);
81 static int mem_ap_arch_state(struct target
*target
)
83 LOG_DEBUG("%s", __func__
);
87 static int mem_ap_poll(struct target
*target
)
89 if (target
->state
== TARGET_UNKNOWN
) {
90 target
->state
= TARGET_RUNNING
;
91 target
->debug_reason
= DBG_REASON_NOTHALTED
;
97 static int mem_ap_halt(struct target
*target
)
99 LOG_DEBUG("%s", __func__
);
100 target
->state
= TARGET_HALTED
;
101 target
->debug_reason
= DBG_REASON_DBGRQ
;
102 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
106 static int mem_ap_resume(struct target
*target
, int current
, target_addr_t address
,
107 int handle_breakpoints
, int debug_execution
)
109 LOG_DEBUG("%s", __func__
);
110 target
->state
= TARGET_RUNNING
;
111 target
->debug_reason
= DBG_REASON_NOTHALTED
;
115 static int mem_ap_step(struct target
*target
, int current
, target_addr_t address
,
116 int handle_breakpoints
)
118 LOG_DEBUG("%s", __func__
);
119 target
->state
= TARGET_HALTED
;
120 target
->debug_reason
= DBG_REASON_DBGRQ
;
121 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
125 static int mem_ap_assert_reset(struct target
*target
)
127 target
->state
= TARGET_RESET
;
128 target
->debug_reason
= DBG_REASON_UNDEFINED
;
130 LOG_DEBUG("%s", __func__
);
134 static int mem_ap_examine(struct target
*target
)
136 struct mem_ap
*mem_ap
= target
->arch_info
;
138 if (!target_was_examined(target
)) {
140 dap_put_ap(mem_ap
->ap
);
144 mem_ap
->ap
= dap_get_ap(mem_ap
->dap
, mem_ap
->ap_num
);
146 LOG_ERROR("Cannot get AP");
149 target_set_examined(target
);
150 target
->state
= TARGET_UNKNOWN
;
151 target
->debug_reason
= DBG_REASON_UNDEFINED
;
152 return mem_ap_init(mem_ap
->ap
);
158 static int mem_ap_deassert_reset(struct target
*target
)
160 if (target
->reset_halt
) {
161 target
->state
= TARGET_HALTED
;
162 target
->debug_reason
= DBG_REASON_DBGRQ
;
163 target_call_event_callbacks(target
, TARGET_EVENT_HALTED
);
165 target
->state
= TARGET_RUNNING
;
166 target
->debug_reason
= DBG_REASON_NOTHALTED
;
169 LOG_DEBUG("%s", __func__
);
173 static int mem_ap_reg_get(struct reg
*reg
)
178 static int mem_ap_reg_set(struct reg
*reg
, uint8_t *buf
)
183 static struct reg_arch_type mem_ap_reg_arch_type
= {
184 .get
= mem_ap_reg_get
,
185 .set
= mem_ap_reg_set
,
188 const char *mem_ap_get_gdb_arch(struct target
*target
)
194 * Dummy ARM register emulation:
195 * reg[0..15]: 32 bits, r0~r12, sp, lr, pc
196 * reg[16..23]: 96 bits, f0~f7
197 * reg[24]: 32 bits, fps
198 * reg[25]: 32 bits, cpsr
200 * Set 'exist' only to reg[0..15], so initial response to GDB is correct
203 #define MAX_REG_SIZE 96
204 #define REG_EXIST(n) ((n) < 16)
205 #define REG_SIZE(n) ((((n) >= 16) && ((n) < 24)) ? 96 : 32)
207 struct mem_ap_alloc_reg_list
{
208 /* reg_list must be the first field */
209 struct reg
*reg_list
[NUM_REGS
];
210 struct reg regs
[NUM_REGS
];
211 uint8_t regs_value
[MAX_REG_SIZE
/ 8];
214 static int mem_ap_get_gdb_reg_list(struct target
*target
, struct reg
**reg_list
[],
215 int *reg_list_size
, enum target_register_class reg_class
)
217 struct mem_ap_alloc_reg_list
*mem_ap_alloc
= calloc(1, sizeof(struct mem_ap_alloc_reg_list
));
219 LOG_ERROR("Out of memory");
223 *reg_list
= mem_ap_alloc
->reg_list
;
224 *reg_list_size
= NUM_REGS
;
225 struct reg
*regs
= mem_ap_alloc
->regs
;
227 for (int i
= 0; i
< NUM_REGS
; i
++) {
229 regs
[i
].value
= mem_ap_alloc
->regs_value
;
230 regs
[i
].size
= REG_SIZE(i
);
231 regs
[i
].exist
= REG_EXIST(i
);
232 regs
[i
].type
= &mem_ap_reg_arch_type
;
233 (*reg_list
)[i
] = ®s
[i
];
239 static int mem_ap_read_memory(struct target
*target
, target_addr_t address
,
240 uint32_t size
, uint32_t count
, uint8_t *buffer
)
242 struct mem_ap
*mem_ap
= target
->arch_info
;
244 LOG_DEBUG("Reading memory at physical address " TARGET_ADDR_FMT
245 "; size %" PRIu32
"; count %" PRIu32
, address
, size
, count
);
247 if (count
== 0 || !buffer
)
248 return ERROR_COMMAND_SYNTAX_ERROR
;
250 return mem_ap_read_buf(mem_ap
->ap
, buffer
, size
, count
, address
);
253 static int mem_ap_write_memory(struct target
*target
, target_addr_t address
,
254 uint32_t size
, uint32_t count
,
255 const uint8_t *buffer
)
257 struct mem_ap
*mem_ap
= target
->arch_info
;
259 LOG_DEBUG("Writing memory at physical address " TARGET_ADDR_FMT
260 "; size %" PRIu32
"; count %" PRIu32
, address
, size
, count
);
262 if (count
== 0 || !buffer
)
263 return ERROR_COMMAND_SYNTAX_ERROR
;
265 return mem_ap_write_buf(mem_ap
->ap
, buffer
, size
, count
, address
);
268 struct target_type mem_ap_target
= {
271 .target_create
= mem_ap_target_create
,
272 .init_target
= mem_ap_init_target
,
273 .deinit_target
= mem_ap_deinit_target
,
274 .examine
= mem_ap_examine
,
275 .target_jim_configure
= adiv5_jim_configure
,
278 .arch_state
= mem_ap_arch_state
,
281 .resume
= mem_ap_resume
,
284 .assert_reset
= mem_ap_assert_reset
,
285 .deassert_reset
= mem_ap_deassert_reset
,
287 .get_gdb_arch
= mem_ap_get_gdb_arch
,
288 .get_gdb_reg_list
= mem_ap_get_gdb_reg_list
,
290 .read_memory
= mem_ap_read_memory
,
291 .write_memory
= mem_ap_write_memory
,