From patchwork Sat Jan 21 00:05:07 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kevin Cernekee X-Patchwork-Id: 9532533 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id BABCE6042D for ; Mon, 23 Jan 2017 13:29:52 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id A6390282EC for ; Mon, 23 Jan 2017 13:29:52 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 9A9E22831B; Mon, 23 Jan 2017 13:29:52 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-1.9 required=2.0 tests=BAYES_00, RCVD_IN_DNSWL_NONE autolearn=unavailable version=3.3.1 Received: from emsm-gh1-uea10.nsa.gov (smtp.nsa.gov [8.44.101.8]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 8944A282EC for ; Mon, 23 Jan 2017 13:29:50 +0000 (UTC) X-IronPort-AV: E=Sophos;i="5.33,274,1477958400"; d="scan'208";a="3056910" IronPort-PHdr: =?us-ascii?q?9a23=3AXYeeCRPS2+6gcir9NSEl6mtUPXoX/o7sNwtQ0KIM?= =?us-ascii?q?zox0LP//psbcNUDSrc9gkEXOFd2CrakV16yK4uu9ASQp2tWoiDg6aptCVhsI24?= =?us-ascii?q?09vjcLJ4q7M3D9N+PgdCcgHc5PBxdP9nC/NlVJSo6lPwWB6nK94iQPFRrhKAF7?= =?us-ascii?q?Ovr6GpLIj8Swyuu+54Dfbx9GiTe5br5+Nhq7oAHeusQWnYdpN7o8xAbOrnZUYe?= =?us-ascii?q?pd2HlmJUiUnxby58ew+IBs/iFNsP8/9MBOTLv3cb0gQbNXEDopPWY15Nb2tRbY?= =?us-ascii?q?VguA+mEcUmQNnRVWBQXO8Qz3UY3wsiv+sep9xTWaMMjrRr06RTiu86FmQwLmhy?= =?us-ascii?q?cdMz4y7X/ZhMp+gqlGpB6tvgFzz5LRbIyTKfFwfL7SfckCSGRBQMhfSiJPDIC7?= =?us-ascii?q?YYQNAeoBJeRVo5TzqlQBsRSwChejBPj0xz9UhHL7x7E23v49HQ3Y2gErAtIAsG?= =?us-ascii?q?7TrNXwLKocVP66zLfJzTXFcvhbxyny6JLOch8/ovGDQ6x/etfWxEYzCQzFlFOQ?= =?us-ascii?q?ppLmPzyLyOsAqHSU7+p6VeKojm4nqhxxoj21yscrkInJiZsYx1bZ/it62IY4Pc?= =?us-ascii?q?C0RUF0bNK+EJZcqjuWO5V5T888WW1kpT42xqMatZO/ZiQHy5QqywTCZ/GDbYSE?= =?us-ascii?q?+A/vWeSSLDp+mXlrYqiwhwyo/kil0uD8U86030tUoSddidnMs2wN1wTU6siaVv?= =?us-ascii?q?tx5keh1iiL1wDU8uxEPVo7lbDaK5482b48jIYTsETfES/2n0X6lqmWeVk/+ue0?= =?us-ascii?q?8ejnZ7TmppuEO491jAHxLLgul9SiDek3PQUCRWiW9fmm2LH98kD1Xq9GguAunq?= =?us-ascii?q?ncqp/aJMAbpqCjAw9S14Yu8w2/ACmi0NQZm3kHMV1EdAucgIjuJlHOJuz3Aumk?= =?us-ascii?q?g1m3jDdqx+zJPr3mApnXKHjDi63ucaxy605b1go/1cpf6I5MCrEdPPLzXVf8tN?= =?us-ascii?q?7fDh8/KQO03+bnB8971o4FW2KPBamZMKbIvl+T+uIgPfOMZJQPtDb6Mfgl6Obk?= =?us-ascii?q?jWUlll8FYampwZwXZWi6HvRkOUqWfXnsgswGEWcMvwo+UvfniFOGUT5OaHe9RL?= =?us-ascii?q?885jcnCIK7F4vDQZqtgLOZ1iehApJWfnxGCkyLEXrweYSEWvMMaCeMLc97iTEE?= =?us-ascii?q?W6auRJIm1RG0rgD606BnLu3W+iIGqZ3jyMJ55+rJlRE97TZ0FdiS03mRT2FomW?= =?us-ascii?q?MFXyI507x6oUx6zFeDzbV0judGFdNN/fNJUwY7NZnaz+BgDdD9RB7BdM+TSFm6?= =?us-ascii?q?WtWmHS0xTtUpztATf0ZyAc+igwvf0CqtBr8ai6aEBIco8q7G2Xj+Odp9wW7c1K?= =?us-ascii?q?Y9l1kmXtdPNWq+i69/9gnTAIjJnl6cl6aubKgc3SjN+H2FzWWUpkFYUw9wUbvb?= =?us-ascii?q?UnwFYEvZs8j57FvYT7CyEbQnLhdBycmaJ6RRcdLlilFGRPb4ONTCeGK9gXywCg?= =?us-ascii?q?iUyb+Wd4rlZWEd3CTbCEgZnAEe5mqJNAgkBie8uGLSFjJvGkjzY0P39ul+rmm3?= =?us-ascii?q?TkguzwGFd0dhzaa6+gYJhfyATPMexrwEuD07pDVyAFm93snWBsGFpwp5faVQeM?= =?us-ascii?q?g94Vlc1W7DsAx9JJOgJbh4hlECawR3o1/u1xJvB4VDi8cqr3QqzBdpJKKbylxB?= =?us-ascii?q?dDSY3Y3qNr3QMGny8wila7TK1VHGzNaW5qAP5ewipFr+pgGpF1Qt82983tZPz3?= =?us-ascii?q?Sc44/GDA0IUZL+Skw37QR1p6nGYikh4IPZzX1sPrewsj/G3NIkH+8lygu8f9dY?= =?us-ascii?q?NaOLDhX+E8oAB8ihMOYqgUSmbgoYPOBO8645J9imd/Wc2K6sJ+ZggCmrjX9B4I?= =?us-ascii?q?B63EOM8jBzSujS05YD3f6YwhONVy3gg1e5rsD3hYdEaCkcH2WlzSjkGJBeZrdp?= =?us-ascii?q?fYsQF2ehPde3yc5jh57oQXJY80SjB1we0s+zZRWSd0D93RFX1UkPvXyohDa3zz?= =?us-ascii?q?1unDEttaeQwCvOw+H+exUdIW5LWHNujVHyLoiol9oaRlSnbxA1lBu54kb3365b?= =?us-ascii?q?pKV7L2nXX0hIZDP7IHt8XauqsbqOeclP6IknsS9PSuSzfUiaSqLhoxsdyy7jAW?= =?us-ascii?q?peyywndzGtoJX1hQB1iGKaLHZ1o3rUYsVwxRbZ5NPGX/5R2SAKRC5iiTnYHlK8?= =?us-ascii?q?JcWm/c2Il5ffteCzT2ahVpxIcSn31I+ArzW05WlrAR25gvCylcbqERMi0S/60d?= =?us-ascii?q?lqVDnHrA3mbontyau6LfptflN0C1/k98p6BoZ+n5MqhJEX3Xgagoua/WAbnmf0?= =?us-ascii?q?P9RWwrn+bGcRSj4Q2dLV5xLl2EJ7JHKT2435TmmdwtdmZ9SiemMZwD8978RQBK?= =?us-ascii?q?iO9rBLhix1ol6krQLWZ/hwhTIdxeco6H4dn+4FogwtwTuBAroKB0lXITTslwiU?= =?us-ascii?q?79C5tKhXZ3igcb6r1EdlntCuEreCohpaWHnnZpcuByhw7t9wMFjUyn389pnkeM?= =?us-ascii?q?XMbdIUrhCUjRHAgPVOJZIvkPoFmCpnNXj7vXI71+4xlQZu0o2ivIibN2Vt+7q0?= =?us-ascii?q?AgZCOT3oY8Me4S3ijadCnseWxoyvEI9uGjMRUJvvV/KoHyoYte77OAaWDD08tn?= =?us-ascii?q?CbFKLFHQCC9UhrtH3PE5WkNn2NInkW08liTgGHJENDmAAUQCk6npkhGwCy3sPh?= =?us-ascii?q?bUN56S4J5lHirBtM1vxnNwPkX2fCvwendC00SIOFIBpN6QFC+l3VPtCA4eJ9GC?= =?us-ascii?q?FY5JKhoxKXJmydeQtIEXkDWlaYCFD7Irmu+d7A/vCWBuWkKfvOfbKOqelFWveG?= =?us-ascii?q?252gz4xm/yyWOcWXJHliCP871VRfUnBlAcjZnC8PSyMPnSLXc8GbvAu8+jFwrs?= =?us-ascii?q?2n9fTkQgbv5Y+RBLtOLdVg4Qq5jLyFN+GOmCZ5MipX2YkUxXDW0rQf2kAdiz12?= =?us-ascii?q?fTm3DbsArTLNTL7XmqJPFR4XcS1yONFN760m2glNPs7ah8jv2bFki/45EVBFVU?= =?us-ascii?q?bumsuxf8wFP3m9NE/bBEaMLLmGIyfLzNvvYaOkUrBQguRUtweruTaHHU/jPzKD?= =?us-ascii?q?mCPvVx+zMOFDliWbMAZZuIGnfRZnEXLjQ87+ah2nLN93iiU7waUqiXzRK2EcNz?= =?us-ascii?q?l8c19KrrCL7CNXnOtwFHJb4npiN+mElD6T7/PEJZYOrftrHiN0mvpH73Qh1bRa?= =?us-ascii?q?9i5EROZvlyvMtdNuuEupkuqSyjp9ShVCsDJLhJ+NvUp4I6XV74VAWXHH/BMN6m?= =?us-ascii?q?WcERIKqMV5Ctf3oaBf1sDPlL7vKDdF69/U5tETB9bOJ8KILnUhKgHkGCXOAwsb?= =?us-ascii?q?VzGrOn/Qh1dHnPGU6HKVsoAwqoLwl5oWVr9bSFs1G+sBBURkE9wCJ5F3Uyg5nr?= =?us-ascii?q?GFl8EI5GCxrB/LSMVdpJDHWeqYAe/zJzaBkblEexwIzKviIoQcLIL7xVJtZ0J9?= =?us-ascii?q?nITSBUXQW9VNrTdgbg8wu0pN93d/Qnc020L/ZQOn+GUTGuKsnh4qlgt+Zvwg9C?= =?us-ascii?q?vr41cyPFbKviwwkUgvltXjmj+RajnxI7mzXYxNFyX0sE0xPY/hTAZucQ2+h0pk?= =?us-ascii?q?OynYR7hJlbtvaXhriBPAuZtIAfNcTq1FYBsOyvyMYvUo1lpcqiu5yk9b+evFCZ?= =?us-ascii?q?xilA40fpK2qXJPxR5jZsYvJaPMPKpJ0kRQhqWWsy+uyO8+2gseKl0O8GOVYy4I?= =?us-ascii?q?pFYHNr89Jyqr/+xg8wqClCVfeGIUTfolvupq9l8hO+SH1y/gyaBMKluvOOOFNa?= =?us-ascii?q?OWp2jAmNWTTVMxzEMHik5F/bZu0cc5bUWVV1ojzL2PGBQVLcDCMx1ab9JO9HjP?= =?us-ascii?q?eiaDqfjCwZVzP4W7C+/nU+uOtKcPj02+AgkpBYMM4t4GHpm230HSNd3nI6IdyR?= =?us-ascii?q?Ux+ATrI02IA+lTdxKVkTcIvtq/wYRt0olHPDEdBmt8MT6p6bnLuw8qmvuDXMs2?= =?us-ascii?q?Y3sAWIsLKG42UtWgmyFFp3RAECW30uUBxQiM9T/zuDnfDCLmYNplePeUYghsBc?= =?us-ascii?q?qs9joj9qi6k1nX8o/RJ2viL9RtpsfP6f8Gp5aAE/5USb59s13ClIleRn2qVHXC?= =?us-ascii?q?EdGzJ5jtcYUsasb0CnmiWFyllz01V9vxPMqqLqWQmgHnW4JUsIid3DA+Os6wDS?= =?us-ascii?q?0RGxB1p+4f/q18fhEDb4A9YRH2qwQ0L7a/LxuA0tWyX2atLiNbT/pFzeS6fbNX?= =?us-ascii?q?yTYsbu+hxXsvSZE61/W4/VQLRJ4UkhHU3eyjaJVGUSjvBnxdfB3CpTY4l2hkMe?= =?us-ascii?q?Yy3uc/wRPTvFYBMjCKdPZmZ3des9E6G1ySPW18CnAkSF+EkYrD/gms0qgI8CtZ?= =?us-ascii?q?ntZbzfNKv2D7vp7fZjKsX6qrpo/OviU7bNgpuatxPZXtIsubrp/emCLQTIXIuA?= =?us-ascii?q?2fTCG6D+ZamsRXIC9AW/ZHh2clNNcctoVc90o+SN0+J6dVB6k2prGmcz1kDTQd?= =?us-ascii?q?zSUBTYOPwCQCgvug27vdjhqQf4kiMB0AsJVGnNQdVjV7bT4Aq6C4VoXZjWmERn?= =?us-ascii?q?IMIAcJ4gRG/BgAmZNofuD5/IrIS4dByyRQo/J1TiTLFp5o91/gSm+OmFb2Ve+v?= =?us-ascii?q?nvCu0w9J0P3s1dwbVwJlBkhG2+ZajE0oJ69rK6MIpI7FrieIdV/mvGLq0OamPk?= =?us-ascii?q?NeydfTd1LjF4fFqXD8XTcC+XIKQY9PyXffFZsWkwp4Z6YrpElMII68dUbk4jwo?= =?us-ascii?q?3YJpEKekVcqz3VYqsW4GRzu2E9pGE+xnvkjbVyFlY5CqrZXlOo9dQmxL9Z2ctV?= =?us-ascii?q?hWjltiPzS+yZpGJMFH+iQMUyRXoTWBoNuyT9VO1tVsD58RJNdzoXT9FbhFOJiQ?= =?us-ascii?q?on02pqfgxmXf+z8irFew3C+zFLOgT+JF420eHR0kJ2WYqkkzEeQs9nnd8lXTvV?= =?us-ascii?q?Bo5edaBqOCjUJpoDljGJBOAyxG1XGhL1toS3lHvP9WKKPPc8xTW/MyfwOgOwQi?= =?us-ascii?q?Ff462EyE5U50nW3jbCx0qgtX4CHdXw46VCkTnrftmSMRqsChOT8GVZ1Idy8tby?= =?us-ascii?q?HbJAKHgSpXpgpQa1l2W5AFBdZI460b3YxR/sfZVUagNSQFUwd4OgI+z/VfiVZJ?= =?us-ascii?q?sF+EdiDFEQqoafHPvwV3fciLts6mNvD58xpch4z6ru84770DSGOimQKzW9DStY?= =?us-ascii?q?j8tseFtkGWbqf3L/W8YWPdTDjLlR2wh7AkAIfR8ifOLgVbMId1yWA4YZf/FGHH?= =?us-ascii?q?JxJGKLwHJ0BDT6B1dc1GovxGZ89jYKsG4qFtCQ6bSh7tBYCiouJLIUrURTTbMy?= =?us-ascii?q?qO6Pe/oZ7J4bzbV+fgetSGx2zbTKJvIpd69T77Fq/w0YBA50X22u1i9l9hRFjC?= =?us-ascii?q?NCCBssruKh0X68mla0TtoIclHTXID5dsiHDt3F1Pd9ILQy2295QV0ItZ6G3sSe?= =?us-ascii?q?1iz0fzrPZf96Jj6Ykq+bBm1dm7JaHOKfRAq0BnBgKYBgJw9pUiGGJ/XXxeYvcN?= =?us-ascii?q?KPfNeqQUldzuq/rpGKMJ9RKY4PFZad/bJ0HbgMa/FDCcSRtAnAgftT4WNAyc1+?= =?us-ascii?q?SKm6VsU8aqufD52l4x41i5NhMJ0bZt6p2f96WVou/YdQHdzb8eWqjlXsnztKgj?= =?us-ascii?q?u1uO5f04k74DYm51bBe9EOgaTc4dwn3vzb4xwCIpDsPDG67g+P9fWHI4hD3gnY?= =?us-ascii?q?t9E08RGvMOErqB5Z5ekXsgm+zFKt0WdbhPmmSVGh6iHL8C03mr5DaJL2R+nhHB?= =?us-ascii?q?yRfwQXi07FPsqy93XzfMxc/5kkVJTrm3GVtSXy2xNE9+tDOCJwvotNzyuagv7U?= =?us-ascii?q?E2NGLktMiXm2u6JLNXBdD/K8CAISkpvlIYkoc9Rtu12YAUAdC9Osse8GlibvvC?= =?us-ascii?q?7GOmiylBo6ZbiIrZ5sGa4O7XEWOhj62drLWN3ytYx2M9vVww5dGsLPbO58eFQ/?= =?us-ascii?q?6wzWYeUz9/uxfdXx6ysrHUs0obOUiV30fQhIwLPtZZ0GIj1k765egsXtQz9Blf?= =?us-ascii?q?Fonaff8Coy78OCfsy1aFf903TjWe0ydQHl/tFVl4A6081WLrscLHi3jf5looRp?= =?us-ascii?q?NqeEz/nxx3CIc4Jlwx51gL2CYDFhINaR+DBrGyGUvlNZcEVVQEaRmf3ri6e6I3?= =?us-ascii?q?0FZ2wryx5O7cc/Z8B6sLNvZSlAKOmkZUGo4Ou60EXL18Y0Nd9LLQpgX6CojmXu?= =?us-ascii?q?LpmmAsOvCuWcBV79wZuGU+7QqlQBqg85hD5a4BiJ+Ubq5EfYTMvMdk4kh85D4P?= =?us-ascii?q?bSJMjwJ9jxO4TeAcvPrs4sXfsJez9umuU7siSPsN+BgpHWR+iIHwj0o5rdHQze?= =?us-ascii?q?dcRZXfiZ7j/wBVP36KpIHa3gFkKeUUN4KkYLZg9nsAJygEJHICJMGWZOc44y9s?= =?us-ascii?q?NjXT+lNDD9gUZdwCIMrChQBUi0PuWLFJ9crXAFyYBJlpd8Au8WX3zCo58ZwmUu?= =?us-ascii?q?bv8DW2P4zQ70lRP/NfiyVhjM7CpPILzvrWEicX52eWZgNozSODxJmNCurw8v+X?= =?us-ascii?q?yN7OTVMGAzQ6U4FDKzqe4QanXPa6lI31UgOI7c/+mJ0+e1iKRnOvgKQFsr1BEe?= =?us-ascii?q?pBiiXnwDdeFpr6h++Os9a27mtYqEFHGp5p7RLZAKVfIol7ORPgm8mkWEd8ADf/?= =?us-ascii?q?eMbTdhYpo+qZ2OMM4+R4N0vjao4WORYExKzg6XtVVARiUrj2sUiFXegJfttpVO?= =?us-ascii?q?vErmxJ6YJnM6IAIFqdq4b2oTpTtF82BwspaLsxrjNEbEnOgBNaVLr0uLIajQsc?= =?us-ascii?q?S9F5s1dWGW2sIGI++ybHVaNNgamUD/wV9CmTTqMQXEhzNyN+Qgm62JNwdLu1k/?= =?us-ascii?q?FHtXlGniBmoPQw1TxpWge8szX2p60RwTIg5K24tDIZtHxKUuqeiDzIBUxewvoF?= =?us-ascii?q?i6kcCnDi6UGzYXQYY4vy5aNoJcL++oU75HQ/exojdTUcXeu8EyHwk7+IAouXvd?= =?us-ascii?q?Jegx6NuMPOYaWvIigSMrQ91A/sRnl80gjYhxZo82oLTy6+7N8lOoWyI8IlyTep?= =?us-ascii?q?GWTBclYD/L9JutPrtVEXVOs2dU9hwGJ738iGWC0CXsrPFn0xjgg5dGpEcZVD6Q?= =?us-ascii?q?QAG6kvmDaIsbFM/hsIbzfMDoSl5o7QkN/K2XYjQ9dqyGbWq7aLh5ww1n1qhc90?= =?us-ascii?q?4jSIuHsMa+zSS9VsDWTr1odD1ez+YO2gsu8DSIthxrWuTvsCMs249Gut35VqXE?= =?us-ascii?q?6lyagEE1q/LuAD2q/RUz25Rm2AReSLb2+Mki47Mk7y5RioNlo3aMNLr08hLOTP?= =?us-ascii?q?nZtclwz9UbNuWCqcv1jbzHYsMekCbQI5pJ+nexAWTO4Wf+WcOekuwPglBVsQbn?= =?us-ascii?q?/GASh2BPGysVK3moh0JWlg613gYevx6gDmLMeSGh4cHI7fr55x+v+6RmWaNH9i?= =?us-ascii?q?1hJyP0509+HBGFQ3rONcdYiencTIjdRhzeEFb+ttMTE6utMLgY1s94+U0NuRfB?= =?us-ascii?q?HKypbyIs3VouSGA/LB0ksmYGZaUqAWYQnt/YU1IsY5W6HPHbtepRkcHa86QJg7?= =?us-ascii?q?OGfr+qB0KwdzcgDKabSxhcnqofmLaYVIqH/M6VIwNzzcuxwFyvy7VwB7aIqqh3?= =?us-ascii?q?rqKpAqWj1Bt8FtCgdhHIZXFcMPsQ6nA5+MmK6lkNKw+kJ6u+oPsaXuEPDK0Mq2?= =?us-ascii?q?0592X5hA6kyBJCzRC7VzgkR5kuSyhe/N05fpCcP4eNMLSPZ0T3XAar/HAoW/MC?= =?us-ascii?q?yBNtj7e05c/L6WyKh5XQmJZCDlQ6qGszWpNPJg4Uol0YF4ZO7TwyY277HH2dv9?= =?us-ascii?q?e31bpj29onGXLpdf6kLFBfDGVRJOVfWF6HplHbEQbYbs8OcOMNoiwMWT4gVq6D?= =?us-ascii?q?RC0dCFI7S6rkLX20J0b5TbLEzz1yY+Q4kKLwy1MVEwjm/BtnTdHXNcI9C/KcZz?= =?us-ascii?q?hNaVDxrt51R+mG0qaWBBBmroSsmLOWcFw8KxfhaH9AFVANYZme64Z0o4ubavSe?= =?us-ascii?q?lnIJlFnv+qtLofm9ZzNy7PXNRaPz3XLLJuOzpeFPnApFgpYh4CtLg4QZk1ZZmI?= =?us-ascii?q?IEwZNEeAyCXyzRbN0EHucNyszqmJKj4M8npb17LFzSRMpw6htPabmMLjU7fZY4?= =?us-ascii?q?rtUf7PNiolSjGaRTMvEUam+Vekp+AIvPyGLmcDuloUeD6dCBYPpqBzqtjdFmDT?= =?us-ascii?q?lvd4c50QhfCVRSTwRTZmlKo2HClLrkGMQ+cZGQnQcXDhnHJWuBa+Kf9U4XLlc7?= =?us-ascii?q?qYy7JXW+wTBYtMaOeZQ9rDef1FITcnjDAZN/i9f9HGqLY5yF3IR3MDE6bU7F2e?= =?us-ascii?q?UFKWQvuEyjLwU4UVupQ7tysr99/LgC94Db7IP7eepj6p9I60liCYtvPCVmM1eU?= =?us-ascii?q?w6nPoCAHWdwBlHMGwECdYVuEfpQqObYkZDym8miexp2x8WZAt8TGdi0ntIk/ah?= =?us-ascii?q?SYVlTgsPkG6gTvAAKlNzBSgr8FWWyhb/asEGtNyVTGhbsvMMRJAXIeM0wIbQPq?= =?us-ascii?q?cX2rAgxDtgqWo9qSrbBk4Zxg6M7afVNK512LBH4W4247dwU13LCyvWb2zv0oO7?= =?us-ascii?q?D4dKwiB0rDbv0M+Q9vthL5NGtop5BxEMGiswKdfDuXhMSWju2RCapx+hHS+GJD?= =?us-ascii?q?sS7XAMPyNWWPxyyrpYvQjJcJ7q5FmWuqEspQP/AguRDLe31ZFjAcHz0gC5dCwN?= =?us-ascii?q?di+kQcMl4s1RncofNPt0LbO1BErMe02nVg8=3D?= X-IPAS-Result: =?us-ascii?q?A2GrAwBABIZY/wHyM5BdGgEBAQECAQEBAQgBAQEBFQEBAQE?= =?us-ascii?q?CAQEBAQgBAQEBgxIBAQEBAR+BaY5NqEsih3RXAQEBAQEBAQECAQJgKIIzG4IcB?= =?us-ascii?q?gECFwEMExQgCwMDCQEBFykICAMBLQMBBQELEQcHCwUYBIhrn2I/jW06JgKKFgw?= =?us-ascii?q?mEo9EEQGGAAEEiQCHKoshkV2KLiaGJ0iQaDKBFFhzNyoIOoQ5HIICUoVIDRcHg?= =?us-ascii?q?hABAQE?= Received: from unknown (HELO tarius.tycho.ncsc.mil) ([144.51.242.1]) by emsm-gh1-uea10.nsa.gov with ESMTP; 23 Jan 2017 13:29:49 +0000 Received: from prometheus.infosec.tycho.ncsc.mil (prometheus [192.168.25.40]) by tarius.tycho.ncsc.mil (8.14.4/8.14.4) with ESMTP id v0NDTleu009654; Mon, 23 Jan 2017 08:29:48 -0500 Received: from tarius.tycho.ncsc.mil (tarius.infosec.tycho.ncsc.mil [144.51.242.1]) by prometheus.infosec.tycho.ncsc.mil (8.15.2/8.15.2) with ESMTP id v0L06ZTQ040458 for ; Fri, 20 Jan 2017 19:06:35 -0500 Received: from goalie.tycho.ncsc.mil (goalie [144.51.242.250]) by tarius.tycho.ncsc.mil (8.14.4/8.14.4) with ESMTP id v0L06Z1E009808 for ; Fri, 20 Jan 2017 19:06:35 -0500 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: A1CJAQBMpYJYhrLAVdFeHAEBBAEBCgEBgz0BAQEBAYIItzWIH1cBAgEBAQEBAhMBAQEICwsKHYUaBhoBDFIQUTQBBQEcBxKJBqJmP41tOop6CQEIlVYFiQCHKYsfkVqKLoZNSJBmMoEUgX8qCIQkAU4cggEdNYZuK4IQAQEB X-IPAS-Result: A1CJAQBMpYJYhrLAVdFeHAEBBAEBCgEBgz0BAQEBAYIItzWIH1cBAgEBAQEBAhMBAQEICwsKHYUaBhoBDFIQUTQBBQEcBxKJBqJmP41tOop6CQEIlVYFiQCHKYsfkVqKLoZNSJBmMoEUgX8qCIQkAU4cggEdNYZuK4IQAQEB X-IronPort-AV: E=Sophos;i="5.33,260,1477972800"; d="scan'208";a="5915770" Received: from emsm-gh1-uea11.corp.nsa.gov (HELO emsm-gh1-uea11.nsa.gov) ([10.208.41.37]) by goalie.tycho.ncsc.mil with ESMTP; 20 Jan 2017 19:06:32 -0500 IronPort-PHdr: =?us-ascii?q?9a23=3A/ocM/RdPJb5m4gnkzGKP0LuvlGMj4u6mDksu8pMi?= =?us-ascii?q?zoh2WeGdxcS5Zx7h7PlgxGXEQZ/co6odzbGH7+a8BSdavd6oizMrSNR0TRgLiM?= =?us-ascii?q?EbzUQLIfWuLgnFFsPsdDEwB89YVVVorDmROElRH9viNRWJ+iXhpTEdFQ/iOgVr?= =?us-ascii?q?O+/7BpDdj9it1+C15pbffxhEiCCzbL52Ixi6twrcu8YZjYd8Jas61wfErGZPd+?= =?us-ascii?q?lK321jOEidnwz75se+/Z5j9zpftvc8/MNeUqv0Yro1Q6VAADspL2466svrtQLe?= =?us-ascii?q?TQSU/XsTTn8WkhtTDAfb6hzxQ4r8vTH7tup53ymaINH2QLUpUjms86tnVBnlgz?= =?us-ascii?q?oBOjUk8m/Yl9Zwgbpbrhy/uhJxzY3aboaXO/pwZa7RYc8WSHBdUstLSyBNHoWx?= =?us-ascii?q?ZJYPAeobOuZYqpHwqV4QohugBAmsAv7kxyFWiX/s2601zechHh/Y0wc9GN8BrG?= =?us-ascii?q?rbrM/zNKgMUuC60rfHwC7fYPNWwzf9743IchE8ofGJR75wdtDRyUY2Gg7Dk16e?= =?us-ascii?q?qpTlMiuL2ugRt2WX9eltWOK1h2I6rwx9vCKjytouh4TKgI8e10rK+j9jwIkvIN?= =?us-ascii?q?21UE57bsCgEJtXryyaMpF5QsImQ21xoCY6xKEKtYe1fCQXypkqxATTa/OAc4iP?= =?us-ascii?q?7RLjUPieLS1ki3JifbKznxey8U6+xe3gTsS4zkpGoy5fntTPtn0BzQHf58yZRv?= =?us-ascii?q?dn40us2zWC2xjW6u5eIEA0kaTbK4Qmwr41jpccrVrMHjXwmEroj6+ZaFsr9/On?= =?us-ascii?q?6+TgZbXmqZucOJFuhg7iNaQun9SzAf4kPQgWQ2ib5eO82aX4/ULnRLVKj/s2kr?= =?us-ascii?q?TWsZ3BOcQaprK2Aw9S0oo57Ra/FC2p3M4XnXkAMlIWMC6A2pP1Nl/ALfa+DvO2?= =?us-ascii?q?mE+hiitD3P3NI7vsHtPGKX2H2LfsZ7xw8VJ0xw01wddFoZtMA7cIZvXpVQn4qZ?= =?us-ascii?q?iQAhYnPgmcz+/5BdB50Y0CH2SCHuvRKKrPtXeQ7/8rZuyLY5UY/j36Lrxt/PL1?= =?us-ascii?q?pWMokl8aO6+y1N0Yb278Vvl+Kl+YelL0i80ACn8OtwEzCuvwhw6sSzlWMlW/Qa?= =?us-ascii?q?M6rho2EoSrDorODtSmjaaH0SS2E7VdZnpBD1GRFDHvbYrSCKREUz6bPsI0ym9M?= =?us-ascii?q?brOmUYJ0jRw=3D?= X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: =?us-ascii?q?A0EdAgCCpYJYhrLAVdFeHAEBBAEBCgEBF?= =?us-ascii?q?wEBBAEBCgEBgxIBAQEBAYIItzWIH1cBAQEBAQEBAQIBAhABAQEICwsKHTCCMxm?= =?us-ascii?q?CHgYaAQxSEFE0AQUBHAcSiQaiZz+NbTqKegkBCJVWBYkAhymLH5Faii6GTUiQZ?= =?us-ascii?q?jKBFIIAKgiEJAFOHIIBHTWGbiuCEAEBAQ?= X-IPAS-Result: =?us-ascii?q?A0EdAgCCpYJYhrLAVdFeHAEBBAEBCgEBFwEBBAEBCgEBgxI?= =?us-ascii?q?BAQEBAYIItzWIH1cBAQEBAQEBAQIBAhABAQEICwsKHTCCMxmCHgYaAQxSEFE0A?= =?us-ascii?q?QUBHAcSiQaiZz+NbTqKegkBCJVWBYkAhymLH5Faii6GTUiQZjKBFIIAKgiEJAF?= =?us-ascii?q?OHIIBHTWGbiuCEAEBAQ?= X-IronPort-AV: E=Sophos;i="5.33,260,1477958400"; d="scan'208";a="2468374" X-IronPort-Outbreak-Status: No, level 0, Unknown - Unknown Received: from mail-pf0-f178.google.com ([209.85.192.178]) by emsm-gh1-uea11.nsa.gov with ESMTP/TLS/AES128-GCM-SHA256; 21 Jan 2017 00:06:29 +0000 Received: by mail-pf0-f178.google.com with SMTP id e4so25836584pfg.1 for ; Fri, 20 Jan 2017 16:06:29 -0800 (PST) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:cc:subject:date:message-id:in-reply-to :references; bh=W5cfkaMrfF8BY/OOmOzfDuNwaShJameO8u47ONe8u1Y=; b=UWl8QgAjXx9ALzQrFhgRXF+xp9YwSG6JmyfRJLpqgFJWorEzNDWJFnANnxYnrWnaXt WF4U4QLsyFtefEiY4lg2tiWD20YpVzDS4Ru68OqFz6UBYior0s7hopWKwPJTvgCuRyMD 44PlzN8SFbVof7WGLu82kbl5LlbrZD0xhhf4vEiRDgH+C+rGjEsZZVkHfFTol1Fe54ji MhebxSjScyXB2DSqK9L9jbxSzb/OcJqKsihHHDabvX5PUMa0rm85HJrA9f5jVwJgLx0V z3g1068KecNDZi4cpYEPOZHQnPnt0s4ecn7+ZTBK49DtBD1bL/mxOoJWklqvazb+mCoG Zcow== X-Gm-Message-State: AIkVDXLIii/dPKRwTX1VoUuK13efph2UfrQWyQhws7lWlifV1YNVZpkaQa+jF05B2iVKkse1 X-Received: by 10.84.210.233 with SMTP id a96mr25325607pli.72.1484957188289; Fri, 20 Jan 2017 16:06:28 -0800 (PST) Received: from kcl.mtv.corp.google.com ([172.22.66.15]) by smtp.gmail.com with ESMTPSA id 66sm19375359pfx.29.2017.01.20.16.06.27 (version=TLS1_2 cipher=ECDHE-RSA-AES128-SHA bits=128/128); Fri, 20 Jan 2017 16:06:27 -0800 (PST) From: Kevin Cernekee To: steffen.klassert@secunet.com, herbert@gondor.apana.org.au, davem@davemloft.net, paul@paul-moore.com, sds@tycho.nsa.gov, eparis@parisplace.org Subject: [PATCH 4/4] xfrm_user: Add new 32/64-agnostic netlink messages Date: Fri, 20 Jan 2017 16:05:07 -0800 Message-Id: <20170121000507.34381-5-cernekee@chromium.org> X-Mailer: git-send-email 2.11.0.483.g087da7b7c-goog In-Reply-To: <20170121000507.34381-1-cernekee@chromium.org> References: <20170121000507.34381-1-cernekee@chromium.org> X-Mailman-Approved-At: Mon, 23 Jan 2017 08:28:53 -0500 X-BeenThere: selinux@tycho.nsa.gov X-Mailman-Version: 2.1.20 Precedence: list List-Id: "Security-Enhanced Linux \(SELinux\) mailing list" List-Post: List-Help: Cc: netdev@vger.kernel.org, fw@strlen.de, dianders@chromium.org, linux-kernel@vger.kernel.org, selinux@tycho.nsa.gov, fan.du@windriver.com, dtor@chromium.org MIME-Version: 1.0 Errors-To: selinux-bounces@tycho.nsa.gov Sender: "Selinux" X-Virus-Scanned: ClamAV using ClamSMTP Add several new message types to address longstanding 32-bit/64-bit compatibility issues. Use xfrm_user_legacy to handle the existing message types, which will retain the old IDs for compatibility with existing binaries. For user->kernel messages, the nlmsg_type will determine whether to use the old format or the new format (for both requests and replies). For kernel->user multicasts, both types will be sent. setsockopt() will deduce the format from the length. Signed-off-by: Kevin Cernekee --- include/uapi/linux/xfrm.h | 152 ++++++++++++++++++++++++++++++--------- net/xfrm/xfrm_user.c | 136 ++++++++++++++++++++++++++++++++--- net/xfrm/xfrm_user.h | 75 ++++++++++++++++++++ net/xfrm/xfrm_user_legacy.c | 169 ++++++++++++++++++++++++++++---------------- security/selinux/nlmsgtab.c | 61 +++++++++------- 5 files changed, 466 insertions(+), 127 deletions(-) diff --git a/include/uapi/linux/xfrm.h b/include/uapi/linux/xfrm.h index 1fc62b239f1b..ae5f97681989 100644 --- a/include/uapi/linux/xfrm.h +++ b/include/uapi/linux/xfrm.h @@ -1,6 +1,7 @@ #ifndef _LINUX_XFRM_H #define _LINUX_XFRM_H +#include #include #include @@ -157,34 +158,34 @@ enum { enum { XFRM_MSG_BASE = 0x10, - XFRM_MSG_NEWSA = 0x10, -#define XFRM_MSG_NEWSA XFRM_MSG_NEWSA - XFRM_MSG_DELSA, -#define XFRM_MSG_DELSA XFRM_MSG_DELSA - XFRM_MSG_GETSA, -#define XFRM_MSG_GETSA XFRM_MSG_GETSA - - XFRM_MSG_NEWPOLICY, -#define XFRM_MSG_NEWPOLICY XFRM_MSG_NEWPOLICY - XFRM_MSG_DELPOLICY, -#define XFRM_MSG_DELPOLICY XFRM_MSG_DELPOLICY - XFRM_MSG_GETPOLICY, -#define XFRM_MSG_GETPOLICY XFRM_MSG_GETPOLICY - - XFRM_MSG_ALLOCSPI, -#define XFRM_MSG_ALLOCSPI XFRM_MSG_ALLOCSPI - XFRM_MSG_ACQUIRE, -#define XFRM_MSG_ACQUIRE XFRM_MSG_ACQUIRE - XFRM_MSG_EXPIRE, -#define XFRM_MSG_EXPIRE XFRM_MSG_EXPIRE - - XFRM_MSG_UPDPOLICY, -#define XFRM_MSG_UPDPOLICY XFRM_MSG_UPDPOLICY - XFRM_MSG_UPDSA, -#define XFRM_MSG_UPDSA XFRM_MSG_UPDSA - - XFRM_MSG_POLEXPIRE, -#define XFRM_MSG_POLEXPIRE XFRM_MSG_POLEXPIRE + XFRM_MSG_NEWSA_LEGACY = 0x10, +#define XFRM_MSG_NEWSA_LEGACY XFRM_MSG_NEWSA_LEGACY + XFRM_MSG_DELSA_LEGACY, +#define XFRM_MSG_DELSA_LEGACY XFRM_MSG_DELSA_LEGACY + XFRM_MSG_GETSA_LEGACY, +#define XFRM_MSG_GETSA_LEGACY XFRM_MSG_GETSA_LEGACY + + XFRM_MSG_NEWPOLICY_LEGACY, +#define XFRM_MSG_NEWPOLICY_LEGACY XFRM_MSG_NEWPOLICY_LEGACY + XFRM_MSG_DELPOLICY_LEGACY, +#define XFRM_MSG_DELPOLICY_LEGACY XFRM_MSG_DELPOLICY_LEGACY + XFRM_MSG_GETPOLICY_LEGACY, +#define XFRM_MSG_GETPOLICY_LEGACY XFRM_MSG_GETPOLICY_LEGACY + + XFRM_MSG_ALLOCSPI_LEGACY, +#define XFRM_MSG_ALLOCSPI_LEGACY XFRM_MSG_ALLOCSPI_LEGACY + XFRM_MSG_ACQUIRE_LEGACY, +#define XFRM_MSG_ACQUIRE_LEGACY XFRM_MSG_ACQUIRE_LEGACY + XFRM_MSG_EXPIRE_LEGACY, +#define XFRM_MSG_EXPIRE_LEGACY XFRM_MSG_EXPIRE_LEGACY + + XFRM_MSG_UPDPOLICY_LEGACY, +#define XFRM_MSG_UPDPOLICY_LEGACY XFRM_MSG_UPDPOLICY_LEGACY + XFRM_MSG_UPDSA_LEGACY, +#define XFRM_MSG_UPDSA_LEGACY XFRM_MSG_UPDSA_LEGACY + + XFRM_MSG_POLEXPIRE_LEGACY, +#define XFRM_MSG_POLEXPIRE_LEGACY XFRM_MSG_POLEXPIRE_LEGACY XFRM_MSG_FLUSHSA, #define XFRM_MSG_FLUSHSA XFRM_MSG_FLUSHSA @@ -214,6 +215,34 @@ enum { XFRM_MSG_MAPPING, #define XFRM_MSG_MAPPING XFRM_MSG_MAPPING + + XFRM_MSG_ALLOCSPI, +#define XFRM_MSG_ALLOCSPI XFRM_MSG_ALLOCSPI + XFRM_MSG_ACQUIRE, +#define XFRM_MSG_ACQUIRE XFRM_MSG_ACQUIRE + XFRM_MSG_EXPIRE, +#define XFRM_MSG_EXPIRE XFRM_MSG_EXPIRE + XFRM_MSG_POLEXPIRE, +#define XFRM_MSG_POLEXPIRE XFRM_MSG_POLEXPIRE + + XFRM_MSG_NEWSA, +#define XFRM_MSG_NEWSA XFRM_MSG_NEWSA + XFRM_MSG_UPDSA, +#define XFRM_MSG_UPDSA XFRM_MSG_UPDSA + XFRM_MSG_DELSA, +#define XFRM_MSG_DELSA XFRM_MSG_DELSA + XFRM_MSG_GETSA, +#define XFRM_MSG_GETSA XFRM_MSG_GETSA + + XFRM_MSG_NEWPOLICY, +#define XFRM_MSG_NEWPOLICY XFRM_MSG_NEWPOLICY + XFRM_MSG_UPDPOLICY, +#define XFRM_MSG_UPDPOLICY XFRM_MSG_UPDPOLICY + XFRM_MSG_DELPOLICY, +#define XFRM_MSG_DELPOLICY XFRM_MSG_DELPOLICY + XFRM_MSG_GETPOLICY, +#define XFRM_MSG_GETPOLICY XFRM_MSG_GETPOLICY + __XFRM_MSG_MAX }; #define XFRM_MSG_MAX (__XFRM_MSG_MAX - 1) @@ -221,7 +250,7 @@ enum { #define XFRM_NR_MSGTYPES (XFRM_MSG_MAX + 1 - XFRM_MSG_BASE) /* - * Generic LSM security context for comunicating to user space + * Generic LSM security context for communicating to user space * NOTE: Same format as sadb_x_sec_ctx */ struct xfrm_user_sec_ctx { @@ -357,6 +386,22 @@ struct xfrmu_spdhthresh { __u8 rbits; }; +/* Legacy structs are incompatible between 32-bit and 64-bit. */ +struct xfrm_usersa_info_legacy { + struct xfrm_selector sel; + struct xfrm_id id; + xfrm_address_t saddr; + struct xfrm_lifetime_cfg lft; + struct xfrm_lifetime_cur curlft; + struct xfrm_stats stats; + __u32 seq; + __u32 reqid; + __u16 family; + __u8 mode; /* XFRM_MODE_xxx */ + __u8 replay_window; + __u8 flags; +}; + struct xfrm_usersa_info { struct xfrm_selector sel; struct xfrm_id id; @@ -378,7 +423,8 @@ struct xfrm_usersa_info { #define XFRM_STATE_AF_UNSPEC 32 #define XFRM_STATE_ALIGN4 64 #define XFRM_STATE_ESN 128 -}; + __u8 reserved[7]; +} __packed; #define XFRM_SA_XFLAG_DONT_ENCAP_DSCP 1 @@ -396,10 +442,28 @@ struct xfrm_aevent_id { __u32 reqid; }; +struct xfrm_userspi_info_legacy { + struct xfrm_usersa_info_legacy info; + __u32 min; + __u32 max; +}; + struct xfrm_userspi_info { struct xfrm_usersa_info info; __u32 min; __u32 max; +} __packed; + +struct xfrm_userpolicy_info_legacy { + struct xfrm_selector sel; + struct xfrm_lifetime_cfg lft; + struct xfrm_lifetime_cur curlft; + __u32 priority; + __u32 index; + __u8 dir; + __u8 action; + __u8 flags; + __u8 share; }; struct xfrm_userpolicy_info { @@ -417,7 +481,8 @@ struct xfrm_userpolicy_info { /* Automatically expand selector to include matching ICMP payloads. */ #define XFRM_POLICY_ICMP 2 __u8 share; -}; + __u8 reserved[4]; +} __packed; struct xfrm_userpolicy_id { struct xfrm_selector sel; @@ -425,6 +490,17 @@ struct xfrm_userpolicy_id { __u8 dir; }; +struct xfrm_user_acquire_legacy { + struct xfrm_id id; + xfrm_address_t saddr; + struct xfrm_selector sel; + struct xfrm_userpolicy_info_legacy policy; + __u32 aalgos; + __u32 ealgos; + __u32 calgos; + __u32 seq; +}; + struct xfrm_user_acquire { struct xfrm_id id; xfrm_address_t saddr; @@ -434,17 +510,29 @@ struct xfrm_user_acquire { __u32 ealgos; __u32 calgos; __u32 seq; +} __packed; + +struct xfrm_user_expire_legacy { + struct xfrm_usersa_info_legacy state; + __u8 hard; }; struct xfrm_user_expire { struct xfrm_usersa_info state; __u8 hard; + __u8 reserved[7]; +} __packed; + +struct xfrm_user_polexpire_legacy { + struct xfrm_userpolicy_info_legacy pol; + __u8 hard; }; struct xfrm_user_polexpire { struct xfrm_userpolicy_info pol; __u8 hard; -}; + __u8 reserved[7]; +} __packed; struct xfrm_usersa_flush { __u8 proto; diff --git a/net/xfrm/xfrm_user.c b/net/xfrm/xfrm_user.c index 4d733f02c3a1..5456dde974bc 100644 --- a/net/xfrm/xfrm_user.c +++ b/net/xfrm/xfrm_user.c @@ -2350,6 +2350,32 @@ static const int xfrm_msg_min[XFRM_NR_MSGTYPES] = { [XFRM_MSG_GETSADINFO - XFRM_MSG_BASE] = sizeof(u32), [XFRM_MSG_NEWSPDINFO - XFRM_MSG_BASE] = sizeof(u32), [XFRM_MSG_GETSPDINFO - XFRM_MSG_BASE] = sizeof(u32), + + [XFRM_MSG_ALLOCSPI_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_userspi_info_legacy), + [XFRM_MSG_ACQUIRE_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_user_acquire_legacy), + [XFRM_MSG_EXPIRE_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_user_expire_legacy), + [XFRM_MSG_POLEXPIRE_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_user_polexpire_legacy), + + [XFRM_MSG_NEWSA_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_usersa_info_legacy), + [XFRM_MSG_UPDSA_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_usersa_info_legacy), + [XFRM_MSG_DELSA_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_usersa_id), + [XFRM_MSG_GETSA_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_usersa_id), + [XFRM_MSG_NEWPOLICY_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_userpolicy_info_legacy), + [XFRM_MSG_UPDPOLICY_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_userpolicy_info_legacy), + [XFRM_MSG_DELPOLICY_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_userpolicy_id), + [XFRM_MSG_GETPOLICY_LEGACY - XFRM_MSG_BASE] = + XMSGSIZE(xfrm_userpolicy_id), }; #undef XMSGSIZE @@ -2396,6 +2422,7 @@ static const struct xfrm_link { int (*done)(struct netlink_callback *); const struct nla_policy *nla_pol; int nla_max; + bool legacy; } xfrm_dispatch[XFRM_NR_MSGTYPES] = { [XFRM_MSG_NEWSA - XFRM_MSG_BASE] = { .doit = xfrm_add_sa }, [XFRM_MSG_DELSA - XFRM_MSG_BASE] = { .doit = xfrm_del_sa }, @@ -2423,6 +2450,62 @@ static const struct xfrm_link { .nla_pol = xfrma_spd_policy, .nla_max = XFRMA_SPD_MAX }, [XFRM_MSG_GETSPDINFO - XFRM_MSG_BASE] = { .doit = xfrm_get_spdinfo }, + +#ifdef CONFIG_XFRM_USER_LEGACY + [XFRM_MSG_ALLOCSPI_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_alloc_userspi_legacy, + .legacy = true, + }, + [XFRM_MSG_ACQUIRE_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_acquire_legacy, + .legacy = true, + }, + [XFRM_MSG_EXPIRE_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_sa_expire_legacy, + .legacy = true, + }, + [XFRM_MSG_POLEXPIRE_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_pol_expire_legacy, + .legacy = true, + }, + + [XFRM_MSG_NEWSA_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_sa_legacy, + .legacy = true, + }, + [XFRM_MSG_UPDSA_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_sa_legacy, + .legacy = true, + }, + [XFRM_MSG_DELSA_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_del_sa_legacy, + .legacy = true, + }, + [XFRM_MSG_GETSA_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_get_sa_legacy, + .dump = xfrm_dump_sa_legacy, + .done = xfrm_dump_sa_done_legacy, + .legacy = true, + }, + [XFRM_MSG_NEWPOLICY_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_policy_legacy, + .legacy = true, + }, + [XFRM_MSG_UPDPOLICY_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_add_policy_legacy, + .legacy = true, + }, + [XFRM_MSG_DELPOLICY_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_get_policy_legacy, + .legacy = true, + }, + [XFRM_MSG_GETPOLICY_LEGACY - XFRM_MSG_BASE] = { + .doit = xfrm_get_policy_legacy, + .dump = xfrm_dump_policy_legacy, + .done = xfrm_dump_policy_done_legacy, + .legacy = true, + }, +#endif /* CONFIG_XFRM_USER_LEGACY */ }; static int xfrm_user_rcv_msg(struct sk_buff *skb, struct nlmsghdr *nlh) @@ -2432,11 +2515,6 @@ static int xfrm_user_rcv_msg(struct sk_buff *skb, struct nlmsghdr *nlh) const struct xfrm_link *link; int type, err; -#ifdef CONFIG_COMPAT - if (in_compat_syscall()) - return -EOPNOTSUPP; -#endif - type = nlh->nlmsg_type; if (type > XFRM_MSG_MAX) return -EINVAL; @@ -2444,12 +2522,19 @@ static int xfrm_user_rcv_msg(struct sk_buff *skb, struct nlmsghdr *nlh) type -= XFRM_MSG_BASE; link = &xfrm_dispatch[type]; +#ifdef CONFIG_COMPAT + if (link->legacy && in_compat_syscall()) + return -EOPNOTSUPP; +#endif + /* All operations require privileges, even GET */ if (!netlink_net_capable(skb, CAP_NET_ADMIN)) return -EPERM; if ((type == (XFRM_MSG_GETSA - XFRM_MSG_BASE) || - type == (XFRM_MSG_GETPOLICY - XFRM_MSG_BASE)) && + type == (XFRM_MSG_GETPOLICY - XFRM_MSG_BASE) || + type == (XFRM_MSG_GETSA_LEGACY - XFRM_MSG_BASE) || + type == (XFRM_MSG_GETPOLICY_LEGACY - XFRM_MSG_BASE)) && (nlh->nlmsg_flags & NLM_F_DUMP)) { if (link->dump == NULL) return -EINVAL; @@ -2670,16 +2755,23 @@ static int xfrm_notify_sa(const struct xfrm_state *x, const struct km_event *c) static int xfrm_send_state_notify(const struct xfrm_state *x, const struct km_event *c) { + int err; switch (c->event) { case XFRM_MSG_EXPIRE: - return xfrm_exp_state_notify(x, c); + err = xfrm_exp_state_notify(x, c); + if (err) + return err; + return xfrm_exp_state_notify_legacy(x, c); case XFRM_MSG_NEWAE: return xfrm_aevent_state_notify(x, c); case XFRM_MSG_DELSA: case XFRM_MSG_UPDSA: case XFRM_MSG_NEWSA: - return xfrm_notify_sa(x, c); + err = xfrm_notify_sa(x, c); + if (err) + return err; + return xfrm_notify_sa_legacy(x, c); case XFRM_MSG_FLUSHSA: return xfrm_notify_sa_flush(c); default: @@ -2748,6 +2840,7 @@ static int xfrm_send_acquire(struct xfrm_state *x, { struct net *net = xs_net(x); struct sk_buff *skb; + int err; skb = nlmsg_new(xfrm_acquire_msgsize(x, xp), GFP_ATOMIC); if (skb == NULL) @@ -2756,7 +2849,11 @@ static int xfrm_send_acquire(struct xfrm_state *x, if (build_acquire(skb, x, xt, xp) < 0) BUG(); - return xfrm_nlmsg_multicast(net, skb, 0, XFRMNLGRP_ACQUIRE); + err = xfrm_nlmsg_multicast(net, skb, 0, XFRMNLGRP_ACQUIRE); + if (err) + return err; + + return xfrm_send_acquire_legacy(x, xt, xp); } /* User gives us xfrm_user_policy_info followed by an array of 0 @@ -2799,6 +2896,16 @@ static struct xfrm_policy *xfrm_compile_policy(struct sock *sk, int opt, return NULL; nr = ((len - sizeof(*p)) / sizeof(*ut)); + if (len == (nr + 1) * sizeof(*ut) + sizeof(*p) - sizeof(u32)) { + /* The user passed a legacy xfrm_userpolicy_info struct whose + * length is padded to 32 bits instead of 64, so the above + * division had a remainder. Adjust the start address and + * count accordingly. + */ + ut = (void *)data + sizeof(*p) - sizeof(u32); + nr++; + } + if (validate_tmpl(nr, ut, p->sel.family)) return NULL; @@ -2979,16 +3086,23 @@ static int xfrm_send_policy_notify(const struct xfrm_policy *xp, int dir, const struct km_event *c) { + int err; switch (c->event) { case XFRM_MSG_NEWPOLICY: case XFRM_MSG_UPDPOLICY: case XFRM_MSG_DELPOLICY: - return xfrm_notify_policy(xp, dir, c); + err = xfrm_notify_policy(xp, dir, c); + if (err) + return err; + return xfrm_notify_policy_legacy(xp, dir, c); case XFRM_MSG_FLUSHPOLICY: return xfrm_notify_policy_flush(c); case XFRM_MSG_POLEXPIRE: - return xfrm_exp_policy_notify(xp, dir, c); + err = xfrm_exp_policy_notify(xp, dir, c); + if (err) + return err; + return xfrm_exp_policy_notify_legacy(xp, dir, c); default: printk(KERN_NOTICE "xfrm_user: Unknown Policy event %d\n", c->event); diff --git a/net/xfrm/xfrm_user.h b/net/xfrm/xfrm_user.h index 29bab2ebee83..78627d1c1cec 100644 --- a/net/xfrm/xfrm_user.h +++ b/net/xfrm/xfrm_user.h @@ -1,6 +1,7 @@ #ifndef _XFRM_USER_H #define _XFRM_USER_H +#include #include #include #include @@ -87,4 +88,78 @@ static inline int copy_to_user_state_sec_ctx(const struct xfrm_state *x, return 0; } +/* Legacy functions */ + +#ifdef CONFIG_XFRM_USER_LEGACY +int xfrm_alloc_userspi_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_add_pol_expire_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_add_sa_expire_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_add_acquire_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); + +int xfrm_add_sa_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_del_sa_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_dump_sa_done_legacy(struct netlink_callback *cb); +int xfrm_dump_sa_legacy(struct sk_buff *skb, struct netlink_callback *cb); +int xfrm_get_sa_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_add_policy_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); +int xfrm_dump_policy_done_legacy(struct netlink_callback *cb); +int xfrm_dump_policy_legacy(struct sk_buff *skb, struct netlink_callback *cb); +int xfrm_get_policy_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, + struct nlattr **attrs); + +int xfrm_exp_state_notify_legacy(const struct xfrm_state *x, + const struct km_event *c); +int xfrm_notify_sa_legacy(const struct xfrm_state *x, const struct km_event *c); +int xfrm_send_acquire_legacy(struct xfrm_state *x, + const struct xfrm_tmpl *xt, + const struct xfrm_policy *xp); +int xfrm_exp_policy_notify_legacy(const struct xfrm_policy *xp, + int dir, + const struct km_event *c); +int xfrm_notify_policy_legacy(const struct xfrm_policy *xp, + int dir, + const struct km_event *c); +#else /* CONFIG_XFRM_USER_LEGACY */ +static inline int xfrm_exp_state_notify_legacy(const struct xfrm_state *x, + const struct km_event *c) +{ + return 0; +} + +static inline int xfrm_notify_sa_legacy(const struct xfrm_state *x, + const struct km_event *c) +{ + return 0; +} + +static inline int xfrm_send_acquire_legacy(struct xfrm_state *x, + const struct xfrm_tmpl *xt, + const struct xfrm_policy *xp) +{ + return 0; +} + +static inline int xfrm_exp_policy_notify_legacy(const struct xfrm_policy *xp, + int dir, + const struct km_event *c) +{ + return 0; +} + +static inline int xfrm_notify_policy_legacy(const struct xfrm_policy *xp, + int dir, + const struct km_event *c) +{ + return 0; +} +#endif /* CONFIG_XFRM_USER_LEGACY */ + #endif /* _XFRM_USER_H */ diff --git a/net/xfrm/xfrm_user_legacy.c b/net/xfrm/xfrm_user_legacy.c index 058accfefc83..aa48845b47fa 100644 --- a/net/xfrm/xfrm_user_legacy.c +++ b/net/xfrm/xfrm_user_legacy.c @@ -29,28 +29,33 @@ #include #include "xfrm_user.h" -static int xfrm_add_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_add_sa_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); - const struct xfrm_usersa_info *p = nlmsg_data(nlh); + const struct xfrm_usersa_info_legacy *p = nlmsg_data(nlh); struct xfrm_state *x; int err; struct km_event c; - err = xfrm_verify_newsa_info(p, attrs); + /* This cast is safe because the only difference is end padding. */ + err = xfrm_verify_newsa_info((const struct xfrm_usersa_info *)p, attrs); if (err) return err; - x = xfrm_state_construct(net, p, attrs, &err); + x = xfrm_state_construct(net, (const struct xfrm_usersa_info *)p, + attrs, &err); if (!x) return err; xfrm_state_hold(x); - if (nlh->nlmsg_type == XFRM_MSG_NEWSA) + if (nlh->nlmsg_type == XFRM_MSG_NEWSA_LEGACY) { err = xfrm_state_add(x); - else + c.event = XFRM_MSG_NEWSA; + } else { err = xfrm_state_update(x); + c.event = XFRM_MSG_UPDSA; + } xfrm_audit_state_add(x, err ? 0 : 1, true); @@ -62,7 +67,6 @@ static int xfrm_add_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, c.seq = nlh->nlmsg_seq; c.portid = nlh->nlmsg_pid; - c.event = nlh->nlmsg_type; km_state_notify(x, &c); out: @@ -70,7 +74,7 @@ static int xfrm_add_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, return err; } -static int xfrm_del_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_del_sa_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); @@ -98,7 +102,7 @@ static int xfrm_del_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, c.seq = nlh->nlmsg_seq; c.portid = nlh->nlmsg_pid; - c.event = nlh->nlmsg_type; + c.event = XFRM_MSG_DELSA; km_state_notify(x, &c); out: @@ -108,7 +112,7 @@ static int xfrm_del_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, } static void copy_to_user_state(const struct xfrm_state *x, - struct xfrm_usersa_info *p) + struct xfrm_usersa_info_legacy *p) { memset(p, 0, sizeof(*p)); memcpy(&p->id, &x->id, sizeof(p->id)); @@ -128,7 +132,7 @@ static void copy_to_user_state(const struct xfrm_state *x, } static int copy_to_user_state_extra(const struct xfrm_state *x, - struct xfrm_usersa_info *p, + struct xfrm_usersa_info_legacy *p, struct sk_buff *skb) { int ret = 0; @@ -209,12 +213,12 @@ static int dump_one_state(const struct xfrm_state *x, int count, void *ptr) struct xfrm_dump_info *sp = ptr; struct sk_buff *in_skb = sp->in_skb; struct sk_buff *skb = sp->out_skb; - struct xfrm_usersa_info *p; + struct xfrm_usersa_info_legacy *p; struct nlmsghdr *nlh; int err; nlh = nlmsg_put(skb, NETLINK_CB(in_skb).portid, sp->nlmsg_seq, - XFRM_MSG_NEWSA, sizeof(*p), sp->nlmsg_flags); + XFRM_MSG_NEWSA_LEGACY, sizeof(*p), sp->nlmsg_flags); if (nlh == NULL) return -EMSGSIZE; @@ -229,7 +233,7 @@ static int dump_one_state(const struct xfrm_state *x, int count, void *ptr) return 0; } -static int xfrm_dump_sa_done(struct netlink_callback *cb) +int xfrm_dump_sa_done_legacy(struct netlink_callback *cb) { struct xfrm_state_walk *walk = (struct xfrm_state_walk *) &cb->args[1]; struct sock *sk = cb->skb->sk; @@ -241,7 +245,7 @@ static int xfrm_dump_sa_done(struct netlink_callback *cb) } static const struct nla_policy xfrma_policy[XFRMA_MAX+1]; -static int xfrm_dump_sa(struct sk_buff *skb, struct netlink_callback *cb) +int xfrm_dump_sa_legacy(struct sk_buff *skb, struct netlink_callback *cb) { struct net *net = sock_net(skb->sk); struct xfrm_state_walk *walk = (struct xfrm_state_walk *) &cb->args[1]; @@ -311,7 +315,7 @@ static struct sk_buff *xfrm_state_netlink(struct sk_buff *in_skb, return skb; } -static int xfrm_get_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_get_sa_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); @@ -335,12 +339,12 @@ static int xfrm_get_sa(struct sk_buff *skb, const struct nlmsghdr *nlh, return err; } -static int xfrm_alloc_userspi(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_alloc_userspi_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); struct xfrm_state *x; - const struct xfrm_userspi_info *p; + const struct xfrm_userspi_info_legacy *p; struct sk_buff *resp_skb; const xfrm_address_t *daddr; int family; @@ -395,7 +399,7 @@ static int xfrm_alloc_userspi(struct sk_buff *skb, const struct nlmsghdr *nlh, } static void copy_to_user_policy(const struct xfrm_policy *xp, - struct xfrm_userpolicy_info *p, + struct xfrm_userpolicy_info_legacy *p, int dir) { memset(p, 0, sizeof(*p)); @@ -411,24 +415,27 @@ static void copy_to_user_policy(const struct xfrm_policy *xp, p->share = XFRM_SHARE_ANY; /* XXX xp->share */ } -static int xfrm_add_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_add_policy_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); - const struct xfrm_userpolicy_info *p = nlmsg_data(nlh); + const struct xfrm_userpolicy_info_legacy *p = nlmsg_data(nlh); struct xfrm_policy *xp; struct km_event c; int err; int excl; - err = xfrm_verify_newpolicy_info(p); + /* This cast is safe because the only difference is end padding. */ + err = xfrm_verify_newpolicy_info( + (const struct xfrm_userpolicy_info *)p); if (err) return err; err = xfrm_verify_sec_ctx_len(attrs); if (err) return err; - xp = xfrm_policy_construct(net, p, attrs, &err); + xp = xfrm_policy_construct(net, (const struct xfrm_userpolicy_info *)p, + attrs, &err); if (!xp) return err; @@ -436,7 +443,13 @@ static int xfrm_add_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, * Aha! this is anti-netlink really i.e more pfkey derived * in netlink excl is a flag and you wouldnt need * a type XFRM_MSG_UPDPOLICY - JHS */ - excl = nlh->nlmsg_type == XFRM_MSG_NEWPOLICY; + if (nlh->nlmsg_type == XFRM_MSG_NEWPOLICY_LEGACY) { + excl = 1; + c.event = XFRM_MSG_NEWPOLICY; + } else { + excl = 0; + c.event = XFRM_MSG_UPDPOLICY; + } err = xfrm_policy_insert(p->dir, xp, excl); xfrm_audit_policy_add(xp, err ? 0 : 1, true); @@ -446,7 +459,6 @@ static int xfrm_add_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, return err; } - c.event = nlh->nlmsg_type; c.seq = nlh->nlmsg_seq; c.portid = nlh->nlmsg_pid; km_policy_notify(xp, p->dir, &c); @@ -471,14 +483,14 @@ static int dump_one_policy(const struct xfrm_policy *xp, void *ptr) { struct xfrm_dump_info *sp = ptr; - struct xfrm_userpolicy_info *p; + struct xfrm_userpolicy_info_legacy *p; struct sk_buff *in_skb = sp->in_skb; struct sk_buff *skb = sp->out_skb; struct nlmsghdr *nlh; int err; nlh = nlmsg_put(skb, NETLINK_CB(in_skb).portid, sp->nlmsg_seq, - XFRM_MSG_NEWPOLICY, sizeof(*p), sp->nlmsg_flags); + XFRM_MSG_NEWPOLICY_LEGACY, sizeof(*p), sp->nlmsg_flags); if (nlh == NULL) return -EMSGSIZE; @@ -499,7 +511,7 @@ static int dump_one_policy(const struct xfrm_policy *xp, return 0; } -static int xfrm_dump_policy_done(struct netlink_callback *cb) +int xfrm_dump_policy_done_legacy(struct netlink_callback *cb) { struct xfrm_policy_walk *walk = (struct xfrm_policy_walk *) &cb->args[1]; struct net *net = sock_net(cb->skb->sk); @@ -508,7 +520,7 @@ static int xfrm_dump_policy_done(struct netlink_callback *cb) return 0; } -static int xfrm_dump_policy(struct sk_buff *skb, struct netlink_callback *cb) +int xfrm_dump_policy_legacy(struct sk_buff *skb, struct netlink_callback *cb) { struct net *net = sock_net(skb->sk); struct xfrm_policy_walk *walk = (struct xfrm_policy_walk *) &cb->args[1]; @@ -559,7 +571,7 @@ static struct sk_buff *xfrm_policy_netlink(struct sk_buff *in_skb, return skb; } -static int xfrm_get_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_get_policy_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); @@ -573,7 +585,13 @@ static int xfrm_get_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, u32 mark = xfrm_mark_get(attrs, &m); p = nlmsg_data(nlh); - delete = nlh->nlmsg_type == XFRM_MSG_DELPOLICY; + if (nlh->nlmsg_type == XFRM_MSG_DELPOLICY_LEGACY) { + delete = 1; + c.event = XFRM_MSG_DELPOLICY; + } else { + delete = 0; + c.event = XFRM_MSG_GETPOLICY; + } err = xfrm_copy_from_user_policy_type(&type, attrs); if (err) @@ -625,7 +643,6 @@ static int xfrm_get_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, goto out; c.data.byid = p->index; - c.event = nlh->nlmsg_type; c.seq = nlh->nlmsg_seq; c.portid = nlh->nlmsg_pid; km_policy_notify(xp, p->dir, &c); @@ -638,13 +655,13 @@ static int xfrm_get_policy(struct sk_buff *skb, const struct nlmsghdr *nlh, return err; } -static int xfrm_add_pol_expire(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_add_pol_expire_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); struct xfrm_policy *xp; - const struct xfrm_user_polexpire *up = nlmsg_data(nlh); - const struct xfrm_userpolicy_info *p = &up->pol; + const struct xfrm_user_polexpire_legacy *up = nlmsg_data(nlh); + const struct xfrm_userpolicy_info_legacy *p = &up->pol; u8 type = XFRM_POLICY_TYPE_MAIN; int err = -ENOENT; struct xfrm_mark m; @@ -698,14 +715,14 @@ static int xfrm_add_pol_expire(struct sk_buff *skb, const struct nlmsghdr *nlh, return err; } -static int xfrm_add_sa_expire(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_add_sa_expire_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); struct xfrm_state *x; int err; - const struct xfrm_user_expire *ue = nlmsg_data(nlh); - const struct xfrm_usersa_info *p = &ue->state; + const struct xfrm_user_expire_legacy *ue = nlmsg_data(nlh); + const struct xfrm_usersa_info_legacy *p = &ue->state; struct xfrm_mark m; u32 mark = xfrm_mark_get(attrs, &m); @@ -732,7 +749,7 @@ static int xfrm_add_sa_expire(struct sk_buff *skb, const struct nlmsghdr *nlh, return err; } -static int xfrm_add_acquire(struct sk_buff *skb, const struct nlmsghdr *nlh, +int xfrm_add_acquire_legacy(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr **attrs) { struct net *net = sock_net(skb->sk); @@ -742,7 +759,7 @@ static int xfrm_add_acquire(struct sk_buff *skb, const struct nlmsghdr *nlh, struct nlattr *rt = attrs[XFRMA_TMPL]; struct xfrm_mark mark; - const struct xfrm_user_acquire *ua = nlmsg_data(nlh); + const struct xfrm_user_acquire_legacy *ua = nlmsg_data(nlh); struct xfrm_state *x = xfrm_state_alloc(net); int err = -ENOMEM; @@ -751,12 +768,15 @@ static int xfrm_add_acquire(struct sk_buff *skb, const struct nlmsghdr *nlh, xfrm_mark_get(attrs, &mark); - err = xfrm_verify_newpolicy_info(&ua->policy); + /* This cast is safe because the only difference is end padding. */ + err = xfrm_verify_newpolicy_info( + (const struct xfrm_userpolicy_info *)&ua->policy); if (err) goto free_state; /* build an XP */ - xp = xfrm_policy_construct(net, &ua->policy, attrs, &err); + xp = xfrm_policy_construct(net, (const struct xfrm_userpolicy_info *) + &ua->policy, attrs, &err); if (!xp) goto free_state; @@ -793,7 +813,7 @@ static int xfrm_add_acquire(struct sk_buff *skb, const struct nlmsghdr *nlh, static inline size_t xfrm_expire_msgsize(void) { - return NLMSG_ALIGN(sizeof(struct xfrm_user_expire)) + return NLMSG_ALIGN(sizeof(struct xfrm_user_expire_legacy)) + nla_total_size(sizeof(struct xfrm_mark)); } @@ -801,11 +821,12 @@ static int build_expire(struct sk_buff *skb, const struct xfrm_state *x, const struct km_event *c) { - struct xfrm_user_expire *ue; + struct xfrm_user_expire_legacy *ue; struct nlmsghdr *nlh; int err; - nlh = nlmsg_put(skb, c->portid, 0, XFRM_MSG_EXPIRE, sizeof(*ue), 0); + nlh = nlmsg_put(skb, c->portid, 0, XFRM_MSG_EXPIRE_LEGACY, + sizeof(*ue), 0); if (nlh == NULL) return -EMSGSIZE; @@ -821,7 +842,7 @@ static int build_expire(struct sk_buff *skb, return 0; } -static int xfrm_exp_state_notify(const struct xfrm_state *x, +int xfrm_exp_state_notify_legacy(const struct xfrm_state *x, const struct km_event *c) { struct net *net = xs_net(x); @@ -839,15 +860,16 @@ static int xfrm_exp_state_notify(const struct xfrm_state *x, return xfrm_nlmsg_multicast(net, skb, 0, XFRMNLGRP_EXPIRE); } -static int xfrm_notify_sa(const struct xfrm_state *x, const struct km_event *c) +int xfrm_notify_sa_legacy(const struct xfrm_state *x, const struct km_event *c) { struct net *net = xs_net(x); - struct xfrm_usersa_info *p; + struct xfrm_usersa_info_legacy *p; struct xfrm_usersa_id *id; struct nlmsghdr *nlh; struct sk_buff *skb; int len = xfrm_sa_len(x); int headlen, err; + u32 event = 0; headlen = sizeof(*p); if (c->event == XFRM_MSG_DELSA) { @@ -861,7 +883,19 @@ static int xfrm_notify_sa(const struct xfrm_state *x, const struct km_event *c) if (skb == NULL) return -ENOMEM; - nlh = nlmsg_put(skb, c->portid, c->seq, c->event, headlen, 0); + switch (c->event) { + case XFRM_MSG_NEWSA: + event = XFRM_MSG_NEWSA_LEGACY; + break; + case XFRM_MSG_UPDSA: + event = XFRM_MSG_UPDSA_LEGACY; + break; + case XFRM_MSG_DELSA: + event = XFRM_MSG_DELSA_LEGACY; + break; + } + + nlh = nlmsg_put(skb, c->portid, c->seq, event, headlen, 0); err = -EMSGSIZE; if (nlh == NULL) goto out_free_skb; @@ -899,7 +933,7 @@ static int xfrm_notify_sa(const struct xfrm_state *x, const struct km_event *c) static inline size_t xfrm_acquire_msgsize(const struct xfrm_state *x, const struct xfrm_policy *xp) { - return NLMSG_ALIGN(sizeof(struct xfrm_user_acquire)) + return NLMSG_ALIGN(sizeof(struct xfrm_user_acquire_legacy)) + nla_total_size(sizeof(struct xfrm_user_tmpl) * xp->xfrm_nr) + nla_total_size(sizeof(struct xfrm_mark)) + nla_total_size(xfrm_user_sec_ctx_size(x->security)) @@ -912,11 +946,11 @@ static int build_acquire(struct sk_buff *skb, const struct xfrm_policy *xp) { __u32 seq = xfrm_get_acqseq(); - struct xfrm_user_acquire *ua; + struct xfrm_user_acquire_legacy *ua; struct nlmsghdr *nlh; int err; - nlh = nlmsg_put(skb, 0, 0, XFRM_MSG_ACQUIRE, sizeof(*ua), 0); + nlh = nlmsg_put(skb, 0, 0, XFRM_MSG_ACQUIRE_LEGACY, sizeof(*ua), 0); if (nlh == NULL) return -EMSGSIZE; @@ -946,7 +980,7 @@ static int build_acquire(struct sk_buff *skb, return 0; } -static int xfrm_send_acquire(struct xfrm_state *x, +int xfrm_send_acquire_legacy(struct xfrm_state *x, const struct xfrm_tmpl *xt, const struct xfrm_policy *xp) { @@ -965,7 +999,7 @@ static int xfrm_send_acquire(struct xfrm_state *x, static inline size_t xfrm_polexpire_msgsize(const struct xfrm_policy *xp) { - return NLMSG_ALIGN(sizeof(struct xfrm_user_polexpire)) + return NLMSG_ALIGN(sizeof(struct xfrm_user_polexpire_legacy)) + nla_total_size(sizeof(struct xfrm_user_tmpl) * xp->xfrm_nr) + nla_total_size(xfrm_user_sec_ctx_size(xp->security)) + nla_total_size(sizeof(struct xfrm_mark)) @@ -977,12 +1011,13 @@ static int build_polexpire(struct sk_buff *skb, int dir, const struct km_event *c) { - struct xfrm_user_polexpire *upe; + struct xfrm_user_polexpire_legacy *upe; int hard = c->data.hard; struct nlmsghdr *nlh; int err; - nlh = nlmsg_put(skb, c->portid, 0, XFRM_MSG_POLEXPIRE, sizeof(*upe), 0); + nlh = nlmsg_put(skb, c->portid, 0, XFRM_MSG_POLEXPIRE_LEGACY, + sizeof(*upe), 0); if (nlh == NULL) return -EMSGSIZE; @@ -1005,7 +1040,7 @@ static int build_polexpire(struct sk_buff *skb, return 0; } -static int xfrm_exp_policy_notify(const struct xfrm_policy *xp, +int xfrm_exp_policy_notify_legacy(const struct xfrm_policy *xp, int dir, const struct km_event *c) { @@ -1022,19 +1057,21 @@ static int xfrm_exp_policy_notify(const struct xfrm_policy *xp, return xfrm_nlmsg_multicast(net, skb, 0, XFRMNLGRP_EXPIRE); } -static int xfrm_notify_policy(const struct xfrm_policy *xp, +int xfrm_notify_policy_legacy(const struct xfrm_policy *xp, int dir, const struct km_event *c) { int len = nla_total_size(sizeof(struct xfrm_user_tmpl) * xp->xfrm_nr); struct net *net = xp_net(xp); - struct xfrm_userpolicy_info *p; + struct xfrm_userpolicy_info_legacy *p; struct xfrm_userpolicy_id *id; struct nlmsghdr *nlh; struct sk_buff *skb; int headlen, err; + u32 event = 0; headlen = sizeof(*p); + if (c->event == XFRM_MSG_DELPOLICY) { len += nla_total_size(headlen); headlen = sizeof(*id); @@ -1047,7 +1084,19 @@ static int xfrm_notify_policy(const struct xfrm_policy *xp, if (skb == NULL) return -ENOMEM; - nlh = nlmsg_put(skb, c->portid, c->seq, c->event, headlen, 0); + switch (c->event) { + case XFRM_MSG_NEWPOLICY: + event = XFRM_MSG_NEWPOLICY_LEGACY; + break; + case XFRM_MSG_UPDPOLICY: + event = XFRM_MSG_UPDPOLICY_LEGACY; + break; + case XFRM_MSG_DELPOLICY: + event = XFRM_MSG_DELPOLICY_LEGACY; + break; + } + + nlh = nlmsg_put(skb, c->portid, c->seq, event, headlen, 0); err = -EMSGSIZE; if (nlh == NULL) goto out_free_skb; diff --git a/security/selinux/nlmsgtab.c b/security/selinux/nlmsgtab.c index 2ca9cde939d4..15e8b1381c13 100644 --- a/security/selinux/nlmsgtab.c +++ b/security/selinux/nlmsgtab.c @@ -90,29 +90,42 @@ static struct nlmsg_perm nlmsg_tcpdiag_perms[] = static struct nlmsg_perm nlmsg_xfrm_perms[] = { - { XFRM_MSG_NEWSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_DELSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_GETSA, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_NEWPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_DELPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_GETPOLICY, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_ALLOCSPI, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_ACQUIRE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_EXPIRE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_UPDPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_UPDSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_POLEXPIRE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_FLUSHSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_FLUSHPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_NEWAE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_GETAE, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_REPORT, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_MIGRATE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_NEWSADINFO, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_GETSADINFO, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_NEWSPDINFO, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, - { XFRM_MSG_GETSPDINFO, NETLINK_XFRM_SOCKET__NLMSG_READ }, - { XFRM_MSG_MAPPING, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_NEWSA_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_DELSA_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_GETSA_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_NEWPOLICY_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_DELPOLICY_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_GETPOLICY_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_ALLOCSPI_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_ACQUIRE_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_EXPIRE_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_UPDPOLICY_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_UPDSA_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_POLEXPIRE_LEGACY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_FLUSHSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_FLUSHPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_NEWAE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_GETAE, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_REPORT, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_MIGRATE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_NEWSADINFO, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_GETSADINFO, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_NEWSPDINFO, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_GETSPDINFO, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_MAPPING, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_ALLOCSPI, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_ACQUIRE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_EXPIRE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_POLEXPIRE, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_NEWSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_NEWSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_UPDSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_DELSA, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_GETSA, NETLINK_XFRM_SOCKET__NLMSG_READ }, + { XFRM_MSG_NEWPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_UPDPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_DELPOLICY, NETLINK_XFRM_SOCKET__NLMSG_WRITE }, + { XFRM_MSG_GETPOLICY, NETLINK_XFRM_SOCKET__NLMSG_READ }, }; static struct nlmsg_perm nlmsg_audit_perms[] = @@ -168,7 +181,7 @@ int selinux_nlmsg_lookup(u16 sclass, u16 nlmsg_type, u32 *perm) break; case SECCLASS_NETLINK_XFRM_SOCKET: - BUILD_BUG_ON(XFRM_MSG_MAX != XFRM_MSG_MAPPING); + BUILD_BUG_ON(XFRM_MSG_MAX != XFRM_MSG_GETPOLICY); err = nlmsg_perm(nlmsg_type, perm, nlmsg_xfrm_perms, sizeof(nlmsg_xfrm_perms)); break;