Merge "IPACM: fix ipv6 rules issue for usb/wlan client"
diff --git a/ipacm/inc/IPACM_Filtering.h b/ipacm/inc/IPACM_Filtering.h
index 48a3d66..7554ba9 100644
--- a/ipacm/inc/IPACM_Filtering.h
+++ b/ipacm/inc/IPACM_Filtering.h
@@ -69,7 +69,6 @@
 private:
 	static const char *DEVICE_NAME;
 	int fd; /* File descriptor of the IPA device node /dev/ipa */
-	int fd_wwan_ioctl;
 };
 
 #endif //IPACM_FILTERING_H
diff --git a/ipacm/src/Android.mk b/ipacm/src/Android.mk
new file mode 100644
index 0000000..5d06031
--- /dev/null
+++ b/ipacm/src/Android.mk
@@ -0,0 +1,80 @@
+ifneq (,$(filter $(QCOM_BOARD_PLATFORMS),$(TARGET_BOARD_PLATFORM)))
+ifneq (, $(filter aarch64 arm arm64, $(TARGET_ARCH)))
+
+LOCAL_PATH := $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_C_INCLUDES := $(LOCAL_PATH)/../src
+LOCAL_C_INCLUDES += $(LOCAL_PATH)/../inc
+LOCAL_C_INCLUDES += $(LOCAL_PATH)/../../ipanat/inc
+LOCAL_C_INCLUDES += external/icu4c/common
+LOCAL_C_INCLUDES += external/dhcpcd
+LOCAL_C_INCLUDES += bionic/libstdc++/include
+LOCAL_C_INCLUDES += external/libxml2/include
+LOCAL_C_INCLUDES += external/libnetfilter_conntrack/include
+LOCAL_C_INCLUDES += external/libnfnetlink/include
+
+LOCAL_C_INCLUDES += $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include
+LOCAL_ADDITIONAL_DEPENDENCIES := $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr
+
+
+LOCAL_CFLAGS := -v
+LOCAL_CFLAGS += -DFEATURE_IPA_ANDROID
+LOCAL_CFLAGS += -DDEBUG
+
+ifeq ($(TARGET_ARCH),arm)
+LOCAL_CFLAGS += -include bionic/libc/kernel/arch-arm/asm/posix_types.h
+LOCAL_CFLAGS += -include bionic/libc/kernel/arch-arm/asm/byteorder.h
+endif
+
+LOCAL_SRC_FILES := IPACM_Main.cpp \
+		IPACM_EvtDispatcher.cpp \
+		IPACM_Config.cpp \
+		IPACM_CmdQueue.cpp \
+		IPACM_Filtering.cpp \
+		IPACM_Routing.cpp \
+		IPACM_Header.cpp \
+		IPACM_Lan.cpp \
+		IPACM_Iface.cpp \
+		IPACM_Wlan.cpp \
+		IPACM_Wan.cpp \
+		IPACM_IfaceManager.cpp \
+		IPACM_Neighbor.cpp \
+		IPACM_Netlink.cpp \
+		IPACM_Xml.cpp \
+		IPACM_Conntrack_NATApp.cpp\
+		IPACM_ConntrackClient.cpp \
+		IPACM_ConntrackListener.cpp \
+                IPACM_Log.cpp
+
+LOCAL_MODULE := ipacm
+LOCAL_MODULE_TAGS := debug
+
+LOCAL_SHARED_LIBRARIES := libipanat
+LOCAL_SHARED_LIBRARIES += libxml2
+LOCAL_SHARED_LIBRARIES += libnfnetlink
+LOCAL_SHARED_LIBRARIES += libnetfilter_conntrack
+LOCAL_SHARED_LIBRARIES += libicuuc
+LOCAL_SHARED_LIBRARIES += libdhcpcd
+include $(BUILD_EXECUTABLE)
+
+################################################################################
+
+define ADD_TEST
+
+include $(CLEAR_VARS)
+LOCAL_MODULE       := $1
+LOCAL_SRC_FILES    := $1
+LOCAL_MODULE_CLASS := ipacm
+LOCAL_MODULE_TAGS  := debug
+LOCAL_MODULE_PATH  := $(TARGET_OUT_ETC)
+include $(BUILD_PREBUILT)
+
+endef
+
+IPACM_FILE_LIST := IPACM_cfg.xml
+$(foreach TEST,$(IPACM_FILE_LIST),$(eval $(call ADD_TEST,$(TEST))))
+
+endif # $(TARGET_ARCH)
+endif
diff --git a/ipacm/src/IPACM_Filtering.cpp b/ipacm/src/IPACM_Filtering.cpp
index fac26a2..4882ebb 100644
--- a/ipacm/src/IPACM_Filtering.cpp
+++ b/ipacm/src/IPACM_Filtering.cpp
@@ -57,18 +57,11 @@
 	{
 		IPACMERR("Failed opening %s.\n", DEVICE_NAME);
 	}
-
-	fd_wwan_ioctl = open(WWAN_QMI_IOCTL_DEVICE_NAME, O_RDWR);
-	if(fd_wwan_ioctl < 0)
-	{
-		IPACMERR("Failed to open %s.\n",WWAN_QMI_IOCTL_DEVICE_NAME);
-	}
 }
 
 IPACM_Filtering::~IPACM_Filtering()
 {
 	close(fd);
-	close(fd_wwan_ioctl);
 }
 
 bool IPACM_Filtering::DeviceNodeIsOpened()
@@ -238,16 +231,12 @@
 	int ret = 0, cnt, num_rules = 0, pos = 0;
 	ipa_install_fltr_rule_req_msg_v01 qmi_rule_msg;
 
+	int fd_wwan_ioctl = open(WWAN_QMI_IOCTL_DEVICE_NAME, O_RDWR);
 	if(fd_wwan_ioctl < 0)
 	{
-		IPACMERR("WWAN ioctl is not open.\n");
+		IPACMERR("Failed to open %s.\n",WWAN_QMI_IOCTL_DEVICE_NAME);
 		return false;
 	}
-	else
-	{
-		IPACMDBG("WWAN ioctl is open.\n");
-	}
-   
 
 	if(rule_table_v4 != NULL)
 	{
@@ -263,6 +252,7 @@
 	if(num_rules > QMI_IPA_MAX_FILTERS_V01)
 	{
 		IPACMERR("The number of filtering rules exceed limit.\n");
+		close(fd_wwan_ioctl);
 		return false;
 	}
 	else
@@ -329,20 +319,22 @@
 		if (ret != 0)
 		{
 			IPACMERR("Failed adding Filtering rule %p with ret %d\n ", &qmi_rule_msg, ret);
+			close(fd_wwan_ioctl);
 			return false;
 		}
 	}
 	IPACMDBG("Added Filtering rule %p\n", &qmi_rule_msg);
+	close(fd_wwan_ioctl);
 	return true;
 }
 
 bool IPACM_Filtering::SendFilteringRuleIndex(struct ipa_fltr_installed_notif_req_msg_v01* table)
 {
 	int ret = 0;
-
+	int fd_wwan_ioctl = open(WWAN_QMI_IOCTL_DEVICE_NAME, O_RDWR);
 	if(fd_wwan_ioctl < 0)
 	{
-		IPACMERR("WWAN ioctl is not open.\n");
+		IPACMERR("Failed to open %s.\n",WWAN_QMI_IOCTL_DEVICE_NAME);
 		return false;
 	}
 
@@ -350,10 +342,12 @@
 	if (ret != 0)
 	{
 		IPACMERR("Failed adding filtering rule index %p with ret %d\n", table, ret);
+		close(fd_wwan_ioctl);
 		return false;
 	}
 
 	IPACMDBG("Added Filtering rule index %p\n", table);
+	close(fd_wwan_ioctl);
 	return true;
 }
 
diff --git a/ipacm/src/IPACM_Iface.cpp b/ipacm/src/IPACM_Iface.cpp
index 6fb2e5c..293c311 100644
--- a/ipacm/src/IPACM_Iface.cpp
+++ b/ipacm/src/IPACM_Iface.cpp
@@ -511,6 +511,7 @@
 	if(iface_query == NULL)
 	{
 		IPACMERR("Unable to allocate iface_query memory.\n");
+		close(fd);
 		return IPACM_FAILURE;
 	}
 	IPACMDBG("iface name %s\n", dev_name);
@@ -531,6 +532,7 @@
 		if(tx_prop == NULL)
 		{
 			IPACMERR("Unable to allocate tx_prop memory.\n");
+			close(fd);
 			return IPACM_FAILURE;
 		}
 	memcpy(tx_prop->name, dev_name, sizeof(tx_prop->name));
@@ -562,6 +564,7 @@
 		if(rx_prop == NULL)
 		{
 			IPACMERR("Unable to allocate rx_prop memory.\n");
+			close(fd);
 			return IPACM_FAILURE;
 		}
 	memcpy(rx_prop->name, dev_name,
diff --git a/ipacm/src/IPACM_Main.cpp b/ipacm/src/IPACM_Main.cpp
index 8871303..d474d73 100644
--- a/ipacm/src/IPACM_Main.cpp
+++ b/ipacm/src/IPACM_Main.cpp
@@ -199,7 +199,7 @@
 		if(event == NULL)
 		{
 			IPACMERR("Failed to allocate memory.\n");
-			return;
+			return NULL;
 		}
 		memset(event, 0, length);
 		memcpy(event, buffer, length);
diff --git a/ipacm/src/IPACM_Netlink.cpp b/ipacm/src/IPACM_Netlink.cpp
index d579952..9c616af 100644
--- a/ipacm/src/IPACM_Netlink.cpp
+++ b/ipacm/src/IPACM_Netlink.cpp
@@ -210,6 +210,11 @@
 
 	while(true)
 	{
+	    for(i = 0; i < sk_fd_set->num_fd; i++ )
+		{
+			FD_SET(sk_fd_set->sk_fds[i].sk_fd, &(sk_fd_set->fdset));
+		}
+
 		if((ret = select(sk_fd_set->max_fd + 1, &(sk_fd_set->fdset), NULL, NULL, NULL)) < 0)
 		{
 			IPACMERR("ipa_nl select failed\n");
@@ -230,6 +235,7 @@
 											 i,
 											 sk_fd_set->sk_fds[i].sk_fd);
 						}
+						FD_CLR(sk_fd_set->sk_fds[i].sk_fd, &(sk_fd_set->fdset));
 					}
 					else
 					{
@@ -1595,6 +1601,7 @@
 	if(ipa_nl_addfd_map(sk_fdset, sk_info.sk_fd, read_f) != IPACM_SUCCESS)
 	{
 		IPACMERR("cannot add nl routing sock for reading\n");
+		close(sk_info.sk_fd);
 		return IPACM_FAILURE;
 	}
 
diff --git a/ipacm/src/IPACM_Wan.cpp b/ipacm/src/IPACM_Wan.cpp
index b1ea8f4..2c02e31 100644
--- a/ipacm/src/IPACM_Wan.cpp
+++ b/ipacm/src/IPACM_Wan.cpp
@@ -2522,6 +2522,7 @@
 			IPACMERR("ioctl IPA_IOC_QUERY_INTF_EXT_PROPS failed\n");
 			/* ext_prop memory will free when iface-down*/
 			free(ext_prop);
+			close(fd);
 			return ret;
 		}
 
@@ -2540,6 +2541,7 @@
 			IPACM_Wan::is_ext_prop_set = true;
 		}
 		free(ext_prop);
+		close(fd);
 	}
 	return IPACM_SUCCESS;
 }
diff --git a/ipacm/src/IPACM_Wlan.cpp b/ipacm/src/IPACM_Wlan.cpp
index f26a900..397b67f 100644
--- a/ipacm/src/IPACM_Wlan.cpp
+++ b/ipacm/src/IPACM_Wlan.cpp
@@ -967,6 +967,7 @@
 	if (pFilteringTable == NULL)
 	{
 		IPACMERR("Error Locate ipa_flt_rule_add memory...\n");
+		close(fd);
 		return IPACM_FAILURE;
 	}
 	memset(pFilteringTable, 0, len);
@@ -2852,4 +2853,4 @@
 		}
 	}
 	return IPACM_SUCCESS;
-}
\ No newline at end of file
+}
diff --git a/ipanat/src/Android.mk b/ipanat/src/Android.mk
new file mode 100644
index 0000000..a1116df
--- /dev/null
+++ b/ipanat/src/Android.mk
@@ -0,0 +1,24 @@
+ifneq (,$(filter $(QCOM_BOARD_PLATFORMS),$(TARGET_BOARD_PLATFORM)))
+ifneq (, $(filter aarch64 arm arm64, $(TARGET_ARCH)))
+
+LOCAL_PATH := $(call my-dir)
+
+include $(CLEAR_VARS)
+
+LOCAL_C_INCLUDES := $(LOCAL_PATH)/../inc
+LOCAL_C_INCLUDES += $(LOCAL_PATH)
+LOCAL_C_INCLUDES += $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr/include
+LOCAL_ADDITIONAL_DEPENDENCIES := $(TARGET_OUT_INTERMEDIATES)/KERNEL_OBJ/usr
+
+LOCAL_SRC_FILES := ipa_nat_drv.c \
+                   ipa_nat_drvi.c
+
+LOCAL_CFLAGS := -DDEBUG
+LOCAL_MODULE := libipanat
+LOCAL_MODULE_TAGS := debug
+LOCAL_PRELINK_MODULE := false
+
+include $(BUILD_SHARED_LIBRARY)
+
+endif # $(TARGET_ARCH)
+endif