Lines Matching +full:multi +full:- +full:attr

1 // SPDX-License-Identifier: GPL-2.0-only
16 #include <linux/bpf-cgroup.h>
22 #include "../cgroup/cgroup-internal.h"
76 array = rcu_dereference(cgrp->effective[atype]);
77 item = &array->items[0];
79 while ((prog = READ_ONCE(item->prog))) {
87 run_ctx.retval = -EPERM;
107 shim_prog = (const struct bpf_prog *)((void *)insn - offsetof(struct bpf_prog, insnsi));
109 cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
111 ret = bpf_prog_run_array_cg(&cgrp->bpf,
112 shim_prog->aux->cgroup_atype,
129 shim_prog = (const struct bpf_prog *)((void *)insn - offsetof(struct bpf_prog, insnsi));
131 cgrp = sock_cgroup_ptr(&sock->sk->sk_cgrp_data);
133 ret = bpf_prog_run_array_cg(&cgrp->bpf,
134 shim_prog->aux->cgroup_atype,
147 shim_prog = (const struct bpf_prog *)((void *)insn - offsetof(struct bpf_prog, insnsi));
152 ret = bpf_prog_run_array_cg(&cgrp->bpf,
153 shim_prog->aux->cgroup_atype,
184 return -E2BIG;
190 int i = cgroup_atype - CGROUP_LSM_START;
203 int i = cgroup_atype - CGROUP_LSM_START;
206 if (--cgroup_lsm_atype[i].refcnt <= 0)
217 return -EOPNOTSUPP;
224 percpu_ref_kill(&cgrp->bpf.refcnt);
249 map = prog->aux->cgroup_storage[stype];
260 return -ENOMEM;
288 /* Called when bpf_cgroup_link is auto-detached from dying cgroup.
295 cgroup_put(link->cgroup);
296 link->cgroup = NULL;
300 * cgroup_bpf_release() - put references of all bpf programs and
309 struct list_head *storages = &cgrp->bpf.storages;
316 for (atype = 0; atype < ARRAY_SIZE(cgrp->bpf.progs); atype++) {
317 struct hlist_head *progs = &cgrp->bpf.progs[atype];
322 hlist_del(&pl->node);
323 if (pl->prog) {
324 if (pl->prog->expected_attach_type == BPF_LSM_CGROUP)
325 bpf_trampoline_unlink_cgroup_shim(pl->prog);
326 bpf_prog_put(pl->prog);
328 if (pl->link) {
329 if (pl->link->link.prog->expected_attach_type == BPF_LSM_CGROUP)
330 bpf_trampoline_unlink_cgroup_shim(pl->link->link.prog);
331 bpf_cgroup_link_auto_detach(pl->link);
337 cgrp->bpf.effective[atype],
352 percpu_ref_exit(&cgrp->bpf.refcnt);
357 * cgroup_bpf_release_fn() - callback used to schedule releasing
365 INIT_WORK(&cgrp->bpf.release_work, cgroup_bpf_release);
366 queue_work(cgroup_bpf_destroy_wq, &cgrp->bpf.release_work);
374 if (pl->prog)
375 return pl->prog;
376 if (pl->link)
377 return pl->link->link.prog;
392 if (preorder_cnt && (pl->flags & BPF_F_PREORDER))
399 /* if parent has non-overridable prog attached,
401 * if parent has overridable or multi-prog, allow attaching
412 u32 flags = p->bpf.flags[atype];
417 cnt = prog_list_length(&p->bpf.progs[atype], NULL);
429 * Note that parent's F_ALLOW_OVERRIDE-type program is yielding
444 if (cnt == 0 || (p->bpf.flags[atype] & BPF_F_ALLOW_MULTI))
445 cnt += prog_list_length(&p->bpf.progs[atype], &preorder_cnt);
451 return -ENOMEM;
457 bstart = preorder_cnt - 1;
459 if (cnt > 0 && !(p->bpf.flags[atype] & BPF_F_ALLOW_MULTI))
463 hlist_for_each_entry(pl, &p->bpf.progs[atype], node) {
467 if (pl->flags & BPF_F_PREORDER) {
468 item = &progs->items[bstart];
469 bstart--;
471 item = &progs->items[fstart];
474 item->prog = prog_list_prog(pl);
475 bpf_cgroup_storages_assign(item->cgroup_storage,
476 pl->storage);
480 /* reverse pre-ordering progs at this cgroup level */
481 for (i = bstart + 1, j = init_bstart; i < j; i++, j--)
482 swap(progs->items[i], progs->items[j]);
494 old_array = rcu_replace_pointer(cgrp->bpf.effective[atype], old_array,
503 * cgroup_bpf_inherit() - inherit effective programs from parent
511 #define NR ARRAY_SIZE(cgrp->bpf.effective)
516 ret = percpu_ref_init(&cgrp->bpf.refcnt, cgroup_bpf_release_fn, 0,
525 INIT_HLIST_HEAD(&cgrp->bpf.progs[i]);
527 INIT_LIST_HEAD(&cgrp->bpf.storages);
544 percpu_ref_exit(&cgrp->bpf.refcnt);
546 return -ENOMEM;
555 if (cgrp->root != &cgrp_dfl_root)
577 css_for_each_descendant_pre(css, &cgrp->self) {
580 if (percpu_ref_is_zero(&desc->bpf.refcnt))
583 err = compute_effective_progs(desc, atype, &desc->bpf.inactive);
589 css_for_each_descendant_pre(css, &cgrp->self) {
592 if (percpu_ref_is_zero(&desc->bpf.refcnt)) {
593 if (unlikely(desc->bpf.inactive)) {
594 bpf_prog_array_free(desc->bpf.inactive);
595 desc->bpf.inactive = NULL;
600 activate_effective_progs(desc, atype, desc->bpf.inactive);
601 desc->bpf.inactive = NULL;
610 css_for_each_descendant_pre(css, &cgrp->self) {
613 bpf_prog_array_free(desc->bpf.inactive);
614 desc->bpf.inactive = NULL;
630 /* single-attach case */
634 return hlist_entry(progs->first, typeof(*pl), node);
638 if (prog && pl->prog == prog && prog != replace_prog)
640 return ERR_PTR(-EINVAL);
641 if (link && pl->link == link)
643 return ERR_PTR(-EINVAL);
646 /* direct prog multi-attach w/ replacement case */
649 if (pl->prog == replace_prog)
654 return ERR_PTR(-ENOENT);
662 struct bpf_link *link = ERR_PTR(-EINVAL);
673 struct bpf_prog *prog = ERR_PTR(-EINVAL);
686 struct bpf_prog_list *pltmp, *pl = ERR_PTR(-EINVAL);
697 return ERR_PTR(-EINVAL);
699 return ERR_PTR(-EINVAL);
703 return ERR_PTR(-EINVAL);
724 if (pltmp->node.next)
732 if ((anchor_prog && anchor_prog == pltmp->prog) ||
733 (anchor_link && anchor_link == &pltmp->link->link)) {
734 if (!!(pltmp->flags & BPF_F_PREORDER) != preorder)
741 pl = ERR_PTR(-ENOENT);
761 hlist_add_head(&pl->node, progs);
763 hlist_add_before(&pl->node, &pltmp->node);
765 hlist_add_behind(&pl->node, &pltmp->node);
771 * __cgroup_bpf_attach() - Attach the program or the link to a cgroup, and
782 * Exactly one of @prog or @link can be non-null.
795 struct bpf_prog *new_prog = prog ? : link->link.prog;
804 return -EINVAL;
807 return -EINVAL;
810 return -EINVAL;
813 return -EINVAL;
815 atype = bpf_cgroup_atype_find(type, new_prog->aux->attach_btf_id);
817 return -EINVAL;
818 if (revision && revision != cgrp->bpf.revisions[atype])
819 return -ESTALE;
821 progs = &cgrp->bpf.progs[atype];
824 return -EPERM;
826 if (!hlist_empty(progs) && cgrp->bpf.flags[atype] != saved_flags)
827 /* Disallow attaching non-overridable on top
829 * Disallow attaching multi-prog if overridable or none
831 return -EPERM;
834 return -E2BIG;
842 prog ? : link->link.prog, cgrp))
843 return -ENOMEM;
846 old_prog = pl->prog;
851 return -ENOMEM;
862 pl->prog = prog;
863 pl->link = link;
864 pl->flags = flags;
865 bpf_cgroup_storages_assign(pl->storage, storage);
866 cgrp->bpf.flags[atype] = saved_flags;
878 cgrp->bpf.revisions[atype] += 1;
895 pl->prog = old_prog;
896 pl->link = NULL;
900 hlist_del(&pl->node);
936 css_for_each_descendant_pre(css, &cgrp->self) {
939 if (percpu_ref_is_zero(&desc->bpf.refcnt))
944 if (pos && !(cg->bpf.flags[atype] & BPF_F_ALLOW_MULTI))
947 head = &cg->bpf.progs[atype];
951 if (pl->link == link)
959 desc->bpf.effective[atype],
961 item = &progs->items[pos];
962 WRITE_ONCE(item->prog, link->link.prog);
967 * __cgroup_bpf_replace() - Replace link's program and propagate the change
986 atype = bpf_cgroup_atype_find(link->link.attach_type, new_prog->aux->attach_btf_id);
988 return -EINVAL;
990 progs = &cgrp->bpf.progs[atype];
992 if (link->link.prog->type != new_prog->type)
993 return -EINVAL;
996 if (pl->link == link) {
1002 return -ENOENT;
1004 cgrp->bpf.revisions[atype] += 1;
1005 old_prog = xchg(&link->link.prog, new_prog);
1020 /* link might have been auto-released by dying cgroup, so fail */
1021 if (!cg_link->cgroup) {
1022 ret = -ENOLINK;
1025 if (old_prog && link->prog != old_prog) {
1026 ret = -EPERM;
1029 ret = __cgroup_bpf_replace(cg_link->cgroup, cg_link, new_prog);
1045 return ERR_PTR(-ENOENT);
1050 return hlist_entry(progs->first, typeof(*pl), node);
1054 /* to detach MULTI prog the user has to specify valid FD
1057 return ERR_PTR(-EINVAL);
1061 if (pl->prog == prog && pl->link == link)
1064 return ERR_PTR(-ENOENT);
1068 * purge_effective_progs() - After compute_effective_progs fails to alloc new
1069 * cgrp->bpf.inactive table we can recover by
1089 css_for_each_descendant_pre(css, &cgrp->self) {
1092 if (percpu_ref_is_zero(&desc->bpf.refcnt))
1097 if (pos && !(cg->bpf.flags[atype] & BPF_F_ALLOW_MULTI))
1100 head = &cg->bpf.progs[atype];
1104 if (pl->prog == prog && pl->link == link)
1114 desc->bpf.effective[atype],
1124 * __cgroup_bpf_detach() - Detach the program or link from a cgroup, and
1132 * At most one of @prog or @link can be non-NULL.
1147 attach_btf_id = prog->aux->attach_btf_id;
1149 attach_btf_id = link->link.prog->aux->attach_btf_id;
1153 return -EINVAL;
1155 if (revision && revision != cgrp->bpf.revisions[atype])
1156 return -ESTALE;
1158 progs = &cgrp->bpf.progs[atype];
1159 flags = cgrp->bpf.flags[atype];
1163 return -EINVAL;
1170 old_prog = pl->prog;
1171 pl->prog = NULL;
1172 pl->link = NULL;
1176 pl->prog = old_prog;
1177 pl->link = link;
1182 hlist_del(&pl->node);
1183 cgrp->bpf.revisions[atype] += 1;
1188 cgrp->bpf.flags[atype] = 0;
1210 static int __cgroup_bpf_query(struct cgroup *cgrp, const union bpf_attr *attr,
1213 __u32 __user *prog_attach_flags = u64_to_user_ptr(attr->query.prog_attach_flags);
1214 bool effective_query = attr->query.query_flags & BPF_F_QUERY_EFFECTIVE;
1215 __u32 __user *prog_ids = u64_to_user_ptr(attr->query.prog_ids);
1216 enum bpf_attach_type type = attr->query.attach_type;
1226 return -EINVAL;
1229 if (!effective_query && attr->query.prog_cnt &&
1231 return -EINVAL;
1239 return -EINVAL;
1241 flags = cgrp->bpf.flags[from_atype];
1246 effective = rcu_dereference_protected(cgrp->bpf.effective[atype],
1250 total_cnt += prog_list_length(&cgrp->bpf.progs[atype], NULL);
1254 /* always output uattr->query.attach_flags as 0 during effective query */
1256 if (copy_to_user(&uattr->query.attach_flags, &flags, sizeof(flags)))
1257 return -EFAULT;
1258 if (copy_to_user(&uattr->query.prog_cnt, &total_cnt, sizeof(total_cnt)))
1259 return -EFAULT;
1261 revision = cgrp->bpf.revisions[from_atype];
1262 if (copy_to_user(&uattr->query.revision, &revision, sizeof(revision)))
1263 return -EFAULT;
1264 if (attr->query.prog_cnt == 0 || !prog_ids || !total_cnt)
1268 if (attr->query.prog_cnt < total_cnt) {
1269 total_cnt = attr->query.prog_cnt;
1270 ret = -ENOSPC;
1275 effective = rcu_dereference_protected(cgrp->bpf.effective[atype],
1285 progs = &cgrp->bpf.progs[atype];
1290 id = prog->aux->id;
1292 return -EFAULT;
1298 flags = cgrp->bpf.flags[atype];
1303 return -EFAULT;
1309 total_cnt -= cnt;
1314 static int cgroup_bpf_query(struct cgroup *cgrp, const union bpf_attr *attr,
1320 ret = __cgroup_bpf_query(cgrp, attr, uattr);
1325 int cgroup_bpf_prog_attach(const union bpf_attr *attr,
1332 cgrp = cgroup_get_from_fd(attr->target_fd);
1336 if ((attr->attach_flags & BPF_F_ALLOW_MULTI) &&
1337 (attr->attach_flags & BPF_F_REPLACE)) {
1338 replace_prog = bpf_prog_get_type(attr->replace_bpf_fd, ptype);
1346 attr->attach_type, attr->attach_flags,
1347 attr->relative_fd, attr->expected_revision);
1355 int cgroup_bpf_prog_detach(const union bpf_attr *attr, enum bpf_prog_type ptype)
1361 cgrp = cgroup_get_from_fd(attr->target_fd);
1365 prog = bpf_prog_get_type(attr->attach_bpf_fd, ptype);
1369 ret = cgroup_bpf_detach(cgrp, prog, attr->attach_type, attr->expected_revision);
1383 /* link might have been auto-detached by dying cgroup already,
1386 if (!cg_link->cgroup)
1391 /* re-check cgroup under lock again */
1392 if (!cg_link->cgroup) {
1397 WARN_ON(__cgroup_bpf_detach(cg_link->cgroup, NULL, cg_link,
1398 link->attach_type, 0));
1399 if (link->attach_type == BPF_LSM_CGROUP)
1400 bpf_trampoline_unlink_cgroup_shim(cg_link->link.prog);
1402 cg = cg_link->cgroup;
1403 cg_link->cgroup = NULL;
1433 if (cg_link->cgroup)
1434 cg_id = cgroup_id(cg_link->cgroup);
1441 link->attach_type);
1452 if (cg_link->cgroup)
1453 cg_id = cgroup_id(cg_link->cgroup);
1456 info->cgroup.cgroup_id = cg_id;
1457 info->cgroup.attach_type = link->attach_type;
1477 int cgroup_bpf_link_attach(const union bpf_attr *attr, struct bpf_prog *prog)
1484 if (attr->link_create.flags & (~BPF_F_LINK_ATTACH_MASK))
1485 return -EINVAL;
1487 cgrp = cgroup_get_from_fd(attr->link_create.target_fd);
1493 err = -ENOMEM;
1496 bpf_link_init(&link->link, BPF_LINK_TYPE_CGROUP, &bpf_cgroup_link_lops,
1497 prog, attr->link_create.attach_type);
1498 link->cgroup = cgrp;
1500 err = bpf_link_prime(&link->link, &link_primer);
1507 link->link.attach_type, BPF_F_ALLOW_MULTI | attr->link_create.flags,
1508 attr->link_create.cgroup.relative_fd,
1509 attr->link_create.cgroup.expected_revision);
1522 int cgroup_bpf_prog_query(const union bpf_attr *attr,
1528 cgrp = cgroup_get_from_fd(attr->query.target_fd);
1532 ret = cgroup_bpf_query(cgrp, attr, uattr);
1539 * __cgroup_bpf_run_filter_skb() - Run a program for packet filtering
1551 * NET_XMIT_SUCCESS (0) - continue with packet output
1552 * NET_XMIT_DROP (1) - drop packet and notify TCP to call cwr
1553 * NET_XMIT_CN (2) - continue with packet output and notify TCP
1555 * -err - drop packet
1557 * For ingress packets, this function will return -EPERM if any
1565 unsigned int offset = -skb_network_offset(skb);
1571 if (sk->sk_family != AF_INET && sk->sk_family != AF_INET6)
1574 cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
1575 save_sk = skb->sk;
1576 skb->sk = sk;
1586 ret = bpf_prog_run_array_cg(&cgrp->bpf, atype, skb,
1601 * 3: -err skb should be dropped
1606 ret = -EFAULT;
1612 ret = bpf_prog_run_array_cg(&cgrp->bpf, atype,
1616 ret = -EFAULT;
1620 skb->sk = save_sk;
1627 * __cgroup_bpf_run_filter_sk() - Run a program on a sock
1636 * This function will return %-EPERM if any if an attached program was found
1642 struct cgroup *cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
1644 return bpf_prog_run_array_cg(&cgrp->bpf, atype, sk, bpf_prog_run, 0,
1650 * __cgroup_bpf_run_filter_sock_addr() - Run a program on a sock and
1655 * read-only for AF_INET[6] uaddr but can be modified for AF_UNIX
1664 * This function will return %-EPERM if an attached program is found and
1686 if (sk->sk_family != AF_INET && sk->sk_family != AF_INET6 &&
1687 sk->sk_family != AF_UNIX)
1698 cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
1699 ret = bpf_prog_run_array_cg(&cgrp->bpf, atype, &ctx, bpf_prog_run,
1710 * __cgroup_bpf_run_filter_sock_ops() - Run a program on a sock
1722 * This function will return %-EPERM if any if an attached program was found
1729 struct cgroup *cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
1731 return bpf_prog_run_array_cg(&cgrp->bpf, atype, sock_ops, bpf_prog_run,
1749 ret = bpf_prog_run_array_cg(&cgrp->bpf, atype, &ctx, bpf_prog_run, 0,
1768 ctx = container_of(current->bpf_ctx, struct bpf_cg_run_ctx, run_ctx);
1769 storage = ctx->prog_item->cgroup_storage[stype];
1772 ptr = &READ_ONCE(storage->buf)->data[0];
1774 ptr = this_cpu_ptr(storage->percpu_buf);
1790 container_of(current->bpf_ctx, struct bpf_cg_run_ctx, run_ctx);
1792 return ctx->retval;
1804 container_of(current->bpf_ctx, struct bpf_cg_run_ctx, run_ctx);
1806 ctx->retval = retval;
1873 * __cgroup_bpf_run_filter_sysctl - Run a program on sysctl
1879 * @pcount: value-result argument: value is size of buffer pointed to by @buf,
1882 * @ppos: value-result argument: value is position at which read from or write
1890 * This function will return %-EPERM if an attached program is found and
1915 table->proc_handler(table, 0, ctx.cur_val, &ctx.cur_len, &pos)) {
1936 ret = bpf_prog_run_array_cg(&cgrp->bpf, atype, &ctx, bpf_prog_run, 0,
1958 return -EINVAL;
1967 if (max_optlen <= sizeof(buf->data)) {
1971 ctx->optval = buf->data;
1972 ctx->optval_end = ctx->optval + max_optlen;
1976 ctx->optval = kzalloc(max_optlen, GFP_USER);
1977 if (!ctx->optval)
1978 return -ENOMEM;
1980 ctx->optval_end = ctx->optval + max_optlen;
1988 if (ctx->optval == buf->data)
1990 kfree(ctx->optval);
1996 return ctx->optval != buf->data;
2003 struct cgroup *cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
2025 ret = -EFAULT;
2030 ret = bpf_prog_run_array_cg(&cgrp->bpf, CGROUP_SETSOCKOPT,
2037 if (ctx.optlen == -1) {
2038 /* optlen set to -1, bypass kernel */
2040 } else if (ctx.optlen > max_optlen || ctx.optlen < -1) {
2048 ret = -EFAULT;
2062 /* We've used bpf_sockopt_kern->buf as an intermediary
2065 * No way to export on-stack buf, have to allocate a
2072 ret = -ENOMEM;
2095 struct cgroup *cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
2121 ret = -EFAULT;
2126 ret = -EFAULT;
2133 ret = -EFAULT;
2139 ret = bpf_prog_run_array_cg(&cgrp->bpf, CGROUP_GETSOCKOPT,
2154 ret = -EFAULT;
2161 ret = -EFAULT;
2165 ret = -EFAULT;
2179 struct cgroup *cgrp = sock_cgroup_ptr(&sk->sk_cgrp_data);
2199 ret = bpf_prog_run_array_cg(&cgrp->bpf, CGROUP_GETSOCKOPT,
2205 return -EFAULT;
2221 if (dir->header.parent) {
2222 tmp_ret = sysctl_cpy_dir(dir->header.parent, bufp, lenp);
2227 ret = strscpy(*bufp, dir->header.ctl_table[0].procname, *lenp);
2231 *lenp -= ret;
2242 *lenp -= tmp_ret;
2253 return -EINVAL;
2256 if (!ctx->head)
2257 return -EINVAL;
2258 tmp_ret = sysctl_cpy_dir(ctx->head->parent, &buf, &buf_len);
2263 ret = strscpy(buf, ctx->table->procname, buf_len);
2282 return -EINVAL;
2285 return -E2BIG;
2289 return -EINVAL;
2295 memset(dst + src_len, '\0', dst_len - src_len);
2299 dst[dst_len - 1] = '\0';
2301 return -E2BIG;
2307 return copy_sysctl_value(buf, buf_len, ctx->cur_val, ctx->cur_len);
2322 if (!ctx->write) {
2325 return -EINVAL;
2327 return copy_sysctl_value(buf, buf_len, ctx->new_val, ctx->new_len);
2342 if (!ctx->write || !ctx->new_val || !ctx->new_len || !buf || !buf_len)
2343 return -EINVAL;
2345 if (buf_len > PAGE_SIZE - 1)
2346 return -E2BIG;
2348 memcpy(ctx->new_val, buf, buf_len);
2349 ctx->new_len = buf_len;
2350 ctx->new_updated = 1;
2426 switch (si->off) {
2429 BPF_SIZE(si->code), si->dst_reg, si->src_reg,
2444 if (si->src_reg == treg || si->dst_reg == treg)
2445 --treg;
2446 if (si->src_reg == treg || si->dst_reg == treg)
2447 --treg;
2449 BPF_DW, si->dst_reg, treg,
2453 treg, si->dst_reg,
2456 BPF_CLASS(si->code) | BPF_MEM | BPF_SIZEOF(u32),
2457 treg, si->src_reg,
2460 si->imm);
2462 BPF_DW, treg, si->dst_reg,
2467 si->dst_reg, si->src_reg,
2469 read_size = bpf_size_to_bytes(BPF_SIZE(si->code));
2471 BPF_SIZE(si->code), si->dst_reg, si->dst_reg,
2479 return insn - insn_buf;
2494 const struct net *net = ctx ? sock_net(ctx->sk) : &init_net;
2496 return net->net_cookie;
2525 if (prog->expected_attach_type == BPF_CGROUP_SETSOCKOPT)
2529 if (prog->expected_attach_type == BPF_CGROUP_SETSOCKOPT)
2562 return prog->expected_attach_type ==
2569 return prog->expected_attach_type ==
2582 info->reg_type = PTR_TO_SOCKET;
2587 info->reg_type = PTR_TO_PACKET;
2592 info->reg_type = PTR_TO_PACKET_END;
2597 return prog->expected_attach_type == BPF_CGROUP_GETSOCKOPT;
2608 si->dst_reg, si->src_reg, \
2613 BPF_MEM | BPF_CLASS(si->code)), \
2614 si->dst_reg, si->src_reg, \
2616 si->imm)
2626 switch (si->off) {
2654 if (si->src_reg == treg || si->dst_reg == treg)
2655 --treg;
2656 if (si->src_reg == treg || si->dst_reg == treg)
2657 --treg;
2658 *insn++ = BPF_STX_MEM(BPF_DW, si->dst_reg, treg,
2661 treg, si->dst_reg,
2666 *insn++ = BPF_RAW_INSN(BPF_CLASS(si->code) | BPF_MEM |
2668 treg, si->src_reg,
2670 si->imm);
2671 *insn++ = BPF_LDX_MEM(BPF_DW, treg, si->dst_reg,
2675 si->dst_reg, si->src_reg,
2678 si->dst_reg, si->dst_reg,
2681 si->dst_reg, si->dst_reg,
2693 return insn - insn_buf;
2723 switch (prog->expected_attach_type) {
2741 switch (prog->expected_attach_type) {