4 * Copyright (c) 2000 - 2012 Samsung Electronics Co., Ltd All Rights Reserved
6 * Contact: Kidong Kim <kd0228.kim@samsung.com>
8 * Licensed under the Apache License, Version 2.0 (the "License");
9 * you may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
12 * http://www.apache.org/licenses/LICENSE-2.0
14 * Unless required by applicable law or agreed to in writing, software
15 * distributed under the License is distributed on an "AS IS" BASIS,
16 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17 * See the License for the specific language governing permissions and
18 * limitations under the License.
28 #include <sys/types.h>
30 #include <sys/socket.h>
33 #include <sys/ioctl.h>
35 #include <systemd/sd-daemon.h>
41 #include "secure_storage.h"
42 #include "ss_server_ipc.h"
43 #include "ss_server_main.h"
45 #define CONF_FILE_PATH "/usr/share/secure-storage/config"
47 #define VCONF_SMACK_UPDATE_FILE_PATH_KEY_NODE "db/smack/spd_policy_filepath"
48 #define VCONF_UPDATE_RESULT_KEY_NODE "db/smack/spd_update_result"
49 #define VCONF_UPDATE_RESULT_KEY_NODE_FOR_APP "db/smack/spd_update_result2"
51 static GMainLoop *event_loop;
53 char* get_key_file_path()
58 char seps[] = " :\n\r\t";
61 retbuf = (char*)malloc(sizeof(char) * 128);
64 SLOGE("fail to allocate memory.\n");
67 memset(buf, 0x00, 128);
68 memset(retbuf, 0x00, 128);
70 if(!(fp_conf = fopen(CONF_FILE_PATH, "r")))
72 SLOGE("Configuration file is not exist\n");
77 while(fgets(buf, 128, fp_conf))
79 token = strtok(buf, seps);
82 if(!strncmp(token, "MASTER_KEY_PATH", 15)) // master key path
84 token = strtok(NULL, seps); // real path
93 strncpy(retbuf, token, 127);
106 char* key_path = NULL;
108 key_path = get_key_file_path();
111 SLOGE("Configuration file is not exist\n");
115 if(!(fp_key = fopen(key_path, "r")))
117 SLOGE("Secret key file is not exist, [%s]\n", key_path);
134 char* key_path = NULL;
137 memset(key, 0x00, 33);
139 key_path = get_key_file_path();
142 SLOGE("Configuration file is not exist\n");
146 if((random_dev = open("/dev/urandom", O_RDONLY)) < 0)
148 SLOGE("Random device Open error\n");
155 read_len = read(random_dev, tmp_key, 1);
158 SLOGE("read error from random file");
162 if((tmp_key[0] >= '!') && (tmp_key[0] <= '~')) {
168 if(!(fp_key = fopen(key_path, "w")))
170 SECURE_SLOGE("Secret key file Open error, [%s]\n", key_path);
176 fprintf(fp_key, "%s", key);
178 if(chmod(key_path, 0600)!=0)
180 SLOGE("Secret key file chmod error, [%s]\n", strerror(errno));
193 /* for executing coverage tool (2009-04-03) */
194 void SigHandler(int signo)
196 SLOGI("Got Signal %d\n", signo);
202 int GetSocketFromSystemd(int* pSockfd)
204 int n = sd_listen_fds(0);
207 for(fd = SD_LISTEN_FDS_START; fd < SD_LISTEN_FDS_START+n; ++fd) {
208 if (0 < sd_is_socket_unix(fd, SOCK_STREAM, 1,
218 int CreateNewSocket(int* pSockfd)
220 int server_sockfd = 0;
221 int temp_len_sock = 0;
222 struct sockaddr_un serveraddr;
224 if((server_sockfd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0)
226 SLOGE("Error in function socket()..\n");
230 temp_len_sock = strlen(SS_SOCK_PATH);
232 bzero(&serveraddr, sizeof(serveraddr));
233 serveraddr.sun_family = AF_UNIX;
234 strncpy(serveraddr.sun_path, SS_SOCK_PATH, temp_len_sock);
235 serveraddr.sun_path[temp_len_sock] = '\0';
237 if((bind(server_sockfd, (struct sockaddr*)&serveraddr, sizeof(serveraddr))) < 0)
239 unlink("/tmp/SsSocket");
240 if((bind(server_sockfd, (struct sockaddr*)&serveraddr, sizeof(serveraddr))) < 0)
242 SLOGE("Error in function bind()..\n");
243 close(server_sockfd);
244 return 0; // ipc error
248 if(chmod(SS_SOCK_PATH, S_IRWXU | S_IRWXG | S_IRWXO) != 0)
250 close(server_sockfd);
254 *pSockfd = server_sockfd;
259 void SsServerComm(void)
261 int server_sockfd, client_sockfd;
263 struct sockaddr_un clientaddr, serveraddr;
265 struct ucred cr; // for test client pid. 2009-03-24
266 int cl = sizeof(cr); //
267 int temp_len_sock = 0;
270 ReqData_t recv_data = {0, };
271 RspData_t send_data = {0, };
274 server_sockfd = client_sockfd = -1;
276 if(!GetSocketFromSystemd(&server_sockfd))
278 SLOGE("Failed to get sockfd from systemd");
279 if(!CreateNewSocket(&server_sockfd))
281 SLOGE("Failed to create socket");
282 send_data.rsp_type = SS_SOCKET_ERROR; // ipc error
285 if((listen(server_sockfd, 5)) < 0)
287 SLOGE("Error in function listen()..\n");
288 send_data.rsp_type = SS_SOCKET_ERROR; // ipc error
289 goto Error_close_exit;
294 SLOGD("Get socket from systemd");
297 client_len = sizeof(clientaddr);
299 signal(SIGINT, (void*)SigHandler);
305 if((client_sockfd = accept(server_sockfd, (struct sockaddr*)&clientaddr, (socklen_t*)&client_len)) < 0)
307 SLOGE("Error in function accept()..[%d, %d]\n", client_sockfd, errno);
308 send_data.rsp_type = SS_SOCKET_ERROR; // ipc error
309 goto Error_close_exit;
312 // for test client pid. 2009-03-24
313 if(getsockopt(client_sockfd, SOL_SOCKET, SO_PEERCRED, &cr, (socklen_t*)&cl) != 0)
315 SLOGE("getsockopt() fail\n");
319 if(read(client_sockfd, (char*)&recv_data, sizeof(recv_data)) < 0)
321 SLOGE("Error in function read()..\n");
322 send_data.rsp_type = SS_SOCKET_ERROR; // ipc error
323 goto Error_close_exit;
326 temp_len_in = strlen(recv_data.data_infilepath);
328 switch(recv_data.req_type)
331 send_data.rsp_type = SsServerDataStoreFromFile(cr.pid, recv_data.data_infilepath, recv_data.flag, client_sockfd, recv_data.group_id);
333 if(send_data.rsp_type == 1)
335 strncpy(send_data.data_filepath, recv_data.data_infilepath, MAX_FILENAME_SIZE);
336 send_data.data_filepath[temp_len_in] = '\0';
340 strncpy(send_data.data_filepath, "Error Occured..", MAX_FILENAME_SIZE);
341 send_data.data_filepath[15] = '\0';
344 write(client_sockfd, (char*)&send_data, sizeof(send_data));
347 send_data.rsp_type = SsServerDataStoreFromBuffer(cr.pid, recv_data.buffer, recv_data.count, recv_data.data_infilepath, recv_data.flag, client_sockfd, recv_data.group_id);
349 if(send_data.rsp_type == 1)
351 strncpy(send_data.data_filepath, recv_data.data_infilepath, MAX_FILENAME_SIZE);
352 send_data.data_filepath[temp_len_in] = '\0';
356 strncpy(send_data.data_filepath, "Error Occured..", MAX_FILENAME_SIZE);
357 send_data.data_filepath[15] = '\0';
360 write(client_sockfd, (char*)&send_data, sizeof(send_data));
363 send_data.rsp_type = SsServerDataRead(cr.pid, recv_data.data_infilepath, send_data.buffer, recv_data.count, &(send_data.readLen), recv_data.flag, client_sockfd, recv_data.group_id);
365 if(send_data.rsp_type == 1)
367 strncpy(send_data.data_filepath, recv_data.data_infilepath, MAX_FILENAME_SIZE);
368 send_data.data_filepath[temp_len_in] = '\0';
372 strncpy(send_data.data_filepath, "Error Occured..", MAX_FILENAME_SIZE);
373 send_data.data_filepath[15] = '\0';
376 write(client_sockfd, (char*)&send_data, sizeof(send_data));
379 send_data.rsp_type = SsServerGetInfo(cr.pid, recv_data.data_infilepath, send_data.buffer, recv_data.flag, client_sockfd /*recv_data.cookie*/, recv_data.group_id);
381 if(send_data.rsp_type == 1)
383 strncpy(send_data.data_filepath, recv_data.data_infilepath, MAX_FILENAME_SIZE);
384 send_data.data_filepath[temp_len_in] = '\0';
388 strncpy(send_data.data_filepath, "Error Occured..", MAX_FILENAME_SIZE);
389 send_data.data_filepath[15] = '\0';
392 write(client_sockfd, (char*)&send_data, sizeof(send_data));
395 send_data.rsp_type = SsServerGetDuk(client_sockfd, send_data.buffer, &(send_data.readLen), recv_data.group_id, recv_data.flag);
396 write(client_sockfd, (char*)&send_data, sizeof(send_data));
399 send_data.rsp_type = SsServerDeleteFile(cr.pid, recv_data.data_infilepath, recv_data.flag, client_sockfd, recv_data.group_id);
401 if(send_data.rsp_type == 1)
403 strncpy(send_data.data_filepath, recv_data.data_infilepath, MAX_FILENAME_SIZE);
404 send_data.data_filepath[temp_len_in] = '\0';
408 strncpy(send_data.data_filepath, "Error Occured..", MAX_FILENAME_SIZE);
409 send_data.data_filepath[15] = '\0';
412 write(client_sockfd, (char*)&send_data, sizeof(send_data));
416 SLOGE("Input error..Please check request type\n");
419 close(client_sockfd);
423 close(server_sockfd);
426 strncpy(send_data.data_filepath, "error", MAX_FILENAME_SIZE);
427 send_data.data_filepath[5] = '\0';
429 if(client_sockfd >= 0)
431 write(client_sockfd, (char*)&send_data, sizeof(send_data));
432 close(client_sockfd);
435 SLOGE("cannot connect to client socket.\n");
438 int SsServerUpdateSmackPolicy()
440 typedef int (*SmackPolicyUpdateFuncPointer)();
441 SmackPolicyUpdateFuncPointer pSmackPolicyUpdateFuncPointer = NULL;
444 void* dlHandle = dlopen("/usr/lib/libsmack-update-service.so", RTLD_LAZY);
448 SLOGE("Failed to open so with reason : %s", dlerror());
452 pSmackPolicyUpdateFuncPointer = (SmackPolicyUpdateFuncPointer)dlsym(dlHandle, "spd_smack_policy_update");
453 if (dlerror() != NULL)
455 SLOGE("Failed to find spd_smack_policy_update symbol : %s", dlerror());
459 errCode = pSmackPolicyUpdateFuncPointer();
470 void vconf_smack_update_cb(keynode_t *key, void* data)
472 SLOGD("Callback received");
475 switch(vconf_keynode_get_type(key))
478 printf("key = %s, value = %d(int)\n",
479 vconf_keynode_get_name(key), vconf_keynode_get_int(key));
481 case VCONF_TYPE_STRING:
483 printf("key = %s, value = %s(string)\n",
484 vconf_keynode_get_name(key), vconf_keynode_get_str(key));
485 if (vconf_keynode_get_str(key))
487 errorCode = SsServerUpdateSmackPolicy();
488 LOGD("set the updation status with value %d", errorCode);
489 // set the update result for fota team
490 int ret = vconf_set_int(VCONF_UPDATE_RESULT_KEY_NODE, errorCode);
493 LOGD("failed to set the updation status for fota");
496 // set the update result for the app control
497 ret = vconf_set_int(VCONF_UPDATE_RESULT_KEY_NODE_FOR_APP, errorCode);
500 LOGD("failed to set the updation status for app control");
506 LOGD("file path is invalid");
510 fprintf(stderr, "Unknown Type(%d)\n", vconf_keynode_get_type(key));
514 printf("%s Notification OK", (char *)data);
518 int vconf_smack_update(void* pData)
520 vconf_notify_key_changed(VCONF_SMACK_UPDATE_FILE_PATH_KEY_NODE, vconf_smack_update_cb, NULL);
522 event_loop = g_main_loop_new(NULL, FALSE);
523 g_main_loop_run(event_loop);
530 SLOGI("Secure Storage Server Start..\n");
534 DIR* dp = NULL; // make default directory(if not exist)
535 pthread_t main_thread;
537 pthread_create(&main_thread, NULL, vconf_smack_update, NULL);
538 if((dp = opendir(SS_STORAGE_DEFAULT_PATH)) == NULL)
540 SLOGI("directory [%s] is not exist, making now.\n", SS_STORAGE_DEFAULT_PATH);
541 if(mkdir(SS_STORAGE_DEFAULT_PATH, 0700) < 0)
544 SLOGE("Failed while making [%s] directory. Errno: %s\n", SS_STORAGE_DEFAULT_PATH, strerror(err_tmp));
551 exist_ret = check_key_file(); // if 0, there is not key file. Or 1, exist.
555 make_ret = make_key_file();
559 SLOGE("Making key file fail. ss-server will be terminated..\n");