From patchwork Tue Feb 6 20:30:43 2018 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Roman Kagan X-Patchwork-Id: 10204181 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 2EBDB601A1 for ; Tue, 6 Feb 2018 21:32:40 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 19D2028842 for ; Tue, 6 Feb 2018 21:32:40 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 0CCC328AA6; Tue, 6 Feb 2018 21:32:40 +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=-6.8 required=2.0 tests=BAD_ENC_HEADER,BAYES_00, DKIM_SIGNED, RCVD_IN_DNSWL_HI, T_DKIM_INVALID autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 21E6928842 for ; Tue, 6 Feb 2018 21:32:37 +0000 (UTC) Received: from localhost ([::1]:37315 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1ejAqy-00027p-Tz for patchwork-qemu-devel@patchwork.kernel.org; Tue, 06 Feb 2018 16:32:36 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:45100) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1ej9uP-0001Wr-OP for qemu-devel@nongnu.org; Tue, 06 Feb 2018 15:32:12 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1ej9uM-0003Pb-8V for qemu-devel@nongnu.org; Tue, 06 Feb 2018 15:32:05 -0500 Received: from mail-db5eur01on0134.outbound.protection.outlook.com ([104.47.2.134]:31212 helo=EUR01-DB5-obe.outbound.protection.outlook.com) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1ej9uL-0003Oz-Nh for qemu-devel@nongnu.org; Tue, 06 Feb 2018 15:32:02 -0500 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=virtuozzo.com; s=selector1; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version; bh=pE+JKNfdrttryv46Y2wRQBK+iwd6p+v/J467cNxbczU=; b=WvauEEuV4q3o6SkN278HngNkPQ3z2NNi3vicXNexwgf/MzC+rKfDvDfRHNjODm3A04ID9JoKa5UnjKk+q1F84IgVBdMOhPY9zLTyf8M0iF2Z/xTIHgOhp0FssranwFa/WTwfF6955bPqeK8Yib1odcDL52YfICKK/5XOiin7eLI= Authentication-Results: spf=none (sender IP is ) smtp.mailfrom=rkagan@virtuozzo.com; Received: from rkaganb.sw.ru (195.214.232.6) by VI1PR0801MB1983.eurprd08.prod.outlook.com (2603:10a6:800:8a::16) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384_P256) id 15.20.464.11; Tue, 6 Feb 2018 20:31:57 +0000 From: Roman Kagan To: qemu-devel@nongnu.org Date: Tue, 6 Feb 2018 23:30:43 +0300 Message-Id: <20180206203048.11096-30-rkagan@virtuozzo.com> X-Mailer: git-send-email 2.14.3 In-Reply-To: <20180206203048.11096-1-rkagan@virtuozzo.com> References: <20180206203048.11096-1-rkagan@virtuozzo.com> MIME-Version: 1.0 X-Originating-IP: [195.214.232.6] X-ClientProxiedBy: HE1PR0301CA0008.eurprd03.prod.outlook.com (2603:10a6:3:76::18) To VI1PR0801MB1983.eurprd08.prod.outlook.com (2603:10a6:800:8a::16) X-MS-PublicTrafficType: Email X-MS-Office365-Filtering-Correlation-Id: 31fc9a42-731e-4391-3cce-08d56da0abcf X-Microsoft-Antispam: UriScan:; BCL:0; PCL:0; RULEID:(7020095)(4652020)(4534165)(7168020)(4627221)(201703031133081)(201702281549075)(5600026)(4604075)(2017052603307)(7153060)(7193020); SRVR:VI1PR0801MB1983; X-Microsoft-Exchange-Diagnostics: 1; VI1PR0801MB1983; 3:nCOxD0ySiy1g82EGvbA5VHbnX3QPBf/GpibHOgnFGlEdScZ5317zHlPM/X5fQlQT6B3juuIayGozvmsrFNCbeDwlm6Kz4dia+TV0tMFWDyxKmfcVoB+E/zyOLRbN55p+yOsB1hs6M2oFAINJZnRfTbVB+sWDRKLG9WXkEl9EG3aUw2VibNp2dA0327ZcGG2Ri581/NN6LVMYibdE9GCRrEKdQiG+54YJbkim+tA7YqD2emORRCP/MV7DrkNsk0iB; 25:25d7suAVz4o/9Eimf63CcPzKZbyC4mVlwHkpM7vrCboajYDm6qcb0my4YL9QURQwlgiPW2MZTuM7w8rI+h+KHeMJhPQ1YPKbDikaOt9srF1ojJvSjvsXC1RAFTVVYxXTeS+UiyY6Z7yGIMcqX5TtDz+vJrUnU80UFhy86dip9Q3Uiq+k/tZdvrgMiKHDQe2qQKxE9pMNOoUMnUTGr7Naz/xanhl0pjROrEHl7g8wimVaDGgf1lZrccChcMcXK4r617BRi8UIjP1qZgDjs2mes7JWL5ZtHi9xsMIie4+BIxcO+CF/fl9/Z4eXiH5tMjgMBfjSeT0DgVI11uJgTWCd2g==; 31:YnYCJEU5riQpXhj0fLOUbu0TJ8CBkOxrjC3rH/3Z/9cBXanUZIXCMbvR1OF/FSIbDd4WQ4CFQT64++deO8wCK43Ms1vmBOaKJs2ovCMDl6nfGTNvK8BqChKJEbt3fR+ELCW70bSnmRZweGISRPyWSRRG37MomNdwV+R6OK/KpuGAvzG152BH6YrtiKyo0PE9oxGsld+mkZZ18pWjfqRKKAMWZ2QWGBHdY92Dj001/yo= X-MS-TrafficTypeDiagnostic: VI1PR0801MB1983: X-Microsoft-Exchange-Diagnostics: 1; VI1PR0801MB1983; 20:t1RkyPGL3sArf019dogGbBb3fUsYxevh+QZTDwd6HwyMgrKb8Mat55ffuUEOs02sZ5fQ6Cb09lZUYY4ZVO3VjliBP+rLNnsQReNhIG/RVKNO1A2F32Ql/OztJT6W0acOItKuJLfm2PJBKJAsD3XSF5/RxSlJE1D41e7GYJL0kxsoUdeTPJ0oxNkMM2f+3/2VMvg3FG5ayFR2nCYbLWCFmCAw7ARcUsoup4v83I4dZiBrvAjFL+t+76CS3nhw5aiykh/VUhR+DaH/ihVMiFDtvvENuzZIEgzLqJc0giTI9hDBFfPq9DQRiaXz/hJ8WGrgzx1ZgJXYP7zevZZOl2gJOgpUIHMZrZp/OmDdl7kKOLB0PVhiDYJeUbYCV2VV+uynsCi6wJCQ61WiliARNXUq9idjhMys1RHKtfHHB/2OOEg=; 4:iGLgW8hhnUjQIFOBkZqtbm6cXeVdQLZ/pRBs6dRgxHQVc06I7SFzDhEknvkf3f4djdqFxIdty5TNw2j+kpHF+Ym+G/k9QKlJFMyId7aLvXVmGEz2TEmH8KVdPb5//0VxbexYVOvMRTBVjMAbVNzfjhCSdeYZ5d3k1Zf7cnMmmXL9PUsKa1D3iNgZRebh98s8Kdz1fgfHWMrMx73tJAOrDF4BIBpkjczc1cNHjjhMXq75ffhkwR2YdKpyKNUdShdvsIoJ6RPL/OxH8eNFryEHuw== X-Microsoft-Antispam-PRVS: X-Exchange-Antispam-Report-Test: UriScan:; X-Exchange-Antispam-Report-CFA-Test: BCL:0; PCL:0; RULEID:(6040501)(2401047)(5005006)(8121501046)(3002001)(93006095)(93001095)(3231101)(2400082)(944501161)(10201501046)(6041288)(201703131423095)(201702281528075)(20161123555045)(201703061421075)(201703061406153)(20161123558120)(20161123564045)(20161123562045)(20161123560045)(6072148)(201708071742011); SRVR:VI1PR0801MB1983; BCL:0; PCL:0; RULEID:; SRVR:VI1PR0801MB1983; X-Forefront-PRVS: 0575F81B58 X-Forefront-Antispam-Report: SFV:NSPM; SFS:(10019020)(1496009)(396003)(366004)(376002)(39380400002)(39850400004)(346002)(40224003)(189003)(199004)(16586007)(53936002)(305945005)(53946003)(54906003)(7736002)(3846002)(316002)(105586002)(2361001)(106356001)(2351001)(6116002)(1076002)(50226002)(8936002)(81156014)(5660300001)(8676002)(81166006)(7416002)(2950100002)(6666003)(551934003)(6916009)(76176011)(86362001)(68736007)(66066001)(45080400002)(16526019)(47776003)(50466002)(4326008)(97736004)(26005)(6512007)(51416003)(2906002)(52116002)(386003)(6506007)(59450400001)(48376002)(55236004)(36756003)(53416004)(69596002)(6486002)(478600001)(186003)(25786009)(217873001); DIR:OUT; SFP:1102; SCL:1; SRVR:VI1PR0801MB1983; H:rkaganb.sw.ru; FPR:; SPF:None; PTR:InfoNoRecords; MX:1; A:1; LANG:en; Received-SPF: None (protection.outlook.com: virtuozzo.com does not designate permitted sender hosts) X-Microsoft-Exchange-Diagnostics: =?us-ascii?Q?1; VI1PR0801MB1983; 23:byDyth1TYVXvaCwZkueJkOT+Ax7ECyz27bcEwxY?= =?us-ascii?Q?sUgw/S4MaMS9P4j+vrTo5OJsSMqqVd2GuKW+rWBOQ1awN7fCz+wVZKI3/5RI?= =?us-ascii?Q?F2k2KDRDq9sOnjh0VpfVq9BpKRIrHJIc2zQQl1jy82kUvqPr/JIij9VLuD8S?= =?us-ascii?Q?CfjoITaJVvn59syrkjHoPnE1Glbn1qgufEVK219nZOfkQYAM1wFTNaiCKc81?= =?us-ascii?Q?zfImkrMCRhAtfyPzoSIB527cLBMdol8TnPwfUkhJLlYxR/Ra/EMe2XLPnast?= =?us-ascii?Q?M0bL1uvWLnRqMxO6jE8+Zz6AW6IeF1F15Eaxk8kEqjHUaW+cNS1CgUsE3r8j?= =?us-ascii?Q?Gr78RwiDp1urJO7mrMnG4uGnJBEAVahCe5YJDKk6ICmVjsy07/qvX3FncziY?= =?us-ascii?Q?DwRp7oFQSRTChF2+f7QP1tzRUI2uGiIvcpffW0WlB5Ia5ITOMJLhBCtAWoZC?= =?us-ascii?Q?vW7Ju3UD/x1z8ZIJ4ZActKRb9vkZcy/0i5ERhvc+JiJk766TQbKFA2sa8Lj7?= =?us-ascii?Q?VazhPZHHhB8jrPDyccztAKNrvXMRb8HH9lY5ppzo1DO5dLQI9OZ2CPEQUDcx?= =?us-ascii?Q?Kh6kW7UuLV6EAeQ2coJ2K2Wg5Kp3JunlOjtzxmBXuuua++sDW0ga6jh3zj9Z?= =?us-ascii?Q?qfxSvsD+KwwwHQqzUwNuPnNqUkmiK6mCGV/cpIIXdzdehcdSydD/MEF6SO17?= =?us-ascii?Q?gnuymUn6BnPcDK7EYx/hhcbZJ9tQRJcO7PZYe2mI53QzlbuFiYukKd9O9Tjf?= =?us-ascii?Q?zS1G7om5SIcHU+5koj6egFf9G/gdiwkVQBFmWPRxqHyh/KEzEU1Q1FgtvU6j?= =?us-ascii?Q?kq3M+0um2GXn47OScfuUusfDl7sH9tv/SmyL5EBnK4rBrU6/M1Xod7w4P8vn?= =?us-ascii?Q?FANwC0so3ccHmWHuIVouWK6EacQDe8FrsQp1bNV7BNWBQcKWcauLl/WuaFjH?= =?us-ascii?Q?p736ovaX93s6fsZfMNIJvt+lHC6vRbZNWS9miIzyz+Sh4hy6lEbAFWSUin9R?= =?us-ascii?Q?ZlteO09EuCSBp7pjqcnJ/xeRcc5cE5YmiYM/40gFfQFzn5ClJSXPu8mOydRJ?= =?us-ascii?Q?4WdORtNEuBJvQHS//mRdJLWtk7bDBOrqOybwcRkad9g3y8wnsfTS+k+aNLUb?= =?us-ascii?Q?mHeIjmvX+aeqUioajZLNgHqmreraO/HXb26hvIpJZKN0ZbgGO5XKGGLqxPit?= =?us-ascii?Q?KSucxOeKvOUEm9M8I6LoaqasN7OXRFMSlzxcZTwBFUn0T0jCixxIbtdCkzaJ?= =?us-ascii?Q?9j2k0mD3IOrZxh15lMQRPG3edJRo2oljVG7UNzFveaW18DdVIv+u19+8WnmC?= =?us-ascii?Q?+vivtCRZfxSvtAkngixPNSy4cEVf33CQSr3nK++ellZKuPhlXqbal0r++AiG?= =?us-ascii?Q?R4L5czzFzO32ZfFk0/qPufv9prqyYL1osT4D7uj55NErsSxDAE0AjBTOj+IJ?= =?us-ascii?Q?Ye3zya5C5cQ=3D=3D?= X-Microsoft-Exchange-Diagnostics: 1; VI1PR0801MB1983; 6:neyeYaPz/uEYWOlhvCzI3qq1OSvXDwQFPf0iwWtCb6iZknuYdwuJtROiCbVi52b+UQBdoRV3W1BUzEhI4piEL9bgLMWwdcCqRSF1jQg6/dME5QZb74AgKQYfRACmArezelptWij+e0V+/1dc2k3YOkVm3hY40+9hm0UY+jg2k/7sdu4wVz2wVLYo+BPXqc0aXqWEIBOxfgC0FQci0ywIVq9wvXWrFjLkel/4CXboFTPhNEodUdw1FbKR3+q1p+cO1f/CX1JapEhKmT/HpjAxbtFJTpXIrLzdORG5mMJYiHq3CVtALRzRqxtPDaWf+/sEJZQe9SnFvZEEXbHZ3PRHR0erpYX1f9eI2p2eQ6+FR+Y=; 5:Abzfq4ClQbZX+xWEOliNdkL8joth5yoTGJsyWF+C3F3LMm+IY6FwiZE73uD1Uax54SfykMYhveLEWCmT82aZmemDxQgKezn/gCdT6Gf0IQ6WRFz8dqKefWxpT03Dy38t8bmc+VnyiIcbArrOV1WiM3IiAoK8X5jVdQ3uLp7FD30=; 24:MfxRA77n5l2BRwZw/SWEPIUxOfRH3oXFA2fMabcyFLZFPuJljN+B1qtr97d5h7xBd7yEVPO1E1gQMzxRa5pLL1lMsDMijB77X7xtRKfZttY=; 7:sCOt9AX5IPwuTt0n3/N4obfC8eJcej2rL64yNSzIjbNQKCbv03aiP3g+3sdp5mdqGxBsQSbvsgYJhf+rt+u36LfIqKx7TFov3JuUj6zzV9EdRuWVULIsRCTQj2ImpIECL5YpgeMnoGL9Z84jkKF6bqExmzFPwzJQ/sK6Lhc2glxC4AxBwPTiWLQpiUmoWIEYpT4tzrrGAvs3Mbw+BKGHnPIZ8YQkh8yfoS/k2mRhR7vQUD0zvWoY2es6rlLdOP21 SpamDiagnosticOutput: 1:99 SpamDiagnosticMetadata: NSPM X-Microsoft-Exchange-Diagnostics: 1; VI1PR0801MB1983; 20:Qt/68CYRYpmx8o3uGnsRSyJC2XAseeJD4SnadWregCusMMuzSvXCvY6YxILqU+mbLK0pQmudw3+r2L/WMox3z93rg3tqW354sncCz1SEYhvl5QJeff/1noiUTtX50etPP2DclMSleRinrkkBxNXNHtxTFccU/LQBjM1doVbPY74= X-OriginatorOrg: virtuozzo.com X-MS-Exchange-CrossTenant-OriginalArrivalTime: 06 Feb 2018 20:31:57.8098 (UTC) X-MS-Exchange-CrossTenant-Network-Message-Id: 31fc9a42-731e-4391-3cce-08d56da0abcf X-MS-Exchange-CrossTenant-FromEntityHeader: Hosted X-MS-Exchange-CrossTenant-Id: 0bc7f26d-0264-416e-a6fc-8352af79c58f X-MS-Exchange-Transport-CrossTenantHeadersStamped: VI1PR0801MB1983 X-detected-operating-system: by eggs.gnu.org: Windows 7 or 8 [fuzzy] X-Received-From: 104.47.2.134 Subject: [Qemu-devel] [RFC PATCH 29/34] net: add Hyper-V/VMBus network protocol definitions X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Ben Warren , Konrad Rzeszutek Wilk , Krish Sadhukhan , "Marcos E. Matsunaga" , Jan Dakinevich , Vadim Rozenfeld , "Denis V. Lunev" , si-wei liu , Paolo Bonzini , Vitaly Kuznetsov , Cathy Avery Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP Add a header with data structures and constants defining the protocol for communication between the guest and the hypervisor implementing the Hyper-V/VMBus network adapter. Mostly taken from the corresponding definitions in the Linux kernel. TODO: move RNDIS stuff to rndis.h Signed-off-by: Roman Kagan --- hw/net/hvnet-proto.h | 1161 ++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 1161 insertions(+) create mode 100644 hw/net/hvnet-proto.h diff --git a/hw/net/hvnet-proto.h b/hw/net/hvnet-proto.h new file mode 100644 index 0000000000..1582c7e5a2 --- /dev/null +++ b/hw/net/hvnet-proto.h @@ -0,0 +1,1161 @@ +/* + * Hyper-V network device protocol definitions + * + * Copyright (c) 2011, Microsoft Corporation. + * Copyright (c) 2018 Virtuozzo International GmbH. + * + * This work is licensed under the terms of the GNU GPL, version 2 or later. + * See the COPYING file in the top-level directory. + */ + +#ifndef _HVNET_PROTO_H_ +#define _HVNET_PROTO_H_ + +/**** + * c&p from linux drivers/net/hyperv/hyperv_net.h + ****/ + +/* RSS related */ +#define OID_GEN_RECEIVE_SCALE_CAPABILITIES 0x00010203 /* query only */ +#define OID_GEN_RECEIVE_SCALE_PARAMETERS 0x00010204 /* query and set */ + +#define NDIS_OBJECT_TYPE_RSS_CAPABILITIES 0x88 +#define NDIS_OBJECT_TYPE_RSS_PARAMETERS 0x89 +#define NDIS_OBJECT_TYPE_OFFLOAD 0xa7 + +#define NDIS_RECEIVE_SCALE_CAPABILITIES_REVISION_2 2 +#define NDIS_RECEIVE_SCALE_PARAMETERS_REVISION_2 2 + +struct ndis_obj_header { + uint8_t type; + uint8_t rev; + uint16_t size; +} QEMU_PACKED; + +/* ndis_recv_scale_cap/cap_flag */ +#define NDIS_RSS_CAPS_MESSAGE_SIGNALED_INTERRUPTS 0x01000000 +#define NDIS_RSS_CAPS_CLASSIFICATION_AT_ISR 0x02000000 +#define NDIS_RSS_CAPS_CLASSIFICATION_AT_DPC 0x04000000 +#define NDIS_RSS_CAPS_USING_MSI_X 0x08000000 +#define NDIS_RSS_CAPS_RSS_AVAILABLE_ON_PORTS 0x10000000 +#define NDIS_RSS_CAPS_SUPPORTS_MSI_X 0x20000000 +#define NDIS_RSS_CAPS_HASH_TYPE_TCP_IPV4 0x00000100 +#define NDIS_RSS_CAPS_HASH_TYPE_TCP_IPV6 0x00000200 +#define NDIS_RSS_CAPS_HASH_TYPE_TCP_IPV6_EX 0x00000400 + +struct ndis_recv_scale_cap { /* NDIS_RECEIVE_SCALE_CAPABILITIES */ + struct ndis_obj_header hdr; + uint32_t cap_flag; + uint32_t num_int_msg; + uint32_t num_recv_que; + uint16_t num_indirect_tabent; +} QEMU_PACKED; + + +/* ndis_recv_scale_param flags */ +#define NDIS_RSS_PARAM_FLAG_BASE_CPU_UNCHANGED 0x0001 +#define NDIS_RSS_PARAM_FLAG_HASH_INFO_UNCHANGED 0x0002 +#define NDIS_RSS_PARAM_FLAG_ITABLE_UNCHANGED 0x0004 +#define NDIS_RSS_PARAM_FLAG_HASH_KEY_UNCHANGED 0x0008 +#define NDIS_RSS_PARAM_FLAG_DISABLE_RSS 0x0010 + +/* Hash info bits */ +#define NDIS_HASH_FUNC_TOEPLITZ 0x00000001 +#define NDIS_HASH_IPV4 0x00000100 +#define NDIS_HASH_TCP_IPV4 0x00000200 +#define NDIS_HASH_IPV6 0x00000400 +#define NDIS_HASH_IPV6_EX 0x00000800 +#define NDIS_HASH_TCP_IPV6 0x00001000 +#define NDIS_HASH_TCP_IPV6_EX 0x00002000 + +#define NDIS_RSS_INDIRECTION_TABLE_MAX_SIZE_REVISION_2 (128 * 4) +#define NDIS_RSS_HASH_SECRET_KEY_MAX_SIZE_REVISION_2 40 + +#define ITAB_NUM 128 + +struct ndis_recv_scale_param { /* NDIS_RECEIVE_SCALE_PARAMETERS */ + struct ndis_obj_header hdr; + + /* Qualifies the rest of the information */ + uint16_t flag; + + /* The base CPU number to do receive processing. not used */ + uint16_t base_cpu_number; + + /* This describes the hash function and type being enabled */ + uint32_t hashinfo; + + /* The size of indirection table array */ + uint16_t indirect_tabsize; + + /* The offset of the indirection table from the beginning of this + * structure + */ + uint32_t indirect_taboffset; + + /* The size of the hash secret key */ + uint16_t hashkey_size; + + /* The offset of the secret key from the beginning of this structure */ + uint32_t kashkey_offset; + + uint32_t processor_masks_offset; + uint32_t num_processor_masks; + uint32_t processor_masks_entry_size; +}; + +/* Fwd declaration */ +struct ndis_tcp_ip_checksum_info; +struct ndis_pkt_8021q_info; + +/* + * Represent netvsc packet which contains 1 RNDIS and 1 ethernet frame + * within the RNDIS + * + * The size of this structure is less than 48 bytes and we can now + * place this structure in the skb->cb field. + */ +struct hv_netvsc_packet { + /* Bookkeeping stuff */ + uint8_t cp_partial; /* partial copy into send buffer */ + + uint8_t rmsg_size; /* RNDIS header and PPI size */ + uint8_t rmsg_pgcnt; /* page count of RNDIS header and PPI */ + uint8_t page_buf_cnt; + + uint16_t q_idx; + uint16_t total_packets; + + uint32_t total_bytes; + uint32_t send_buf_index; + uint32_t total_data_buflen; +}; + +enum rndis_device_state { + RNDIS_DEV_UNINITIALIZED = 0, + RNDIS_DEV_INITIALIZING, + RNDIS_DEV_INITIALIZED, + RNDIS_DEV_DATAINITIALIZED, +}; + +#define NETVSC_HASH_KEYLEN 40 + +#define NVSP_INVALID_PROTOCOL_VERSION ((uint32_t)0xFFFFFFFF) + +#define NVSP_PROTOCOL_VERSION_1 2 +#define NVSP_PROTOCOL_VERSION_2 0x30002 +#define NVSP_PROTOCOL_VERSION_4 0x40000 +#define NVSP_PROTOCOL_VERSION_5 0x50000 + +enum { + NVSP_MSG_TYPE_NONE = 0, + + /* Init Messages */ + NVSP_MSG_TYPE_INIT = 1, + NVSP_MSG_TYPE_INIT_COMPLETE = 2, + + NVSP_VERSION_MSG_START = 100, + + /* Version 1 Messages */ + NVSP_MSG1_TYPE_SEND_NDIS_VER = NVSP_VERSION_MSG_START, + + NVSP_MSG1_TYPE_SEND_RECV_BUF, + NVSP_MSG1_TYPE_SEND_RECV_BUF_COMPLETE, + NVSP_MSG1_TYPE_REVOKE_RECV_BUF, + + NVSP_MSG1_TYPE_SEND_SEND_BUF, + NVSP_MSG1_TYPE_SEND_SEND_BUF_COMPLETE, + NVSP_MSG1_TYPE_REVOKE_SEND_BUF, + + NVSP_MSG1_TYPE_SEND_RNDIS_PKT, + NVSP_MSG1_TYPE_SEND_RNDIS_PKT_COMPLETE, + + /* Version 2 messages */ + NVSP_MSG2_TYPE_SEND_CHIMNEY_DELEGATED_BUF, + NVSP_MSG2_TYPE_SEND_CHIMNEY_DELEGATED_BUF_COMP, + NVSP_MSG2_TYPE_REVOKE_CHIMNEY_DELEGATED_BUF, + + NVSP_MSG2_TYPE_RESUME_CHIMNEY_RX_INDICATION, + + NVSP_MSG2_TYPE_TERMINATE_CHIMNEY, + NVSP_MSG2_TYPE_TERMINATE_CHIMNEY_COMP, + + NVSP_MSG2_TYPE_INDICATE_CHIMNEY_EVENT, + + NVSP_MSG2_TYPE_SEND_CHIMNEY_PKT, + NVSP_MSG2_TYPE_SEND_CHIMNEY_PKT_COMP, + + NVSP_MSG2_TYPE_POST_CHIMNEY_RECV_REQ, + NVSP_MSG2_TYPE_POST_CHIMNEY_RECV_REQ_COMP, + + NVSP_MSG2_TYPE_ALLOC_RXBUF, + NVSP_MSG2_TYPE_ALLOC_RXBUF_COMP, + + NVSP_MSG2_TYPE_FREE_RXBUF, + + NVSP_MSG2_TYPE_SEND_VMQ_RNDIS_PKT, + NVSP_MSG2_TYPE_SEND_VMQ_RNDIS_PKT_COMP, + + NVSP_MSG2_TYPE_SEND_NDIS_CONFIG, + + NVSP_MSG2_TYPE_ALLOC_CHIMNEY_HANDLE, + NVSP_MSG2_TYPE_ALLOC_CHIMNEY_HANDLE_COMP, + + NVSP_MSG2_MAX = NVSP_MSG2_TYPE_ALLOC_CHIMNEY_HANDLE_COMP, + + /* Version 4 messages */ + NVSP_MSG4_TYPE_SEND_VF_ASSOCIATION, + NVSP_MSG4_TYPE_SWITCH_DATA_PATH, + NVSP_MSG4_TYPE_UPLINK_CONNECT_STATE_DEPRECATED, + + NVSP_MSG4_MAX = NVSP_MSG4_TYPE_UPLINK_CONNECT_STATE_DEPRECATED, + + /* Version 5 messages */ + NVSP_MSG5_TYPE_OID_QUERY_EX, + NVSP_MSG5_TYPE_OID_QUERY_EX_COMP, + NVSP_MSG5_TYPE_SUBCHANNEL, + NVSP_MSG5_TYPE_SEND_INDIRECTION_TABLE, + + NVSP_MSG5_MAX = NVSP_MSG5_TYPE_SEND_INDIRECTION_TABLE, +}; + +enum { + NVSP_STAT_NONE = 0, + NVSP_STAT_SUCCESS, + NVSP_STAT_FAIL, + NVSP_STAT_PROTOCOL_TOO_NEW, + NVSP_STAT_PROTOCOL_TOO_OLD, + NVSP_STAT_INVALID_RNDIS_PKT, + NVSP_STAT_BUSY, + NVSP_STAT_PROTOCOL_UNSUPPORTED, + NVSP_STAT_MAX, +}; + +struct nvsp_msg_header { + uint32_t msg_type; +}; + +/* Init Messages */ + +/* + * This message is used by the VSC to initialize the channel after the channels + * has been opened. This message should never include anything other then + * versioning (i.e. this message will be the same for ever). + */ +struct nvsp_msg_init { + uint32_t min_protocol_ver; + uint32_t max_protocol_ver; +} QEMU_PACKED; + +/* + * This message is used by the VSP to complete the initialization of the + * channel. This message should never include anything other then versioning + * (i.e. this message will be the same for ever). + */ +struct nvsp_msg_init_complete { + uint32_t negotiated_protocol_ver; + uint32_t max_mdl_chain_len; + uint32_t status; +}; + +/* Version 1 Messages */ + +/* + * This message is used by the VSC to send the NDIS version to the VSP. The VSP + * can use this information when handling OIDs sent by the VSC. + */ +struct nvsp1_msg_ndis_ver { + uint32_t ndis_major_ver; + uint32_t ndis_minor_ver; +} QEMU_PACKED; + +/* + * This message is used by the VSC to send a receive buffer to the VSP. The VSP + * can then use the receive buffer to send data to the VSC. + */ +struct nvsp1_msg_rcvbuf { + uint32_t gpadl_handle; + uint16_t id; +} QEMU_PACKED; + +struct nvsp1_rcvbuf_section { + uint32_t offset; + uint32_t sub_alloc_size; + uint32_t num_sub_allocs; + uint32_t end_offset; +} QEMU_PACKED; + +/* + * This message is used by the VSP to acknowledge a receive buffer send by the + * VSC. This message must be sent by the VSP before the VSP uses the receive + * buffer. + */ +struct nvsp1_msg_rcvbuf_complete { + uint32_t status; + uint32_t num_sections; + + /* + * The receive buffer is split into two parts, a large suballocation + * section and a small suballocation section. These sections are then + * suballocated by a certain size. + */ + + /* + * For example, the following break up of the receive buffer has 6 + * large suballocations and 10 small suballocations. + */ + + /* + * | Large Section | | Small Section | + * ------------------------------------------------------------ + * | | | | | | | | | | | | | | | | | | + * | | + * LargeOffset SmallOffset + */ + + struct nvsp1_rcvbuf_section sections[1]; +} QEMU_PACKED; + +/* + * This message is sent by the VSC to revoke the receive buffer. After the VSP + * completes this transaction, the vsp should never use the receive buffer + * again. + */ +struct nvsp1_msg_revoke_rcvbuf { + uint16_t id; +}; + +/* + * This message is used by the VSC to send a send buffer to the VSP. The VSC + * can then use the send buffer to send data to the VSP. + */ +struct nvsp1_msg_sndbuf { + uint32_t gpadl_handle; + uint16_t id; +} QEMU_PACKED; + +/* + * This message is used by the VSP to acknowledge a send buffer sent by the + * VSC. This message must be sent by the VSP before the VSP uses the sent + * buffer. + */ +struct nvsp1_msg_sndbuf_complete { + uint32_t status; + + /* + * The VSC gets to choose the size of the send buffer and the VSP gets + * to choose the sections size of the buffer. This was done to enable + * dynamic reconfigurations when the cost of GPA-direct buffers + * decreases. + */ + uint32_t section_size; +} QEMU_PACKED; + +/* + * This message is sent by the VSC to revoke the send buffer. After the VSP + * completes this transaction, the vsp should never use the send buffer again. + */ +struct nvsp1_msg_revoke_sndbuf { + uint16_t id; +}; + +/* + * This message is used by both the VSP and the VSC to send a RNDIS message to + * the opposite channel endpoint. + */ +struct nvsp1_msg_rndis_pkt { + /* + * This field is specified by RNDIS. They assume there's two different + * channels of communication. However, the Network VSP only has one. + * Therefore, the channel travels with the RNDIS packet. + */ + uint32_t channel_type; + + /* + * This field is used to send part or all of the data through a send + * buffer. This values specifies an index into the send buffer. If the + * index is 0xFFFFFFFF, then the send buffer is not being used and all + * of the data was sent through other VMBus mechanisms. + */ + uint32_t send_buf_section_index; + uint32_t send_buf_section_size; +} QEMU_PACKED; + +/* + * This message is used by both the VSP and the VSC to complete a RNDIS message + * to the opposite channel endpoint. At this point, the initiator of this + * message cannot use any resources associated with the original RNDIS packet. + */ +struct nvsp1_msg_rndis_pkt_complete { + uint32_t status; +}; + +/* + * Network VSP protocol version 2 messages: + */ +struct nvsp2_vsc_capability { + union { + uint64_t data; + struct { + uint64_t vmq:1; + uint64_t chimney:1; + uint64_t sriov:1; + uint64_t ieee8021q:1; + uint64_t correlation_id:1; + uint64_t teaming:1; + }; + }; +} QEMU_PACKED; + +struct nvsp2_send_ndis_config { + uint32_t mtu; + uint32_t reserved; + struct nvsp2_vsc_capability capability; +} QEMU_PACKED; + +/* Allocate receive buffer */ +struct nvsp2_alloc_rxbuf { + /* Allocation ID to match the allocation request and response */ + uint32_t alloc_id; + + /* Length of the VM shared memory receive buffer that needs to + * be allocated + */ + uint32_t len; +} QEMU_PACKED; + +/* Allocate receive buffer complete */ +struct nvsp2_alloc_rxbuf_comp { + /* The NDIS_STATUS code for buffer allocation */ + uint32_t status; + + uint32_t alloc_id; + + /* GPADL handle for the allocated receive buffer */ + uint32_t gpadl_handle; + + /* Receive buffer ID */ + uint64_t recv_buf_id; +} QEMU_PACKED; + +struct nvsp2_free_rxbuf { + uint64_t recv_buf_id; +} QEMU_PACKED; + +struct nvsp4_send_vf_association { + /* 1: allocated, serial number is valid. 0: not allocated */ + uint32_t allocated; + + /* Serial number of the VF to team with */ + uint32_t serial; +} QEMU_PACKED; + +enum nvsp_vm_datapath { + NVSP_DATAPATH_SYNTHETIC = 0, + NVSP_DATAPATH_VF, + NVSP_DATAPATH_MAX +}; + +struct nvsp4_sw_datapath { + uint32_t active_datapath; /* active data path in VM */ +} QEMU_PACKED; + +enum nvsp_subchannel_operation { + NVSP_SUBCHANNEL_NONE = 0, + NVSP_SUBCHANNEL_ALLOCATE, + NVSP_SUBCHANNEL_MAX +}; + +struct nvsp5_subchannel_request { + uint32_t op; + uint32_t num_subchannels; +} QEMU_PACKED; + +struct nvsp5_subchannel_complete { + uint32_t status; + uint32_t num_subchannels; /* Actual number of subchannels allocated */ +} QEMU_PACKED; + +struct nvsp5_send_indirect_table { + /* The number of entries in the send indirection table */ + uint32_t count; + + /* The offset of the send indirection table from top of this struct. + * The send indirection table tells which channel to put the send + * traffic on. Each entry is a channel number. + */ + uint32_t offset; +} QEMU_PACKED; + +union nvsp_all_messages { + struct nvsp_msg_init init; + struct nvsp_msg_init_complete init_complete; + + struct nvsp1_msg_ndis_ver send_ndis_ver; + struct nvsp1_msg_rcvbuf send_recv_buf; + struct nvsp1_msg_rcvbuf_complete send_recv_buf_complete; + struct nvsp1_msg_revoke_rcvbuf revoke_recv_buf; + struct nvsp1_msg_sndbuf send_send_buf; + struct nvsp1_msg_sndbuf_complete send_send_buf_complete; + struct nvsp1_msg_revoke_sndbuf revoke_send_buf; + struct nvsp1_msg_rndis_pkt send_rndis_pkt; + struct nvsp1_msg_rndis_pkt_complete send_rndis_pkt_complete; + + struct nvsp2_send_ndis_config send_ndis_config; + struct nvsp2_alloc_rxbuf alloc_rxbuf; + struct nvsp2_alloc_rxbuf_comp alloc_rxbuf_comp; + struct nvsp2_free_rxbuf free_rxbuf; + + struct nvsp4_send_vf_association vf_assoc; + struct nvsp4_sw_datapath active_dp; + + struct nvsp5_subchannel_request subchn_req; + struct nvsp5_subchannel_complete subchn_comp; + struct nvsp5_send_indirect_table send_table; +} QEMU_PACKED; + +/* ALL Messages */ +struct nvsp_msg { + struct nvsp_msg_header hdr; + union nvsp_all_messages msg; +} QEMU_PACKED; + + +#define NETVSC_MTU 65535 +#define NETVSC_MTU_MIN ETH_MIN_MTU + +#define NETVSC_RECEIVE_BUFFER_SIZE (1024*1024*16) /* 16MB */ +#define NETVSC_RECEIVE_BUFFER_SIZE_LEGACY (1024*1024*15) /* 15MB */ +#define NETVSC_SEND_BUFFER_SIZE (1024 * 1024 * 15) /* 15MB */ +#define NETVSC_INVALID_INDEX -1 + + +#define NETVSC_RECEIVE_BUFFER_ID 0xcafe +#define NETVSC_SEND_BUFFER_ID 0 + +#define NETVSC_PACKET_SIZE 4096 + +#define VRSS_SEND_TAB_SIZE 16 /* must be power of 2 */ +#define VRSS_CHANNEL_MAX 64 +#define VRSS_CHANNEL_DEFAULT 8 + +#define RNDIS_MAX_PKT_DEFAULT 8 +#define RNDIS_PKT_ALIGN_DEFAULT 8 + +/* Netvsc Receive Slots Max */ +#define NETVSC_RECVSLOT_MAX (NETVSC_RECEIVE_BUFFER_SIZE / ETH_DATA_LEN + 1) + +/* NdisInitialize message */ +struct rndis_initialize_request { + uint32_t req_id; + uint32_t major_ver; + uint32_t minor_ver; + uint32_t max_xfer_size; +}; + +/* Response to NdisInitialize */ +struct rndis_initialize_complete { + uint32_t req_id; + uint32_t status; + uint32_t major_ver; + uint32_t minor_ver; + uint32_t dev_flags; + uint32_t medium; + uint32_t max_pkt_per_msg; + uint32_t max_xfer_size; + uint32_t pkt_alignment_factor; + uint32_t af_list_offset; + uint32_t af_list_size; +}; + +/* Call manager devices only: Information about an address family */ +/* supported by the device is appended to the response to NdisInitialize. */ +struct rndis_co_address_family { + uint32_t address_family; + uint32_t major_ver; + uint32_t minor_ver; +}; + +/* NdisHalt message */ +struct rndis_halt_request { + uint32_t req_id; +}; + +/* NdisQueryRequest message */ +struct rndis_query_request { + uint32_t req_id; + uint32_t oid; + uint32_t info_buflen; + uint32_t info_buf_offset; + uint32_t dev_vc_handle; +}; + +/* Response to NdisQueryRequest */ +struct rndis_query_complete { + uint32_t req_id; + uint32_t status; + uint32_t info_buflen; + uint32_t info_buf_offset; +}; + +/* NdisSetRequest message */ +struct rndis_set_request { + uint32_t req_id; + uint32_t oid; + uint32_t info_buflen; + uint32_t info_buf_offset; + uint32_t dev_vc_handle; +}; + +/* Response to NdisSetRequest */ +struct rndis_set_complete { + uint32_t req_id; + uint32_t status; +}; + +/* NdisReset message */ +struct rndis_reset_request { + uint32_t reserved; +}; + +/* Response to NdisReset */ +struct rndis_reset_complete { + uint32_t status; + uint32_t addressing_reset; +}; + +/* NdisMIndicateStatus message */ +struct rndis_indicate_status { + uint32_t status; + uint32_t status_buflen; + uint32_t status_buf_offset; +}; + +/* Diagnostic information passed as the status buffer in */ +/* struct rndis_indicate_status messages signifying error conditions. */ +struct rndis_diagnostic_info { + uint32_t diag_status; + uint32_t error_offset; +}; + +/* NdisKeepAlive message */ +struct rndis_keepalive_request { + uint32_t req_id; +}; + +/* Response to NdisKeepAlive */ +struct rndis_keepalive_complete { + uint32_t req_id; + uint32_t status; +}; + +/* + * Data message. All Offset fields contain byte offsets from the beginning of + * struct rndis_packet. All Length fields are in bytes. VcHandle is set + * to 0 for connectionless data, otherwise it contains the VC handle. + */ +struct rndis_packet { + uint32_t data_offset; + uint32_t data_len; + uint32_t oob_data_offset; + uint32_t oob_data_len; + uint32_t num_oob_data_elements; + uint32_t per_pkt_info_offset; + uint32_t per_pkt_info_len; + uint32_t vc_handle; + uint32_t reserved; +}; + +/* Optional Out of Band data associated with a Data message. */ +struct rndis_oobd { + uint32_t size; + uint32_t type; + uint32_t class_info_offset; +}; + +/* Packet extension field contents associated with a Data message. */ +struct rndis_per_packet_info { + uint32_t size; + uint32_t type; + uint32_t ppi_offset; +}; + +enum ndis_per_pkt_info_type { + TCPIP_CHKSUM_PKTINFO, + IPSEC_PKTINFO, + TCP_LARGESEND_PKTINFO, + CLASSIFICATION_HANDLE_PKTINFO, + NDIS_RESERVED, + SG_LIST_PKTINFO, + IEEE_8021Q_INFO, + ORIGINAL_PKTINFO, + PACKET_CANCEL_ID, + NBL_HASH_VALUE = PACKET_CANCEL_ID, + ORIGINAL_NET_BUFLIST, + CACHED_NET_BUFLIST, + SHORT_PKT_PADINFO, + MAX_PER_PKT_INFO +}; + +struct ndis_pkt_8021q_info { + union { + struct { + uint32_t pri:3; /* User Priority */ + uint32_t cfi:1; /* Canonical Format ID */ + uint32_t vlanid:12; /* VLAN ID */ + uint32_t reserved:16; + }; + uint32_t value; + }; +}; + +struct ndis_object_header { + uint8_t type; + uint8_t revision; + uint16_t size; +}; + +#define NDIS_OBJECT_TYPE_DEFAULT 0x80 +#define NDIS_OFFLOAD_PARAMETERS_REVISION_3 3 +#define NDIS_OFFLOAD_PARAMETERS_REVISION_2 2 +#define NDIS_OFFLOAD_PARAMETERS_REVISION_1 1 + +#define NDIS_OFFLOAD_PARAMETERS_NO_CHANGE 0 +#define NDIS_OFFLOAD_PARAMETERS_LSOV2_DISABLED 1 +#define NDIS_OFFLOAD_PARAMETERS_LSOV2_ENABLED 2 +#define NDIS_OFFLOAD_PARAMETERS_LSOV1_ENABLED 2 +#define NDIS_OFFLOAD_PARAMETERS_RSC_DISABLED 1 +#define NDIS_OFFLOAD_PARAMETERS_RSC_ENABLED 2 +#define NDIS_OFFLOAD_PARAMETERS_TX_RX_DISABLED 1 +#define NDIS_OFFLOAD_PARAMETERS_TX_ENABLED_RX_DISABLED 2 +#define NDIS_OFFLOAD_PARAMETERS_RX_ENABLED_TX_DISABLED 3 +#define NDIS_OFFLOAD_PARAMETERS_TX_RX_ENABLED 4 + +#define NDIS_TCP_LARGE_SEND_OFFLOAD_V2_TYPE 1 +#define NDIS_TCP_LARGE_SEND_OFFLOAD_IPV4 0 +#define NDIS_TCP_LARGE_SEND_OFFLOAD_IPV6 1 + +#define VERSION_4_OFFLOAD_SIZE 22 +/* + * New offload OIDs for NDIS 6 + */ +#define OID_TCP_OFFLOAD_CURRENT_CONFIG 0xFC01020B /* query only */ +#define OID_TCP_OFFLOAD_PARAMETERS 0xFC01020C /* set only */ +#define OID_TCP_OFFLOAD_HARDWARE_CAPABILITIES 0xFC01020D/* query only */ +#define OID_TCP_CONNECTION_OFFLOAD_CURRENT_CONFIG 0xFC01020E /* query only */ +#define OID_TCP_CONNECTION_OFFLOAD_HARDWARE_CAPABILITIES 0xFC01020F /* query */ +#define OID_OFFLOAD_ENCAPSULATION 0x0101010A /* set/query */ + +/* + * OID_TCP_OFFLOAD_HARDWARE_CAPABILITIES + * ndis_type: NDIS_OBJTYPE_OFFLOAD + */ + +#define NDIS_OFFLOAD_ENCAP_NONE 0x0000 +#define NDIS_OFFLOAD_ENCAP_NULL 0x0001 +#define NDIS_OFFLOAD_ENCAP_8023 0x0002 +#define NDIS_OFFLOAD_ENCAP_8023PQ 0x0004 +#define NDIS_OFFLOAD_ENCAP_8023PQ_OOB 0x0008 +#define NDIS_OFFLOAD_ENCAP_RFC1483 0x0010 + +struct ndis_csum_offload { + uint32_t ip4_txenc; + uint32_t ip4_txcsum; +#define NDIS_TXCSUM_CAP_IP4OPT 0x001 +#define NDIS_TXCSUM_CAP_TCP4OPT 0x004 +#define NDIS_TXCSUM_CAP_TCP4 0x010 +#define NDIS_TXCSUM_CAP_UDP4 0x040 +#define NDIS_TXCSUM_CAP_IP4 0x100 + +#define NDIS_TXCSUM_ALL_TCP4 (NDIS_TXCSUM_CAP_TCP4 | NDIS_TXCSUM_CAP_TCP4OPT) + + uint32_t ip4_rxenc; + uint32_t ip4_rxcsum; +#define NDIS_RXCSUM_CAP_IP4OPT 0x001 +#define NDIS_RXCSUM_CAP_TCP4OPT 0x004 +#define NDIS_RXCSUM_CAP_TCP4 0x010 +#define NDIS_RXCSUM_CAP_UDP4 0x040 +#define NDIS_RXCSUM_CAP_IP4 0x100 + uint32_t ip6_txenc; + uint32_t ip6_txcsum; +#define NDIS_TXCSUM_CAP_IP6EXT 0x001 +#define NDIS_TXCSUM_CAP_TCP6OPT 0x004 +#define NDIS_TXCSUM_CAP_TCP6 0x010 +#define NDIS_TXCSUM_CAP_UDP6 0x040 + uint32_t ip6_rxenc; + uint32_t ip6_rxcsum; +#define NDIS_RXCSUM_CAP_IP6EXT 0x001 +#define NDIS_RXCSUM_CAP_TCP6OPT 0x004 +#define NDIS_RXCSUM_CAP_TCP6 0x010 +#define NDIS_RXCSUM_CAP_UDP6 0x040 + +#define NDIS_TXCSUM_ALL_TCP6 (NDIS_TXCSUM_CAP_TCP6 | \ + NDIS_TXCSUM_CAP_TCP6OPT | \ + NDIS_TXCSUM_CAP_IP6EXT) +}; + +struct ndis_lsov1_offload { + uint32_t encap; + uint32_t maxsize; + uint32_t minsegs; + uint32_t opts; +}; + +struct ndis_ipsecv1_offload { + uint32_t encap; + uint32_t ah_esp; + uint32_t xport_tun; + uint32_t ip4_opts; + uint32_t flags; + uint32_t ip4_ah; + uint32_t ip4_esp; +}; + +struct ndis_lsov2_offload { + uint32_t ip4_encap; + uint32_t ip4_maxsz; + uint32_t ip4_minsg; + uint32_t ip6_encap; + uint32_t ip6_maxsz; + uint32_t ip6_minsg; + uint32_t ip6_opts; +#define NDIS_LSOV2_CAP_IP6EXT 0x001 +#define NDIS_LSOV2_CAP_TCP6OPT 0x004 + +#define NDIS_LSOV2_CAP_IP6 (NDIS_LSOV2_CAP_IP6EXT | \ + NDIS_LSOV2_CAP_TCP6OPT) +}; + +struct ndis_ipsecv2_offload { + uint32_t encap; + uint16_t ip6; + uint16_t ip4opt; + uint16_t ip6ext; + uint16_t ah; + uint16_t esp; + uint16_t ah_esp; + uint16_t xport; + uint16_t tun; + uint16_t xport_tun; + uint16_t lso; + uint16_t extseq; + uint32_t udp_esp; + uint32_t auth; + uint32_t crypto; + uint32_t sa_caps; +}; + +struct ndis_rsc_offload { + uint16_t ip4; + uint16_t ip6; +}; + +struct ndis_encap_offload { + uint32_t flags; + uint32_t maxhdr; +}; + +struct ndis_offload { + struct ndis_object_header header; + struct ndis_csum_offload csum; + struct ndis_lsov1_offload lsov1; + struct ndis_ipsecv1_offload ipsecv1; + struct ndis_lsov2_offload lsov2; + uint32_t flags; + /* NDIS >= 6.1 */ + struct ndis_ipsecv2_offload ipsecv2; + /* NDIS >= 6.30 */ + struct ndis_rsc_offload rsc; + struct ndis_encap_offload encap_gre; +}; + +#define NDIS_OFFLOAD_SIZE sizeof(struct ndis_offload) +#define NDIS_OFFLOAD_SIZE_6_0 offsetof(struct ndis_offload, ipsecv2) +#define NDIS_OFFLOAD_SIZE_6_1 offsetof(struct ndis_offload, rsc) + +struct ndis_offload_params { + struct ndis_object_header header; + uint8_t ip_v4_csum; + uint8_t tcp_ip_v4_csum; + uint8_t udp_ip_v4_csum; + uint8_t tcp_ip_v6_csum; + uint8_t udp_ip_v6_csum; + uint8_t lso_v1; + uint8_t ip_sec_v1; + uint8_t lso_v2_ipv4; + uint8_t lso_v2_ipv6; + uint8_t tcp_connection_ip_v4; + uint8_t tcp_connection_ip_v6; + uint32_t flags; + uint8_t ip_sec_v2; + uint8_t ip_sec_v2_ip_v4; + struct { + uint8_t rsc_ip_v4; + uint8_t rsc_ip_v6; + }; + struct { + uint8_t encapsulated_packet_task_offload; + uint8_t encapsulation_types; + }; +}; + +struct ndis_tcp_ip_checksum_info { + union { + struct { + uint32_t is_ipv4:1; + uint32_t is_ipv6:1; + uint32_t tcp_checksum:1; + uint32_t udp_checksum:1; + uint32_t ip_header_checksum:1; + uint32_t reserved:11; + uint32_t tcp_header_offset:10; + } transmit; + struct { + uint32_t tcp_checksum_failed:1; + uint32_t udp_checksum_failed:1; + uint32_t ip_checksum_failed:1; + uint32_t tcp_checksum_succeeded:1; + uint32_t udp_checksum_succeeded:1; + uint32_t ip_checksum_succeeded:1; + uint32_t loopback:1; + uint32_t tcp_checksum_value_invalid:1; + uint32_t ip_checksum_value_invalid:1; + } receive; + uint32_t value; + }; +}; + +struct ndis_tcp_lso_info { + union { + struct { + uint32_t unused:30; + uint32_t type:1; + uint32_t reserved2:1; + } transmit; + struct { + uint32_t mss:20; + uint32_t tcp_header_offset:10; + uint32_t type:1; + uint32_t reserved2:1; + } lso_v1_transmit; + struct { + uint32_t tcp_payload:30; + uint32_t type:1; + uint32_t reserved2:1; + } lso_v1_transmit_complete; + struct { + uint32_t mss:20; + uint32_t tcp_header_offset:10; + uint32_t type:1; + uint32_t ip_version:1; + } lso_v2_transmit; + struct { + uint32_t reserved:30; + uint32_t type:1; + uint32_t reserved2:1; + } lso_v2_transmit_complete; + uint32_t value; + }; +}; + +#define NDIS_VLAN_PPI_SIZE (sizeof(struct rndis_per_packet_info) + \ + sizeof(struct ndis_pkt_8021q_info)) + +#define NDIS_CSUM_PPI_SIZE (sizeof(struct rndis_per_packet_info) + \ + sizeof(struct ndis_tcp_ip_checksum_info)) + +#define NDIS_LSO_PPI_SIZE (sizeof(struct rndis_per_packet_info) + \ + sizeof(struct ndis_tcp_lso_info)) + +#define NDIS_HASH_PPI_SIZE (sizeof(struct rndis_per_packet_info) + \ + sizeof(uint32_t)) + +/* Total size of all PPI data */ +#define NDIS_ALL_PPI_SIZE (NDIS_VLAN_PPI_SIZE + NDIS_CSUM_PPI_SIZE + \ + NDIS_LSO_PPI_SIZE + NDIS_HASH_PPI_SIZE) + +/* Format of Information buffer passed in a SetRequest for the OID */ +/* OID_GEN_RNDIS_CONFIG_PARAMETER. */ +struct rndis_config_parameter_info { + uint32_t parameter_name_offset; + uint32_t parameter_name_length; + uint32_t parameter_type; + uint32_t parameter_value_offset; + uint32_t parameter_value_length; +}; + +/* Values for ParameterType in struct rndis_config_parameter_info */ +#define RNDIS_CONFIG_PARAM_TYPE_INTEGER 0 +#define RNDIS_CONFIG_PARAM_TYPE_STRING 2 + +/* CONDIS Miniport messages for connection oriented devices */ +/* that do not implement a call manager. */ + +/* CoNdisMiniportCreateVc message */ +struct rcondis_mp_create_vc { + uint32_t req_id; + uint32_t ndis_vc_handle; +}; + +/* Response to CoNdisMiniportCreateVc */ +struct rcondis_mp_create_vc_complete { + uint32_t req_id; + uint32_t dev_vc_handle; + uint32_t status; +}; + +/* CoNdisMiniportDeleteVc message */ +struct rcondis_mp_delete_vc { + uint32_t req_id; + uint32_t dev_vc_handle; +}; + +/* Response to CoNdisMiniportDeleteVc */ +struct rcondis_mp_delete_vc_complete { + uint32_t req_id; + uint32_t status; +}; + +/* CoNdisMiniportQueryRequest message */ +struct rcondis_mp_query_request { + uint32_t req_id; + uint32_t request_type; + uint32_t oid; + uint32_t dev_vc_handle; + uint32_t info_buflen; + uint32_t info_buf_offset; +}; + +/* CoNdisMiniportSetRequest message */ +struct rcondis_mp_set_request { + uint32_t req_id; + uint32_t request_type; + uint32_t oid; + uint32_t dev_vc_handle; + uint32_t info_buflen; + uint32_t info_buf_offset; +}; + +/* CoNdisIndicateStatus message */ +struct rcondis_indicate_status { + uint32_t ndis_vc_handle; + uint32_t status; + uint32_t status_buflen; + uint32_t status_buf_offset; +}; + +/* CONDIS Call/VC parameters */ +struct rcondis_specific_parameters { + uint32_t parameter_type; + uint32_t parameter_length; + uint32_t parameter_lffset; +}; + +struct rcondis_media_parameters { + uint32_t flags; + uint32_t reserved1; + uint32_t reserved2; + struct rcondis_specific_parameters media_specific; +}; + +struct rndis_flowspec { + uint32_t token_rate; + uint32_t token_bucket_size; + uint32_t peak_bandwidth; + uint32_t latency; + uint32_t delay_variation; + uint32_t service_type; + uint32_t max_sdu_size; + uint32_t minimum_policed_size; +}; + +struct rcondis_call_manager_parameters { + struct rndis_flowspec transmit; + struct rndis_flowspec receive; + struct rcondis_specific_parameters call_mgr_specific; +}; + +/* CoNdisMiniportActivateVc message */ +struct rcondis_mp_activate_vc_request { + uint32_t req_id; + uint32_t flags; + uint32_t dev_vc_handle; + uint32_t media_params_offset; + uint32_t media_params_length; + uint32_t call_mgr_params_offset; + uint32_t call_mgr_params_length; +}; + +/* Response to CoNdisMiniportActivateVc */ +struct rcondis_mp_activate_vc_complete { + uint32_t req_id; + uint32_t status; +}; + +/* CoNdisMiniportDeactivateVc message */ +struct rcondis_mp_deactivate_vc_request { + uint32_t req_id; + uint32_t flags; + uint32_t dev_vc_handle; +}; + +/* Response to CoNdisMiniportDeactivateVc */ +struct rcondis_mp_deactivate_vc_complete { + uint32_t req_id; + uint32_t status; +}; + + +/* union with all of the RNDIS messages */ +union rndis_message_container { + struct rndis_packet pkt; + struct rndis_initialize_request init_req; + struct rndis_halt_request halt_req; + struct rndis_query_request query_req; + struct rndis_set_request set_req; + struct rndis_reset_request reset_req; + struct rndis_keepalive_request keep_alive_req; + struct rndis_indicate_status indicate_status; + struct rndis_initialize_complete init_complete; + struct rndis_query_complete query_complete; + struct rndis_set_complete set_complete; + struct rndis_reset_complete reset_complete; + struct rndis_keepalive_complete keep_alive_complete; + struct rcondis_mp_create_vc co_miniport_create_vc; + struct rcondis_mp_delete_vc co_miniport_delete_vc; + struct rcondis_indicate_status co_indicate_status; + struct rcondis_mp_activate_vc_request co_miniport_activate_vc; + struct rcondis_mp_deactivate_vc_request co_miniport_deactivate_vc; + struct rcondis_mp_create_vc_complete co_miniport_create_vc_complete; + struct rcondis_mp_delete_vc_complete co_miniport_delete_vc_complete; + struct rcondis_mp_activate_vc_complete co_miniport_activate_vc_complete; + struct rcondis_mp_deactivate_vc_complete + co_miniport_deactivate_vc_complete; +}; + +/* Remote NDIS message format */ +struct rndis_msg_hdr { + uint32_t msg_type; + uint32_t msg_len; +}; + +#define NDIS_PACKET_TYPE_DIRECTED 0x00000001 +#define NDIS_PACKET_TYPE_MULTICAST 0x00000002 +#define NDIS_PACKET_TYPE_ALL_MULTICAST 0x00000004 +#define NDIS_PACKET_TYPE_BROADCAST 0x00000008 +#define NDIS_PACKET_TYPE_SOURCE_ROUTING 0x00000010 +#define NDIS_PACKET_TYPE_PROMISCUOUS 0x00000020 +#define NDIS_PACKET_TYPE_SMT 0x00000040 +#define NDIS_PACKET_TYPE_ALL_LOCAL 0x00000080 +#define NDIS_PACKET_TYPE_GROUP 0x00000100 +#define NDIS_PACKET_TYPE_ALL_FUNCTIONAL 0x00000200 +#define NDIS_PACKET_TYPE_FUNCTIONAL 0x00000400 +#define NDIS_PACKET_TYPE_MAC_FRAME 0x00000800 + +#define TRANSPORT_INFO_NOT_IP 0 +#define TRANSPORT_INFO_IPV4_TCP 0x01 +#define TRANSPORT_INFO_IPV4_UDP 0x02 +#define TRANSPORT_INFO_IPV6_TCP 0x10 +#define TRANSPORT_INFO_IPV6_UDP 0x20 + +#endif