/* * Class: info_kghost_android_openvpn_OpenVpn_ControlChannel * Method: send * Signature: (Ljava/io/FileDescriptor;Ljava/nio/Buffer;Ljava/io/FileDescriptor;)I */ JNIEXPORT jint JNICALL Java_info_kghost_android_openvpn_OpenVpn_00024ControlChannel_send__Linfo_kghost_android_openvpn_FileDescriptorHolder_2Ljava_nio_Buffer_2IILinfo_kghost_android_openvpn_FileDescriptorHolder_2 (JNIEnv *env, jclass cls, jobject socket, jobject buffer, jint offset, jint length, jobject fd) { int s = jniGetFDFromFileDescriptor(env, socket); if (s < 0) { throwError(env, "java/lang/IllegalArgumentException", "socket"); return -1; } jlong cap = (*env)->GetDirectBufferCapacity(env, buffer); char* ptr = (*env)->GetDirectBufferAddress(env, buffer); int sendfd = jniGetFDFromFileDescriptor(env, fd); int result = write_fd(s, ptr+offset, min(cap-offset, length), sendfd); if (result < 0) { switch (errno) { case EACCES: case EBADF: case ENOTCONN: case ENOTSOCK: case EISCONN: case ECONNRESET: case EDESTADDRREQ: throwError(env, "java/lang/IllegalArgumentException", "socket"); break; case EINVAL: throwError(env, "java/lang/IllegalArgumentException", "inval"); break; case EFAULT: throwError(env, "java/lang/IllegalArgumentException", "buffer"); break; case EMSGSIZE: throwError(env, "java/lang/IllegalArgumentException", "msg size"); break; case EINTR: throwError(env, "java/lang/InterruptedException", "interrupted"); break; case ENOBUFS: case ENOMEM: throwError(env, "java/lang/RuntimeException", "oom"); break; case EAGAIN: throwError(env, "java/lang/IllegalArgumentException", "non-block socket"); break; default: throwError(env, "java/lang/RuntimeException", "unknown error"); break; } } return result; }
static void socket_bind_local (JNIEnv *env, jobject object, jobject fileDescriptor, jstring name, jint namespaceId) { int ret; int fd; if (name == NULL) { jniThrowNullPointerException(env, NULL); return; } fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionCheck()) { return; } ScopedUtfChars nameUtf8(env, name); ret = socket_local_server_bind(fd, nameUtf8.c_str(), namespaceId); if (ret < 0) { jniThrowIOException(env, errno); return; } }
/* * Dump the native heap, writing human-readable output to the specified * file descriptor. */ static void android_os_Debug_dumpNativeHeap(JNIEnv* env, jobject clazz, jobject fileDescriptor) { if (fileDescriptor == NULL) { jniThrowNullPointerException(env, NULL); return; } int origFd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (origFd < 0) { jniThrowRuntimeException(env, "Invalid file descriptor"); return; } /* dup() the descriptor so we don't close the original with fclose() */ int fd = dup(origFd); if (fd < 0) { ALOGW("dup(%d) failed: %s\n", origFd, strerror(errno)); jniThrowRuntimeException(env, "dup() failed"); return; } FILE* fp = fdopen(fd, "w"); if (fp == NULL) { ALOGW("fdopen(%d) failed: %s\n", fd, strerror(errno)); close(fd); jniThrowRuntimeException(env, "fdopen() failed"); return; } ALOGD("Native heap dump starting...\n"); dumpNativeHeap(fp); ALOGD("Native heap dump complete.\n"); fclose(fp); }
/* private native void connectLocal(FileDescriptor fd, * String name, int namespace) throws IOException */ static void socket_connect_local(JNIEnv *env, jobject object, jobject fileDescriptor, jstring name, jint namespaceId) { int ret; int fd; fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionCheck()) { return; } ScopedUtfChars nameUtf8(env, name); ret = socket_local_client_connect( fd, nameUtf8.c_str(), namespaceId, SOCK_STREAM); if (ret < 0) { jniThrowIOException(env, errno); return; } }
/* * Function: getPeerCon * Purpose: retrieves security context of peer socket * Parameters: * fileDescriptor: peer socket file as a FileDescriptor object * Returns: jstring representing the security_context of socket or NULL if error * Exceptions: NullPointerException if fileDescriptor object is NULL */ static jstring getPeerCon(JNIEnv *env, jobject, jobject fileDescriptor) { if (isSELinuxDisabled) { return NULL; } if (fileDescriptor == NULL) { jniThrowNullPointerException(env, "Trying to check security context of a null peer socket."); return NULL; } int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionOccurred() != NULL) { ALOGE("getPeerCon => getFD for %p failed", fileDescriptor); return NULL; } security_context_t tmp = NULL; int ret = getpeercon(fd, &tmp); Unique_SecurityContext context(tmp); ScopedLocalRef<jstring> contextStr(env, NULL); if (ret != -1) { contextStr.reset(env->NewStringUTF(context.get())); } ALOGV("getPeerCon(%d) => %s", fd, context.get()); return contextStr.release(); }
static void com_android_internal_os_ZygoteInit_setCloseOnExec (JNIEnv *env, jobject clazz, jobject descriptor, jboolean flag) { int fd; int err; int fdFlags; fd = jniGetFDFromFileDescriptor(env, descriptor); if (env->ExceptionOccurred() != NULL) { return; } fdFlags = fcntl(fd, F_GETFD); if (fdFlags < 0) { jniThrowIOException(env, errno); return; } if (flag) { fdFlags |= FD_CLOEXEC; } else { fdFlags &= ~FD_CLOEXEC; } err = fcntl(fd, F_SETFD, fdFlags); if (err < 0) { jniThrowIOException(env, errno); return; } }
static jint socket_read (JNIEnv *env, jobject object, jobject fileDescriptor) { int fd; int err; if (fileDescriptor == NULL) { jniThrowNullPointerException(env, NULL); return (jint)-1; } fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionCheck()) { return (jint)0; } unsigned char buf; err = socket_read_all(env, object, fd, &buf, 1); if (err < 0) { jniThrowIOException(env, errno); return (jint)0; } if (err == 0) { // end of file return (jint)-1; } return (jint)buf; }
TILE_GET_INFO_MEMBER(aerofgt_state::get_bg2_tile_info) { UINT16 code = m_bg2videoram[tile_index]; int bank = 4 + ((code & 0x1800) >> 11); SET_TILE_INFO_MEMBER(m_gfxdecode, 1, (code & 0x07ff) + (m_gfxbank[bank] << 11), (code & 0xe000) >> 13, 0); } /*************************************************************************** Start the video hardware emulation. ***************************************************************************/ void aerofgt_state::aerofgt_register_state_globals( ) { save_item(NAME(m_gfxbank)); save_item(NAME(m_bank)); save_item(NAME(m_bg1scrollx)); save_item(NAME(m_bg1scrolly)); save_item(NAME(m_bg2scrollx)); save_item(NAME(m_bg2scrolly)); save_item(NAME(m_charpalettebank)); save_item(NAME(m_spritepalettebank)); } VIDEO_START_MEMBER(aerofgt_state,pspikes) { m_bg1_tilemap = &machine().tilemap().create(tilemap_get_info_delegate(FUNC(aerofgt_state::get_pspikes_tile_info),this),TILEMAP_SCAN_ROWS,8,8,64,32); /* no bg2 in this game */
/* private native void connectLocal(FileDescriptor fd, * String name, int namespace) throws IOException */ static void socket_connect_local(JNIEnv *env, jobject object, jobject fileDescriptor, jstring name, jint namespaceId) { int ret; const char *nameUtf8; int fd; nameUtf8 = env->GetStringUTFChars(name, NULL); fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionOccurred() != NULL) { return; } ret = socket_local_client_connect( fd, nameUtf8, namespaceId, SOCK_STREAM); env->ReleaseStringUTFChars(name, nameUtf8); if (ret < 0) { jniThrowIOException(env, errno); return; } }
static void socket_close (JNIEnv *env, jobject object, jobject fileDescriptor) { int fd; int err; if (fileDescriptor == NULL) { jniThrowNullPointerException(env, NULL); return; } fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionOccurred() != NULL) { return; } do { err = close(fd); } while (err < 0 && errno == EINTR); if (err < 0) { jniThrowIOException(env, errno); return; } }
extern "C" jint Java_java_util_zip_Inflater_setFileInputImpl(JNIEnv* env, jobject, jobject javaFileDescriptor, jlong off, jint len, jlong handle) { NativeZipStream* stream = toNativeZipStream(handle); // We reuse the existing native buffer if it's large enough. // TODO: benchmark. if (stream->inCap < len) { stream->setInput(env, NULL, 0, len); } else { stream->stream.next_in = reinterpret_cast<Bytef*>(&stream->input[0]); stream->stream.avail_in = len; } // As an Android-specific optimization, we read directly onto the native heap. // The original code used Java to read onto the Java heap and then called setInput(byte[]). // TODO: benchmark. int fd = jniGetFDFromFileDescriptor(env, javaFileDescriptor); int rc = TEMP_FAILURE_RETRY(lseek(fd, off, SEEK_SET)); if (rc == -1) { jniThrowIOException(env, errno); return 0; } jint totalByteCount = 0; Bytef* dst = reinterpret_cast<Bytef*>(&stream->input[0]); ssize_t byteCount; while ((byteCount = TEMP_FAILURE_RETRY(read(fd, dst, len))) > 0) { dst += byteCount; len -= byteCount; totalByteCount += byteCount; } if (byteCount == -1) { jniThrowIOException(env, errno); return 0; } return totalByteCount; }
static void socket_bind_local (JNIEnv *env, jobject object, jobject fileDescriptor, jstring name, jint namespaceId) { int ret; int fd; const char *nameUtf8; if (name == NULL) { jniThrowNullPointerException(env, NULL); } fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionOccurred() != NULL) { return; } nameUtf8 = env->GetStringUTFChars(name, NULL); ret = socket_local_server_bind(fd, nameUtf8, namespaceId); env->ReleaseStringUTFChars(name, nameUtf8); if (ret < 0) { jniThrowIOException(env, errno); return; } }
static jint socket_pending (JNIEnv *env, jobject object, jobject fileDescriptor) { int fd; fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionCheck()) { return (jint)-1; } int pending; int ret = ioctl(fd, TIOCOUTQ, &pending); // If this were a non-socket fd, there would be other cases to worry // about... //ALOGD("socket_pending, ioctl ret:%d, pending:%d", ret, pending); if (ret < 0) { jniThrowIOException(env, errno); return (jint) 0; } return (jint)pending; }
static void android_os_MemoryFile_pin(JNIEnv* env, jobject clazz, jobject fileDescriptor, jboolean pin) { int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); int result = (pin ? ashmem_pin_region(fd, 0, 0) : ashmem_unpin_region(fd, 0, 0)); if (result < 0) { jniThrowException(env, "java/io/IOException", NULL); } }
static void android_os_MemoryFile_close(JNIEnv* env, jobject clazz, jobject fileDescriptor) { int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (fd >= 0) { jniSetFileDescriptorOfFD(env, fileDescriptor, -1); close(fd); } }
static jint android_os_MemoryFile_mmap(JNIEnv* env, jobject clazz, jobject fileDescriptor, jint length, jint prot) { int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); jint result = (jint)mmap(NULL, length, prot, MAP_SHARED, fd, 0); if (!result) jniThrowException(env, "java/io/IOException", "mmap failed"); return result; }
static int skipChunk_native(JNIEnv* env, jobject clazz, jobject fdObj, jint bytesToSkip) { int fd = jniGetFDFromFileDescriptor(env, fdObj); lseek(fd, bytesToSkip, SEEK_CUR); return 0; }
static jlong ctor_native(JNIEnv* env, jobject clazz, jobject fileDescriptor) { int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (fd == -1) { return (jlong)NULL; } return (jlong)new BackupDataWriter(fd); }
static int ctor_native(JNIEnv* env, jobject clazz, jobject fileDescriptor) { int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (fd == -1) { return NULL; } return (int)new BackupDataReader(fd); }
static void android_os_Parcel_writeFileDescriptor(JNIEnv* env, jclass clazz, jlong nativePtr, jobject object) { Parcel* parcel = reinterpret_cast<Parcel*>(nativePtr); if (parcel != NULL) { const status_t err = parcel->writeDupFileDescriptor(jniGetFDFromFileDescriptor(env, object)); if (err != NO_ERROR) { signalExceptionForError(env, clazz, err); } } }
static void android_os_Parcel_clearFileDescriptor(JNIEnv* env, jclass clazz, jobject object) { if (object == NULL) { jniThrowNullPointerException(env, NULL); return; } int fd = jniGetFDFromFileDescriptor(env, object); if (fd >= 0) { jniSetFileDescriptorOfFD(env, object, -1); } }
static jint writeSnapshot_native(JNIEnv* env, jobject clazz, jlong ptr, jobject fileDescriptor) { int err; RestoreHelperBase* restore = (RestoreHelperBase*)ptr; int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); err = restore->WriteSnapshot(fd); return (jint) err; }
static jint performBackup_native(JNIEnv* env, jobject clazz, jobject oldState, jlong data, jobject newState, jobjectArray files, jobjectArray keys) { int err; // all parameters have already been checked against null int oldStateFD = oldState != NULL ? jniGetFDFromFileDescriptor(env, oldState) : -1; int newStateFD = jniGetFDFromFileDescriptor(env, newState); BackupDataWriter* dataStream = (BackupDataWriter*)data; const int fileCount = env->GetArrayLength(files); char const** filesUTF = (char const**)malloc(sizeof(char*)*fileCount); for (int i=0; i<fileCount; i++) { filesUTF[i] = env->GetStringUTFChars((jstring)env->GetObjectArrayElement(files, i), NULL); } const int keyCount = env->GetArrayLength(keys); char const** keysUTF = (char const**)malloc(sizeof(char*)*keyCount); for (int i=0; i<keyCount; i++) { keysUTF[i] = env->GetStringUTFChars((jstring)env->GetObjectArrayElement(keys, i), NULL); } err = back_up_files(oldStateFD, dataStream, newStateFD, filesUTF, keysUTF, fileCount); for (int i=0; i<fileCount; i++) { env->ReleaseStringUTFChars((jstring)env->GetObjectArrayElement(files, i), filesUTF[i]); } free(filesUTF); for (int i=0; i<keyCount; i++) { env->ReleaseStringUTFChars((jstring)env->GetObjectArrayElement(keys, i), keysUTF[i]); } free(keysUTF); return (jint) err; }
/* * Class: info_kghost_android_openvpn_OpenVpn_ControlChannel * Method: recv * Signature: (Linfo/kghost/android/openvpn/FileDescriptorHolder;Ljava/nio/Buffer;IILinfo/kghost/android/openvpn/FileDescriptorHolder;)I */ JNIEXPORT jint JNICALL Java_info_kghost_android_openvpn_OpenVpn_00024ControlChannel_recv (JNIEnv *env, jclass cls, jobject socket, jobject buffer, jint offset, jint length, jobject fd) { int s = jniGetFDFromFileDescriptor(env, socket); if (s < 0) { throwError(env, "java/lang/IllegalArgumentException", "socket"); return -1; } jlong cap = (*env)->GetDirectBufferCapacity(env, buffer); char* ptr = (*env)->GetDirectBufferAddress(env, buffer); int recvfd = -1; int result = read_fd(s, ptr+offset, min(cap-offset, length), &recvfd); if (result < 0) { switch (errno) { case EBADF: case ENOTSOCK: case ENOTCONN: case ECONNREFUSED: throwError(env, "java/lang/IllegalArgumentException", "socket"); break; case EINVAL: throwError(env, "java/lang/IllegalArgumentException", "inval"); break; case EFAULT: throwError(env, "java/lang/IllegalArgumentException", "buffer"); break; case EINTR: throwError(env, "java/lang/InterruptedException", "interrupted"); break; case ENOMEM: throwError(env, "java/lang/RuntimeException", "oom"); break; case EAGAIN: throwError(env, "java/lang/IllegalArgumentException", "non-block socket"); break; default: throwError(env, "java/lang/RuntimeException", "unknown error"); break; } return result; } if (recvfd >= 0) { jniSetFileDescriptorOfFD(env, fd, recvfd); } return result; }
static void android_server_UsbMidiDevice_close(JNIEnv *env, jobject thiz, jobjectArray fds) { // write to mPipeFD to unblock input thread jint pipeFD = env->GetIntField(thiz, sPipeFDField); write(pipeFD, &pipeFD, sizeof(pipeFD)); close(pipeFD); env->SetIntField(thiz, sPipeFDField, -1); int count = env->GetArrayLength(fds); for (int i = 0; i < count; i++) { jobject fd = env->GetObjectArrayElement(fds, i); close(jniGetFDFromFileDescriptor(env, fd)); } }
static void com_android_internal_os_ZygoteInit_reopenStdio(JNIEnv* env, jobject clazz, jobject in, jobject out, jobject errfd) { int fd; int err; fd = jniGetFDFromFileDescriptor(env, in); if (env->ExceptionOccurred() != NULL) { return; } do { err = dup2(fd, STDIN_FILENO); } while (err < 0 && errno == EINTR); fd = jniGetFDFromFileDescriptor(env, out); if (env->ExceptionOccurred() != NULL) { return; } do { err = dup2(fd, STDOUT_FILENO); } while (err < 0 && errno == EINTR); fd = jniGetFDFromFileDescriptor(env, errfd); if (env->ExceptionOccurred() != NULL) { return; } do { err = dup2(fd, STDERR_FILENO); } while (err < 0 && errno == EINTR); }
static jint QTagUid_untagSocketFd(JNIEnv* env, jclass, jobject fileDescriptor) { int userFd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionCheck()) { ALOGE("Can't get FileDescriptor num"); return (jint)-1; } int res = qtaguid_untagSocket(userFd); if (res < 0) { return (jint)-errno; } return (jint)res; }
static jint socket_available (JNIEnv *env, jobject object, jobject fileDescriptor) { int fd; fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (env->ExceptionOccurred() != NULL) { return (jint)-1; } #if 1 int avail; int ret = ioctl(fd, FIONREAD, &avail); // If this were a non-socket fd, there would be other cases to worry // about... if (ret < 0) { jniThrowIOException(env, errno); return (jint) 0; } return (jint)avail; #else // there appears to be a bionic bug that prevents this version from working. ssize_t ret; struct msghdr msg; memset(&msg, 0, sizeof(msg)); do { ret = recvmsg(fd, &msg, MSG_PEEK | MSG_DONTWAIT | MSG_NOSIGNAL); } while (ret < 0 && errno == EINTR); // MSG_PEEK returns 0 on EOF and EWOULDBLOCK on none available if (ret < 0 && errno == EWOULDBLOCK) { return 0; } if (ret < 0) { jniThrowIOException(env, errno); return -1; } return (jint)ret; #endif }
/* * Note: fdSet has to be non-const because although on Linux FD_ISSET() is sane * and takes a const fd_set*, it takes fd_set* on Mac OS. POSIX is not on our * side here: * http://www.opengroup.org/onlinepubs/000095399/functions/select.html */ static bool translateFdSet(JNIEnv* env, jobjectArray fdArray, jint count, fd_set& fdSet, jint* flagArray, size_t offset, jint op) { for (int i = 0; i < count; ++i) { jobject fileDescriptor = env->GetObjectArrayElement(fdArray, i); if (fileDescriptor == NULL) { return false; } const int fd = jniGetFDFromFileDescriptor(env, fileDescriptor); if (isValidFd(fd) && FD_ISSET(fd, &fdSet)) { flagArray[i + offset] = op; } else { flagArray[i + offset] = SOCKET_OP_NONE; } } return true; }
//static void FileDescriptor_syncImpl(JNIEnv* env, jobject obj) { JNIEXPORT void JNICALL Java_java_io_FileDescriptor_syncImpl(JNIEnv* env, jobject obj) { int fd = jniGetFDFromFileDescriptor(env, obj); int rc = xi_file_sync(fd); if (rc < 0) { /* * If fd is a socket, then fsync(fd) is defined to fail with * errno EINVAL. This isn't actually cause for concern. * TODO: Look into not bothering to call fsync() at all if * we know we are dealing with a socket. */ log_error(XDLOG, "[java_io_FileDescriptor_syncImpl] SyncFailed!!\n"); jniThrowException(env, "java/io/SyncFailedException", "file sync error!!"); } }