[Feature] add GA346 baseline version
Change-Id: Ic62933698569507dcf98240cdf5d9931ae34348f
diff --git a/src/apps/atom-base/progs/property/libprop/request.c b/src/apps/atom-base/progs/property/libprop/request.c
new file mode 100644
index 0000000..d72531d
--- /dev/null
+++ b/src/apps/atom-base/progs/property/libprop/request.c
@@ -0,0 +1,264 @@
+/* Copyright Statement:
+
+ * This software/firmware and related documentation ("MediaTek Software") are
+ * protected under relevant copyright laws. The information contained herein is
+ * confidential and proprietary to MediaTek Inc. and/or its licensors. Without
+ * the prior written permission of MediaTek inc. and/or its licensors, any
+ * reproduction, modification, use or disclosure of MediaTek Software, and
+ * information contained herein, in whole or in part, shall be strictly
+ * prohibited.
+
+ * MediaTek Inc. (C) 2015. All rights reserved.
+
+ * BY OPENING THIS FILE, RECEIVER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
+ * THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
+ * RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO RECEIVER
+ * ON AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL
+ * WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR
+ * NONINFRINGEMENT. NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH
+ * RESPECT TO THE SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY,
+ * INCORPORATED IN, OR SUPPLIED WITH THE MEDIATEK SOFTWARE, AND RECEIVER AGREES
+ * TO LOOK ONLY TO SUCH THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO.
+ * RECEIVER EXPRESSLY ACKNOWLEDGES THAT IT IS RECEIVER'S SOLE RESPONSIBILITY TO
+ * OBTAIN FROM ANY THIRD PARTY ALL PROPER LICENSES CONTAINED IN MEDIATEK
+ * SOFTWARE. MEDIATEK SHALL ALSO NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE
+ * RELEASES MADE TO RECEIVER'S SPECIFICATION OR TO CONFORM TO A PARTICULAR
+ * STANDARD OR OPEN FORUM. RECEIVER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S
+ * ENTIRE AND CUMULATIVE LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE
+ * RELEASED HEREUNDER WILL BE, AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE
+ * MEDIATEK SOFTWARE AT ISSUE, OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE
+ * CHARGE PAID BY RECEIVER TO MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <stddef.h>
+#include <string.h>
+#include <errno.h>
+#include <assert.h>
+#include <unistd.h>
+#include <fcntl.h>
+#include <time.h>
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <sys/un.h>
+#include <syslog.h>
+#include "utility.h"
+#include "request.h"
+
+/*******************************************************************************/
+/* REQUEST local definitions */
+/*******************************************************************************/
+
+/*******************************************************************************/
+/* REQUEST local prototypes */
+/*******************************************************************************/
+
+/*******************************************************************************/
+/* REQUEST local variables */
+/*******************************************************************************/
+
+/*******************************************************************************/
+/* REQUEST local functions */
+/*******************************************************************************/
+static int pack_request_string(char **p, char **next, const char *roof)
+{
+ if (*p == NULL) {
+ return 0;
+ } else {
+ size_t len = strlen(*p) + 1;
+
+ if ((roof - *next) < (ptrdiff_t)len) {
+ return -1;
+ } else {
+ strcpy(*next, *p);
+ *next += len;
+ *p = (char *)0x12345678;
+ return 0;
+ }
+ }
+}
+
+static int unpack_request_string(char **p, char **next, const char *roof)
+{
+ if (*p == NULL) {
+ return 0;
+ } else if (*p == (char *)0x12345678) {
+ char *end = memchr(*next, '\0', roof - *next);
+
+ if (end == NULL) {
+ return -1;
+ } else {
+ *p = *next;
+ *next = end + 1;
+ return 0;
+ }
+ }
+ return -1;
+}
+
+/*******************************************************************************/
+/* REQUEST functions */
+/*******************************************************************************/
+int pack_request(struct sncfg_request *request)
+{
+ int size;
+ char *next, *roof;
+
+ next = request->string + request->reservedLen;
+ roof = next + sizeof(request->string);
+
+ if (request->magic != SNCFG_REQUEST_MAGIC) {
+ return -1;
+ }
+
+ if (request->type >= SNCFG_REQUEST_TYPE_RESERVED) {
+ return -1;
+ }
+
+ if (pack_request_string(&request->key, &next, roof) < 0 ||
+ pack_request_string(&request->value, &next, roof) < 0) {
+ return -1;
+ }
+
+ size = next - (char *)request;
+ return size;
+}
+
+int unpack_request(struct sncfg_request *request, int size)
+{
+ char *next, *roof;
+
+ next = request->string + request->reservedLen;
+ roof = (char *)request + size;
+
+ if (roof < next) {
+ return -1;
+ }
+
+ if (request->magic != SNCFG_REQUEST_MAGIC) {
+ return -1;
+ }
+
+ if (request->type >= SNCFG_REQUEST_TYPE_RESERVED) {
+ return -1;
+ }
+
+ if (unpack_request_string(&request->key, &next, roof) < 0 ||
+ unpack_request_string(&request->value, &next, roof) < 0) {
+ return -1;
+ }
+
+ return 0;
+}
+
+int connect_request(void)
+{
+ int sock;
+ struct sockaddr_un addr = { AF_UNIX, SNCFG_REQUEST_UNIX_SOCKET };
+
+ if (access(addr.sun_path, R_OK | W_OK) < 0) {
+ return -1;
+ }
+
+ sock = socket(AF_UNIX, SOCK_STREAM, 0);
+ if (sock == -1) {
+ return -1;
+ }
+
+ struct timeval tm;
+ tm.tv_sec = 8; /* 8 Secs Timeout */
+ tm.tv_usec = 0;
+
+ if (setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, (const void *)&tm, sizeof(tm)) < 0) {
+ fprintf(stderr, "[LIBSNCFG][%d] Can't setsockopt SO_SNDTIMEO 8 seconds for connect ... %s !!\r\n", getpid(), strerror(errno));
+ syslog(LOG_WARNING, "[LIBSNCFG][%d] Can't setsockopt SO_SNDTIMEO 8 seconds for connect ... %s !!", getpid(), strerror(errno));
+ close(sock);
+ return -1;
+ }
+ if (setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (const void *)&tm, sizeof(tm)) < 0) {
+ fprintf(stderr, "[LIBSNCFG][%d] Can't setsockopt SO_RCVTIMEO 8 seconds for connect ... %s !!\r\n", getpid(), strerror(errno));
+ syslog(LOG_WARNING, "[LIBSNCFG][%d] Can't setsockopt SO_RCVTIMEO 8 seconds for connect ... %s !!", getpid(), strerror(errno));
+ close(sock);
+ return -1;
+ }
+
+ if (connect(sock, (struct sockaddr *)&addr,
+ offsetof(struct sockaddr_un, sun_path) + strlen(addr.sun_path)) < 0) {
+ close(sock);
+ return -1;
+ }
+
+ return sock;
+}
+
+int accept_request(int sockfd)
+{
+ int sock;
+ socklen_t addrlen;
+ struct sockaddr_un addr;
+
+ addrlen = sizeof(addr);
+ sock = accept(sockfd, (struct sockaddr *)&addr, &addrlen);
+ if (sock == -1) {
+ return -1;
+ }
+
+ if (fcntl(sock, F_SETFD, FD_CLOEXEC) < 0) {
+ close(sock);
+ return -1;
+ }
+
+ struct timeval tm;
+ tm.tv_sec = 8; /* 8 Secs Timeout */
+ tm.tv_usec = 0;
+
+ if (setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO, (const void *)&tm, sizeof(tm)) < 0) {
+ fprintf(stderr, "[LIBSNCFG][%d] Can't setsockopt SO_SNDTIMEO 8 seconds for accept ... %s !!\r\n", getpid(), strerror(errno));
+ syslog(LOG_WARNING, "[LIBSNCFG][%d] Can't setsockopt SO_SNDTIMEO 8 seconds for accept ... %s !!", getpid(), strerror(errno));
+ close(sock);
+ return -1;
+ }
+ if (setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO, (const void *)&tm, sizeof(tm)) < 0) {
+ fprintf(stderr, "[LIBSNCFG][%d] Can't setsockopt SO_RCVTIMEO 8 seconds for accept ... %s !!\r\n", getpid(), strerror(errno));
+ syslog(LOG_WARNING, "[LIBSNCFG][%d] Can't setsockopt SO_RCVTIMEO 8 seconds for accept ... %s !!", getpid(), strerror(errno));
+ close(sock);
+ return -1;
+ }
+
+ return sock;
+}
+
+int request_for_sncfg(struct sncfg_request *request)
+{
+ int sock, size;
+
+ size = pack_request(request);
+ if (size < 0) {
+ return -1;
+ }
+
+ sock = connect_request();
+ if (sock < 0) {
+ return -1;
+ }
+
+ if (safe_write(sock, request, size) != size) {
+ close(sock);
+ return -1;
+ }
+
+ size = safe_read(sock, request, sizeof(struct sncfg_request));
+
+ if (size < 0 ||
+ unpack_request(request, size) < 0 ||
+ request->status < 0) {
+ /* request processing failed */
+ close(sock);
+ return -1;
+ }
+
+ close(sock);
+ return 0;
+}