1 /* 2 * Copyright (c) 2024 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 #ifndef NETSYS_CLATD_PACKET_CONVERTER_H 16 #define NETSYS_CLATD_PACKET_CONVERTER_H 17 18 #include <linux/if_tun.h> 19 #include <netinet/icmp6.h> 20 #include <netinet/in.h> 21 #include <netinet/ip.h> 22 #include <netinet/ip6.h> 23 #include <netinet/ip_icmp.h> 24 #include <netinet/tcp.h> 25 #include <netinet/udp.h> 26 #include <string> 27 #include <sys/uio.h> 28 #include <vector> 29 30 #include "clat_constants.h" 31 #include "clat_utils.h" 32 #include "inet_addr.h" 33 34 namespace OHOS { 35 namespace nmd { 36 using namespace OHOS::NetManagerStandard; 37 class ClatdPacketConverter { 38 public: 39 ClatdPacketConverter(const uint8_t *inputPacket, size_t inputPacketSize, ClatdConvertType convertType, 40 const in_addr &v4Addr, const in6_addr &v6Addr, const in6_addr &prefixAddr); 41 42 int32_t ConvertPacket(bool skip_csum); 43 44 void GetConvertedPacket(std::vector<iovec> &iovPackets, int &effectivePos); 45 46 private: 47 int32_t ConvertV4Packet(int pos, const uint8_t *inputPacket, size_t inputPacketSize); 48 int32_t ConvertV4TpPacket(int pos, const iphdr *ipHeader, ip6_hdr *ip6Header, size_t tpLen, uint8_t v6TpProtocol); 49 int32_t ConvertV6Packet(int pos, const uint8_t *inputPacket, size_t inputPacketSize); 50 int32_t ConvertV6TpPacket(int pos, const ip6_hdr *ip6Header, iphdr *ipHeader, size_t tpLen, uint8_t v4TpProtocol); 51 bool IsV4PacketValid(const iphdr *ipHeader, size_t packetSize); 52 bool IsV6PacketValid(const ip6_hdr *ip6Header, size_t packetSize); 53 void WriteIpv6Header(ip6_hdr *ip6Header, uint8_t tpProtocol, const iphdr *ipHeader); 54 void WriteIpv4Header(iphdr *ipHeader, uint8_t tpProtocol, const ip6_hdr *ip6Header); 55 void ConvertV4Address(uint32_t v4Addr, in6_addr &v6Addr); 56 void ConvertV6Address(const in6_addr &v6Addr, uint32_t &v4Addr); 57 size_t WriteFragHeader(ip6_frag *ip6FragHeader, ip6_hdr *ip6Header, const iphdr *ipHeader); 58 void ProcessFragHeader(const ip6_frag *ip6FragHeader, iphdr *ipHeader, uint8_t &v6TpProtocol, 59 uint8_t &v4TpProtocol); 60 uint32_t CalV4PseudoHeaderChecksum(const iphdr *ipHeader, uint16_t tpLen, uint8_t tpProtocol); 61 uint32_t CalV6PseudoHeaderChecksum(const ip6_hdr *ip6Header, uint32_t tpLen, uint8_t tpProtocol); 62 uint16_t GetIovPacketLength(int pos); 63 int32_t ConvertIcmpPacket(int pos, const icmphdr *icmpHeader, uint32_t checksum, size_t tpLen); 64 int32_t ConvertIcmpv6Packet(int pos, const icmp6_hdr *icmp6Header, size_t tpLen); 65 void ConvertIcmpTypeAndCode(const uint8_t &icmpType, const uint8_t &icmpCode, uint8_t &icmp6Type, 66 uint8_t &icmp6Code); 67 void ConvertIcmpV6TypeAndCode(const uint8_t &icmp6Type, const uint8_t &icmp6Code, uint8_t &icmpType, 68 uint8_t &icmpCode); 69 uint16_t CalIovPacketChecksum(uint32_t sum, int pos); 70 int32_t ConvertTcpPacket(int pos, const tcphdr *tcpHeader, uint32_t oldChecksum, uint32_t newChecksum, 71 size_t tpLen); 72 bool IsTcpPacketValid(const tcphdr *packet, size_t packetSize); 73 int32_t ConvertUdpPacket(int pos, const udphdr *udpHeader, uint32_t oldChecksum, uint32_t newChecksum, 74 size_t tpLen); 75 void WritePayload(int pos, const uint8_t *tpHeader, size_t tpLen); 76 void WriteTunHeader(bool skip_csum); 77 78 const uint8_t *inputPacket_; 79 size_t inputPacketSize_; 80 ClatdConvertType convertType_; 81 in_addr localV4Addr_; 82 in6_addr localV6Addr_; 83 in6_addr prefixAddr_; 84 85 std::vector<std::string> iovBufs_; 86 std::vector<size_t> iovBufLens_; 87 int effectivePos_{0}; 88 }; 89 } // namespace nmd 90 } // namespace OHOS 91 #endif