+ struct breakpoint *bp = malloc(sizeof *bp);
+ if (bp == NULL || breakpoint_init(bp, proc, addr, libsym) < 0) {
+ free(bp);
+ return NULL;
+ }
+
+ /* N.B. (and XXX): BP->addr might differ from ADDR. On ARM
+ * this is a real possibility. The problem here is that to
+ * create a return breakpoint ltrace calls get_return_addr and
+ * then insert_breakpoint_at. So get_return_addr needs to
+ * encode all the information necessary for breakpoint_init
+ * into the address itself, so ADDR is potentially
+ * mangled. */
+
+ struct breakpoint *tmp = insert_breakpoint(proc, bp);
+ if (tmp != bp) {
+ breakpoint_destroy(bp);
+ free(bp);
+ }
+ return tmp;
+}
+
+struct breakpoint *
+insert_breakpoint(struct process *proc, struct breakpoint *bp)
+{