@@ -544,6 +544,120 @@ static int dcbnl_setpfcstate(struct net_device *netdev, struct nlattr **tb,
544
544
return ret ;
545
545
}
546
546
547
+ static int dcbnl_getapp (struct net_device * netdev , struct nlattr * * tb ,
548
+ u32 pid , u32 seq , u16 flags )
549
+ {
550
+ struct sk_buff * dcbnl_skb ;
551
+ struct nlmsghdr * nlh ;
552
+ struct dcbmsg * dcb ;
553
+ struct nlattr * app_nest ;
554
+ struct nlattr * app_tb [DCB_APP_ATTR_MAX + 1 ];
555
+ u16 id ;
556
+ u8 up , idtype ;
557
+ int ret = - EINVAL ;
558
+
559
+ if (!tb [DCB_ATTR_APP ] || !netdev -> dcbnl_ops -> getapp )
560
+ goto out ;
561
+
562
+ ret = nla_parse_nested (app_tb , DCB_APP_ATTR_MAX , tb [DCB_ATTR_APP ],
563
+ dcbnl_app_nest );
564
+ if (ret )
565
+ goto out ;
566
+
567
+ ret = - EINVAL ;
568
+ /* all must be non-null */
569
+ if ((!app_tb [DCB_APP_ATTR_IDTYPE ]) ||
570
+ (!app_tb [DCB_APP_ATTR_ID ]))
571
+ goto out ;
572
+
573
+ /* either by eth type or by socket number */
574
+ idtype = nla_get_u8 (app_tb [DCB_APP_ATTR_IDTYPE ]);
575
+ if ((idtype != DCB_APP_IDTYPE_ETHTYPE ) &&
576
+ (idtype != DCB_APP_IDTYPE_PORTNUM ))
577
+ goto out ;
578
+
579
+ id = nla_get_u16 (app_tb [DCB_APP_ATTR_ID ]);
580
+ up = netdev -> dcbnl_ops -> getapp (netdev , idtype , id );
581
+
582
+ /* send this back */
583
+ dcbnl_skb = nlmsg_new (NLMSG_DEFAULT_SIZE , GFP_KERNEL );
584
+ if (!dcbnl_skb )
585
+ goto out ;
586
+
587
+ nlh = NLMSG_NEW (dcbnl_skb , pid , seq , RTM_GETDCB , sizeof (* dcb ), flags );
588
+ dcb = NLMSG_DATA (nlh );
589
+ dcb -> dcb_family = AF_UNSPEC ;
590
+ dcb -> cmd = DCB_CMD_GAPP ;
591
+
592
+ app_nest = nla_nest_start (dcbnl_skb , DCB_ATTR_APP );
593
+ ret = nla_put_u8 (dcbnl_skb , DCB_APP_ATTR_IDTYPE , idtype );
594
+ if (ret )
595
+ goto out_cancel ;
596
+
597
+ ret = nla_put_u16 (dcbnl_skb , DCB_APP_ATTR_ID , id );
598
+ if (ret )
599
+ goto out_cancel ;
600
+
601
+ ret = nla_put_u8 (dcbnl_skb , DCB_APP_ATTR_PRIORITY , up );
602
+ if (ret )
603
+ goto out_cancel ;
604
+
605
+ nla_nest_end (dcbnl_skb , app_nest );
606
+ nlmsg_end (dcbnl_skb , nlh );
607
+
608
+ ret = rtnl_unicast (dcbnl_skb , & init_net , pid );
609
+ if (ret )
610
+ goto nlmsg_failure ;
611
+
612
+ goto out ;
613
+
614
+ out_cancel :
615
+ nla_nest_cancel (dcbnl_skb , app_nest );
616
+ nlmsg_failure :
617
+ kfree_skb (dcbnl_skb );
618
+ out :
619
+ return ret ;
620
+ }
621
+
622
+ static int dcbnl_setapp (struct net_device * netdev , struct nlattr * * tb ,
623
+ u32 pid , u32 seq , u16 flags )
624
+ {
625
+ int ret = - EINVAL ;
626
+ u16 id ;
627
+ u8 up , idtype ;
628
+ struct nlattr * app_tb [DCB_APP_ATTR_MAX + 1 ];
629
+
630
+ if (!tb [DCB_ATTR_APP ] || !netdev -> dcbnl_ops -> setapp )
631
+ goto out ;
632
+
633
+ ret = nla_parse_nested (app_tb , DCB_APP_ATTR_MAX , tb [DCB_ATTR_APP ],
634
+ dcbnl_app_nest );
635
+ if (ret )
636
+ goto out ;
637
+
638
+ ret = - EINVAL ;
639
+ /* all must be non-null */
640
+ if ((!app_tb [DCB_APP_ATTR_IDTYPE ]) ||
641
+ (!app_tb [DCB_APP_ATTR_ID ]) ||
642
+ (!app_tb [DCB_APP_ATTR_PRIORITY ]))
643
+ goto out ;
644
+
645
+ /* either by eth type or by socket number */
646
+ idtype = nla_get_u8 (app_tb [DCB_APP_ATTR_IDTYPE ]);
647
+ if ((idtype != DCB_APP_IDTYPE_ETHTYPE ) &&
648
+ (idtype != DCB_APP_IDTYPE_PORTNUM ))
649
+ goto out ;
650
+
651
+ id = nla_get_u16 (app_tb [DCB_APP_ATTR_ID ]);
652
+ up = nla_get_u8 (app_tb [DCB_APP_ATTR_PRIORITY ]);
653
+
654
+ ret = dcbnl_reply (netdev -> dcbnl_ops -> setapp (netdev , idtype , id , up ),
655
+ RTM_SETDCB , DCB_CMD_SAPP , DCB_ATTR_APP ,
656
+ pid , seq , flags );
657
+ out :
658
+ return ret ;
659
+ }
660
+
547
661
static int __dcbnl_pg_getcfg (struct net_device * netdev , struct nlattr * * tb ,
548
662
u32 pid , u32 seq , u16 flags , int dir )
549
663
{
@@ -1101,6 +1215,14 @@ static int dcb_doit(struct sk_buff *skb, struct nlmsghdr *nlh, void *arg)
1101
1215
ret = dcbnl_bcn_setcfg (netdev , tb , pid , nlh -> nlmsg_seq ,
1102
1216
nlh -> nlmsg_flags );
1103
1217
goto out ;
1218
+ case DCB_CMD_GAPP :
1219
+ ret = dcbnl_getapp (netdev , tb , pid , nlh -> nlmsg_seq ,
1220
+ nlh -> nlmsg_flags );
1221
+ goto out ;
1222
+ case DCB_CMD_SAPP :
1223
+ ret = dcbnl_setapp (netdev , tb , pid , nlh -> nlmsg_seq ,
1224
+ nlh -> nlmsg_flags );
1225
+ goto out ;
1104
1226
default :
1105
1227
goto errout ;
1106
1228
}
0 commit comments