1 /* 2 * Copyright (C) 2009 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef __KEYSTORE_GET_H__ 18 #define __KEYSTORE_GET_H__ 19 20 #include <stdio.h> 21 #include <stdint.h> 22 #include <unistd.h> 23 #include <sys/types.h> 24 #include <sys/socket.h> 25 26 #include <cutils/sockets.h> 27 28 #define KEYSTORE_MESSAGE_SIZE 65535 29 30 #ifdef __cplusplus 31 extern "C" { 32 #endif 33 34 /* This function is provided for native components to get values from keystore. 35 * Users are required to link against libcutils. Keys and values are 8-bit safe. 36 * The first two arguments are the key and its length. The third argument 37 * specifies the buffer to store the retrieved value, which must be an array of 38 * KEYSTORE_MESSAGE_SIZE bytes. This function returns the length of the value or 39 * -1 if an error happens. */ 40 static int keystore_get(const char *key, int length, char *value) 41 { 42 uint8_t bytes[2] = {length >> 8, length}; 43 uint8_t code = 'g'; 44 int sock; 45 46 if (length < 0 || length > KEYSTORE_MESSAGE_SIZE) { 47 return -1; 48 } 49 sock = socket_local_client("keystore", ANDROID_SOCKET_NAMESPACE_RESERVED, 50 SOCK_STREAM); 51 if (sock == -1) { 52 return -1; 53 } 54 if (send(sock, &code, 1, 0) == 1 && send(sock, bytes, 2, 0) == 2 && 55 send(sock, key, length, 0) == length && shutdown(sock, SHUT_WR) == 0 && 56 recv(sock, &code, 1, 0) == 1 && code == /* NO_ERROR */ 1 && 57 recv(sock, &bytes[0], 1, 0) == 1 && recv(sock, &bytes[1], 1, 0) == 1) { 58 int offset = 0; 59 length = bytes[0] << 8 | bytes[1]; 60 while (offset < length) { 61 int n = recv(sock, &value[offset], length - offset, 0); 62 if (n <= 0) { 63 length = -1; 64 break; 65 } 66 offset += n; 67 } 68 } else { 69 length = -1; 70 } 71 72 close(sock); 73 return length; 74 } 75 76 #ifdef __cplusplus 77 } 78 #endif 79 80 #endif 81